summaryrefslogtreecommitdiffstats
path: root/chromium/third_party/WebKit/Source/core/css
diff options
context:
space:
mode:
authorJocelyn Turcotte <jocelyn.turcotte@digia.com>2014-08-08 14:30:41 +0200
committerJocelyn Turcotte <jocelyn.turcotte@digia.com>2014-08-12 13:49:54 +0200
commitab0a50979b9eb4dfa3320eff7e187e41efedf7a9 (patch)
tree498dfb8a97ff3361a9f7486863a52bb4e26bb898 /chromium/third_party/WebKit/Source/core/css
parent4ce69f7403811819800e7c5ae1318b2647e778d1 (diff)
Update Chromium to beta version 37.0.2062.68
Change-Id: I188e3b5aff1bec75566014291b654eb19f5bc8ca Reviewed-by: Andras Becsi <andras.becsi@digia.com>
Diffstat (limited to 'chromium/third_party/WebKit/Source/core/css')
-rw-r--r--chromium/third_party/WebKit/Source/core/css/AffectedByFocusTest.cpp316
-rw-r--r--chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.cpp237
-rw-r--r--chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.cpp37
-rw-r--r--chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.h30
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSS.idl3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.h8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSAspectRatioValue.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.cpp427
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.h240
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSBorderImage.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSBorderImage.h4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.h10
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.cpp345
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.h53
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCalculationValueTest.cpp196
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.cpp23
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.h41
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.h8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.idl2
-rw-r--r--[-rwxr-xr-x]chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.cpp1142
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.h104
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.cpp10
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.h18
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.cpp46
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.h14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSCustomFontData.h31
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.cpp175
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.h63
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFilterRule.cpp11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFilterRule.h14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFilterValue.cpp44
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFilterValue.h9
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFace.cpp232
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFace.h62
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.cpp6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.h19
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.cpp11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.h14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.cpp266
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.h71
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.cpp37
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.h18
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFaceTest.cpp90
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontFeatureValue.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontSelector.cpp142
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontSelector.h71
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontSelectorClient.h (renamed from chromium/third_party/WebKit/Source/core/css/CSSVariablesMapForEachCallback.h)28
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontValue.cpp12
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFontValue.h18
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.h14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGradientValue.cpp74
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGradientValue.h92
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGrammar.y267
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.h8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGridTemplateAreasValue.cpp (renamed from chromium/third_party/WebKit/Source/core/css/CSSGridTemplateValue.cpp)12
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGridTemplateAreasValue.h (renamed from chromium/third_party/WebKit/Source/core/css/CSSGridTemplateValue.h)21
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.cpp26
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.h8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.h10
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.cpp27
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.h12
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImageValue.cpp66
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImageValue.h36
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImportRule.cpp11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSImportRule.h16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSInheritedValue.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSInitialValue.h10
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.cpp19
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.h22
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.cpp37
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.h27
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.idl2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.cpp149
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.h42
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSLineBoxContainValue.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMarkup.cpp189
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMarkup.h (renamed from chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.cpp)37
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMatrix.cpp43
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMatrix.h28
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMediaRule.cpp7
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMediaRule.h11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.cpp61
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.h61
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSOMUtils.cpp14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSOMUtils.h4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPageRule.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPageRule.h14
-rwxr-xr-xchromium/third_party/WebKit/Source/core/css/CSSParser.h676
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSParserMode.cpp29
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSParserMode.h23
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSParserValues.cpp76
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSParserValues.h42
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSParserValuesTest.cpp41
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.cpp697
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.h197
-rw-r--r--[-rwxr-xr-x]chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValueMappings.h475
-rw-r--r--[-rwxr-xr-x]chromium/third_party/WebKit/Source/core/css/CSSProperties.in145
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSProperty.cpp54
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSProperty.h21
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPropertyNames.in35
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.h47
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSReflectValue.cpp23
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSReflectValue.h19
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRegionRule.cpp61
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRegionRule.h55
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRule.cpp15
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRule.h7
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRule.idl2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRuleList.cpp11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRuleList.h71
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSRuleList.idl3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.h7
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.cpp151
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.h45
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.cpp208
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSelector.cpp391
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSelector.h156
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSelectorList.cpp41
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSelectorList.h25
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSelectorTest.cpp58
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSShaderValue.cpp104
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSShaderValue.h72
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSShadowValue.cpp23
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSShadowValue.h40
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSShorthands.in2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.cpp48
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.h30
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.idl14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleRule.cpp19
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleRule.h16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.cpp222
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.h70
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.idl2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSSupportsRule.h8
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTestHelper.cpp70
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTestHelper.h63
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.h21
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.cpp56
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.h33
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTokenizer-in.cpp174
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTokenizer.h41
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTransformValue.cpp9
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSTransformValue.h9
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSUnicodeRangeValue.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSUnknownRule.h3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValue.cpp302
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValue.h52
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValue.idl1
-rw-r--r--[-rwxr-xr-x]chromium/third_party/WebKit/Source/core/css/CSSValueKeywords.in244
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValueList.cpp59
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValueList.h35
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValuePool.cpp77
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSValuePool.h62
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSVariableValue.h66
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSVariablesIterator.h49
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.cpp121
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.h77
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSViewportRule.cpp11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/CSSViewportRule.h15
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Counter.cpp17
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Counter.h30
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Counter.idl1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.h7
-rw-r--r--chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.h3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.idl6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/DragUpdateTest.cpp69
-rw-r--r--chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.cpp161
-rw-r--r--chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.h87
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFace.cpp393
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFace.h81
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFace.idl29
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceCache.cpp225
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceCache.h (renamed from chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.h)34
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceSet.cpp421
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceSet.h63
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceSet.idl16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.h45
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.idl (renamed from chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.idl)14
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontLoader.cpp95
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontLoader.h51
-rw-r--r--chromium/third_party/WebKit/Source/core/css/FontSize.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/HashTools.h4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.cpp125
-rw-r--r--chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.h61
-rw-r--r--chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.cpp36
-rw-r--r--chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.h36
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.h87
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.in42
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaList.cpp104
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaList.h50
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaList.idl1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQuery.cpp28
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQuery.h23
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.cpp440
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.h67
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluatorTest.cpp102
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryExp.cpp301
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryExp.h73
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryList.cpp24
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryList.h22
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryList.idl3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.cpp27
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.h20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.cpp57
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.h32
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaQuerySetTest.cpp171
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaTypeNames.in15
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValues.cpp206
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValues.h88
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValuesCached.cpp169
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValuesCached.h85
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.cpp132
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.h49
-rw-r--r--chromium/third_party/WebKit/Source/core/css/MediaValuesTest.cpp61
-rw-r--r--chromium/third_party/WebKit/Source/core/css/PageRuleCollector.cpp12
-rw-r--r--chromium/third_party/WebKit/Source/core/css/PageRuleCollector.h3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Pair.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Pair.h35
-rw-r--r--chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.cpp234
-rw-r--r--chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.h109
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RGBColor.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RGBColor.h15
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RGBColor.idl1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Rect.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Rect.h77
-rw-r--r--chromium/third_party/WebKit/Source/core/css/Rect.idl1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.cpp193
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.h70
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuleFeature.cpp513
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuleFeature.h156
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuleSet.cpp340
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuleSet.h126
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuleSetTest.cpp139
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.cpp64
-rw-r--r--chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.h2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SVGCSSComputedStyleDeclaration.cpp63
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SVGCSSParser.cpp427
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SVGCSSPropertyNames.in2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SVGCSSValueKeywords.in1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SelectorChecker.cpp396
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SelectorChecker.h49
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.cpp224
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.h64
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SelectorFilter.cpp37
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SelectorFilter.h2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/SiblingTraversalStrategies.h91
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleColor.h65
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleMedia.cpp12
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleMedia.h11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleMedia.idl3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.cpp323
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.h5
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StylePropertySet.cpp318
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StylePropertySet.h97
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StylePropertyShorthandCustom.cpp47
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleRule.cpp162
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleRule.h134
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleRuleImport.cpp29
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleRuleImport.h22
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheet.h5
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheet.idl3
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheetContents.cpp287
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheetContents.h67
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheetList.cpp23
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheetList.h17
-rw-r--r--chromium/third_party/WebKit/Source/core/css/StyleSheetList.idl10
-rw-r--r--chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.cpp76
-rw-r--r--chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.h19
-rw-r--r--chromium/third_party/WebKit/Source/core/css/WebKitCSSFilterValue.idl5
-rw-r--r--chromium/third_party/WebKit/Source/core/css/WebKitCSSMatrix.idl5
-rw-r--r--chromium/third_party/WebKit/Source/core/css/WebKitCSSMixFunctionValue.idl34
-rw-r--r--chromium/third_party/WebKit/Source/core/css/WebKitCSSRegionRule.idl36
-rw-r--r--chromium/third_party/WebKit/Source/core/css/WebKitCSSTransformValue.idl4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/fullscreen.css1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/html.css84
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.cpp196
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.h103
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSetTest.cpp64
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.cpp167
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.h96
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/StyleSheetInvalidationAnalysis.cpp (renamed from chromium/third_party/WebKit/Source/core/css/StyleInvalidationAnalysis.cpp)62
-rw-r--r--chromium/third_party/WebKit/Source/core/css/invalidation/StyleSheetInvalidationAnalysis.h (renamed from chromium/third_party/WebKit/Source/core/css/StyleInvalidationAnalysis.h)9
-rwxr-xr-xchromium/third_party/WebKit/Source/core/css/make-css-file-arrays.pl6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/mathml.css49
-rw-r--r--chromium/third_party/WebKit/Source/core/css/mediaControls.css74
-rw-r--r--chromium/third_party/WebKit/Source/core/css/mediaControlsAndroid.css34
-rw-r--r--chromium/third_party/WebKit/Source/core/css/navigationTransitions.css13
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser-in.cpp2119
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser.h327
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParserTest.cpp67
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/CSSParserIdioms.h (renamed from chromium/third_party/WebKit/Source/core/css/CSSVariablesMapForEachCallback.idl)24
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/CSSParserObserver.h69
-rw-r--r--[-rwxr-xr-x]chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.cpp (renamed from chromium/third_party/WebKit/Source/core/css/CSSParser-in.cpp)5898
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.h410
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaConditionTest.cpp54
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.cpp28
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.h25
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.cpp66
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.h57
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.cpp265
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.h107
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.cpp129
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.h88
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.cpp527
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.h85
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizerTest.cpp173
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.cpp141
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.h44
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParserTest.cpp82
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.cpp214
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.h59
-rw-r--r--chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParserTest.cpp136
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.cpp152
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.h2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.cpp245
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.h28
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.h12
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.cpp29
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.h17
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.cpp304
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.h4
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.cpp164
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.h41
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/FontBuilderTest.cpp26
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/MatchRequest.h10
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/MatchResult.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.cpp27
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.h1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/MediaQueryResult.h26
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.cpp65
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.h15
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleTree.cpp22
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.cpp79
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.h7
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.cpp412
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.h15
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilder.h11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp314
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.h23
-rw-r--r--[-rwxr-xr-x]chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderCustom.cpp1908
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.cpp890
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.h142
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverIncludes.h13
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.cpp13
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.h78
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.cpp41
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.h60
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.cpp104
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.h17
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.cpp37
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.h6
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.cpp78
-rw-r--r--chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.h16
-rw-r--r--chromium/third_party/WebKit/Source/core/css/svg.css11
-rw-r--r--chromium/third_party/WebKit/Source/core/css/themeChromium.css2
-rw-r--r--chromium/third_party/WebKit/Source/core/css/themeChromiumAndroid.css17
-rw-r--r--chromium/third_party/WebKit/Source/core/css/themeMac.css20
-rw-r--r--chromium/third_party/WebKit/Source/core/css/themeWin.css1
-rw-r--r--chromium/third_party/WebKit/Source/core/css/view-source.css5
371 files changed, 22809 insertions, 17401 deletions
diff --git a/chromium/third_party/WebKit/Source/core/css/AffectedByFocusTest.cpp b/chromium/third_party/WebKit/Source/core/css/AffectedByFocusTest.cpp
new file mode 100644
index 00000000000..c2c4467ba29
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/AffectedByFocusTest.cpp
@@ -0,0 +1,316 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/HTMLNames.h"
+#include "core/dom/Element.h"
+#include "core/dom/ElementTraversal.h"
+#include "core/dom/NodeRenderStyle.h"
+#include "core/frame/FrameView.h"
+#include "core/html/HTMLDocument.h"
+#include "core/html/HTMLElement.h"
+#include "core/testing/DummyPageHolder.h"
+#include <gtest/gtest.h>
+
+using namespace WebCore;
+using namespace HTMLNames;
+
+namespace {
+
+class AffectedByFocusTest : public ::testing::Test {
+
+protected:
+
+ struct ElementResult {
+ const WebCore::QualifiedName tag;
+ bool affectedBy;
+ bool childrenOrSiblingsAffectedBy;
+ };
+
+ virtual void SetUp() OVERRIDE;
+
+ HTMLDocument& document() const { return *m_document; }
+
+ void setHtmlInnerHTML(const char* htmlContent);
+
+ void checkElements(ElementResult expected[], unsigned expectedCount) const;
+
+private:
+ OwnPtr<DummyPageHolder> m_dummyPageHolder;
+
+ HTMLDocument* m_document;
+};
+
+void AffectedByFocusTest::SetUp()
+{
+ m_dummyPageHolder = DummyPageHolder::create(IntSize(800, 600));
+ m_document = toHTMLDocument(&m_dummyPageHolder->document());
+ ASSERT(m_document);
+}
+
+void AffectedByFocusTest::setHtmlInnerHTML(const char* htmlContent)
+{
+ document().documentElement()->setInnerHTML(String::fromUTF8(htmlContent), ASSERT_NO_EXCEPTION);
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+}
+
+void AffectedByFocusTest::checkElements(ElementResult expected[], unsigned expectedCount) const
+{
+ unsigned i = 0;
+ Element* elm = document().body();
+
+ for (; elm && i < expectedCount; elm = ElementTraversal::next(*elm), ++i) {
+ ASSERT_TRUE(elm->hasTagName(expected[i].tag));
+ ASSERT(elm->renderStyle());
+ ASSERT_EQ(expected[i].affectedBy, elm->renderStyle()->affectedByFocus());
+ ASSERT_EQ(expected[i].childrenOrSiblingsAffectedBy, elm->childrenOrSiblingsAffectedByFocus());
+ }
+
+ ASSERT(!elm && i == expectedCount);
+}
+
+// A global :focus rule in html.css currently causes every single element to be
+// affectedByFocus. Check that all elements in a document with no :focus rules
+// gets the affectedByFocus set on RenderStyle and not childrenOrSiblingsAffectedByFocus.
+TEST_F(AffectedByFocusTest, UAUniversalFocusRule)
+{
+ ElementResult expected[] = {
+ { bodyTag, true, false },
+ { divTag, true, false },
+ { divTag, true, false },
+ { divTag, true, false },
+ { spanTag, true, false }
+ };
+
+ setHtmlInnerHTML("<body>"
+ "<div><div></div></div>"
+ "<div><span></span></div>"
+ "</body>");
+
+ checkElements(expected, sizeof(expected) / sizeof(ElementResult));
+}
+
+// ":focus div" will mark ascendants of all divs with childrenOrSiblingsAffectedByFocus.
+TEST_F(AffectedByFocusTest, FocusedAscendant)
+{
+ ElementResult expected[] = {
+ { bodyTag, true, true },
+ { divTag, true, true },
+ { divTag, true, false },
+ { divTag, true, false },
+ { spanTag, true, false }
+ };
+
+ setHtmlInnerHTML("<head>"
+ "<style>:focus div { background-color: pink }</style>"
+ "</head>"
+ "<body>"
+ "<div><div></div></div>"
+ "<div><span></span></div>"
+ "</body>");
+
+ checkElements(expected, sizeof(expected) / sizeof(ElementResult));
+}
+
+// "body:focus div" will mark the body element with childrenOrSiblingsAffectedByFocus.
+TEST_F(AffectedByFocusTest, FocusedAscendantWithType)
+{
+ ElementResult expected[] = {
+ { bodyTag, true, true },
+ { divTag, true, false },
+ { divTag, true, false },
+ { divTag, true, false },
+ { spanTag, true, false }
+ };
+
+ setHtmlInnerHTML("<head>"
+ "<style>body:focus div { background-color: pink }</style>"
+ "</head>"
+ "<body>"
+ "<div><div></div></div>"
+ "<div><span></span></div>"
+ "</body>");
+
+ checkElements(expected, sizeof(expected) / sizeof(ElementResult));
+}
+
+// ":not(body):focus div" should not mark the body element with childrenOrSiblingsAffectedByFocus.
+// Note that currently ":focus:not(body)" does not do the same. Then the :focus is
+// checked and the childrenOrSiblingsAffectedByFocus flag set before the negated type selector
+// is found.
+TEST_F(AffectedByFocusTest, FocusedAscendantWithNegatedType)
+{
+ ElementResult expected[] = {
+ { bodyTag, true, false },
+ { divTag, true, true },
+ { divTag, true, false },
+ { divTag, true, false },
+ { spanTag, true, false }
+ };
+
+ setHtmlInnerHTML("<head>"
+ "<style>:not(body):focus div { background-color: pink }</style>"
+ "</head>"
+ "<body>"
+ "<div><div></div></div>"
+ "<div><span></span></div>"
+ "</body>");
+
+ checkElements(expected, sizeof(expected) / sizeof(ElementResult));
+}
+
+// Checking current behavior for ":focus + div", but this is a BUG or at best
+// sub-optimal. The focused element will also in this case get childrenOrSiblingsAffectedByFocus
+// even if it's really a sibling. Effectively, the whole sub-tree of the focused
+// element will have styles recalculated even though none of the children are
+// affected. There are other mechanisms that makes sure the sibling also gets its
+// styles recalculated.
+TEST_F(AffectedByFocusTest, FocusedSibling)
+{
+ ElementResult expected[] = {
+ { bodyTag, true, false },
+ { divTag, true, true },
+ { spanTag, true, false },
+ { divTag, true, false }
+ };
+
+ setHtmlInnerHTML("<head>"
+ "<style>:focus + div { background-color: pink }</style>"
+ "</head>"
+ "<body>"
+ "<div>"
+ " <span></span>"
+ "</div>"
+ "<div></div>"
+ "</body>");
+
+ checkElements(expected, sizeof(expected) / sizeof(ElementResult));
+}
+
+TEST_F(AffectedByFocusTest, AffectedByFocusUpdate)
+{
+ // Check that when focussing the outer div in the document below, you only
+ // get a single element style recalc.
+
+ setHtmlInnerHTML("<style>:focus { border: 1px solid lime; }</style>"
+ "<div id=d tabIndex=1>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "</div>");
+
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned startCount = document().styleEngine()->resolverAccessCount();
+
+ document().getElementById("d")->focus();
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned accessCount = document().styleEngine()->resolverAccessCount() - startCount;
+
+ ASSERT_EQ(1U, accessCount);
+}
+
+TEST_F(AffectedByFocusTest, ChildrenOrSiblingsAffectedByFocusUpdate)
+{
+ // Check that when focussing the outer div in the document below, you get a
+ // style recalc for the whole subtree.
+
+ setHtmlInnerHTML("<style>:focus div { border: 1px solid lime; }</style>"
+ "<div id=d tabIndex=1>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "</div>");
+
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned startCount = document().styleEngine()->resolverAccessCount();
+
+ document().getElementById("d")->focus();
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned accessCount = document().styleEngine()->resolverAccessCount() - startCount;
+
+ ASSERT_EQ(11U, accessCount);
+}
+
+TEST_F(AffectedByFocusTest, InvalidationSetFocusUpdate)
+{
+ // Check that when focussing the outer div in the document below, you get a
+ // style recalc for the outer div and the class=a div only.
+
+ setHtmlInnerHTML("<style>:focus .a { border: 1px solid lime; }</style>"
+ "<div id=d tabIndex=1>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div class='a'></div>"
+ "</div>");
+
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned startCount = document().styleEngine()->resolverAccessCount();
+
+ document().getElementById("d")->focus();
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned accessCount = document().styleEngine()->resolverAccessCount() - startCount;
+
+ ASSERT_EQ(2U, accessCount);
+}
+
+TEST_F(AffectedByFocusTest, NoInvalidationSetFocusUpdate)
+{
+ // Check that when focussing the outer div in the document below, you get a
+ // style recalc for the outer div only. The invalidation set for :focus will
+ // include 'a', but the id=d div should be affectedByFocus, not childrenOrSiblingsAffectedByFocus.
+
+ setHtmlInnerHTML("<style>#nomatch:focus .a { border: 1px solid lime; }</style>"
+ "<div id=d tabIndex=1>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div></div>"
+ "<div class='a'></div>"
+ "</div>");
+
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned startCount = document().styleEngine()->resolverAccessCount();
+
+ document().getElementById("d")->focus();
+ document().view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned accessCount = document().styleEngine()->resolverAccessCount() - startCount;
+
+ ASSERT_EQ(1U, accessCount);
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.cpp b/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.cpp
index a49ea1495f1..e6399b99187 100644
--- a/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.cpp
@@ -33,58 +33,68 @@
#include "core/css/CSSBasicShapes.h"
#include "core/css/CSSPrimitiveValueMappings.h"
#include "core/css/CSSValuePool.h"
+#include "core/css/Pair.h"
#include "core/css/resolver/StyleResolverState.h"
#include "core/rendering/style/BasicShapes.h"
#include "core/rendering/style/RenderStyle.h"
namespace WebCore {
-PassRefPtr<CSSValue> valueForBasicShape(const RenderStyle& style, const BasicShape* basicShape)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForCenterCoordinate(CSSValuePool& pool, const RenderStyle& style, const BasicShapeCenterCoordinate& center, EBoxOrient orientation)
+{
+ if (center.direction() == BasicShapeCenterCoordinate::TopLeft)
+ return pool.createValue(center.length(), style);
+
+ CSSValueID keyword = orientation == HORIZONTAL ? CSSValueRight : CSSValueBottom;
+
+ return pool.createValue(Pair::create(pool.createIdentifierValue(keyword), pool.createValue(center.length(), style), Pair::DropIdenticalValues));
+}
+
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> basicShapeRadiusToCSSValue(CSSValuePool& pool, const RenderStyle& style, const BasicShapeRadius& radius)
+{
+ switch (radius.type()) {
+ case BasicShapeRadius::Value:
+ return pool.createValue(radius.value(), style);
+ case BasicShapeRadius::ClosestSide:
+ return pool.createIdentifierValue(CSSValueClosestSide);
+ case BasicShapeRadius::FarthestSide:
+ return pool.createIdentifierValue(CSSValueFarthestSide);
+ }
+
+ ASSERT_NOT_REACHED();
+ return nullptr;
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> valueForBasicShape(const RenderStyle& style, const BasicShape* basicShape)
{
CSSValuePool& pool = cssValuePool();
- RefPtr<CSSBasicShape> basicShapeValue;
+ RefPtrWillBeRawPtr<CSSBasicShape> basicShapeValue = nullptr;
switch (basicShape->type()) {
- case BasicShape::BasicShapeRectangleType: {
- const BasicShapeRectangle* rectangle = static_cast<const BasicShapeRectangle*>(basicShape);
- RefPtr<CSSBasicShapeRectangle> rectangleValue = CSSBasicShapeRectangle::create();
-
- rectangleValue->setX(pool.createValue(rectangle->x(), style));
- rectangleValue->setY(pool.createValue(rectangle->y(), style));
- rectangleValue->setWidth(pool.createValue(rectangle->width(), style));
- rectangleValue->setHeight(pool.createValue(rectangle->height(), style));
- rectangleValue->setRadiusX(pool.createValue(rectangle->cornerRadiusX(), style));
- rectangleValue->setRadiusY(pool.createValue(rectangle->cornerRadiusY(), style));
-
- basicShapeValue = rectangleValue.release();
- break;
- }
case BasicShape::BasicShapeCircleType: {
const BasicShapeCircle* circle = static_cast<const BasicShapeCircle*>(basicShape);
- RefPtr<CSSBasicShapeCircle> circleValue = CSSBasicShapeCircle::create();
-
- circleValue->setCenterX(pool.createValue(circle->centerX(), style));
- circleValue->setCenterY(pool.createValue(circle->centerY(), style));
- circleValue->setRadius(pool.createValue(circle->radius(), style));
+ RefPtrWillBeRawPtr<CSSBasicShapeCircle> circleValue = CSSBasicShapeCircle::create();
+ circleValue->setCenterX(valueForCenterCoordinate(pool, style, circle->centerX(), HORIZONTAL));
+ circleValue->setCenterY(valueForCenterCoordinate(pool, style, circle->centerY(), VERTICAL));
+ circleValue->setRadius(basicShapeRadiusToCSSValue(pool, style, circle->radius()));
basicShapeValue = circleValue.release();
break;
}
case BasicShape::BasicShapeEllipseType: {
const BasicShapeEllipse* ellipse = static_cast<const BasicShapeEllipse*>(basicShape);
- RefPtr<CSSBasicShapeEllipse> ellipseValue = CSSBasicShapeEllipse::create();
-
- ellipseValue->setCenterX(pool.createValue(ellipse->centerX(), style));
- ellipseValue->setCenterY(pool.createValue(ellipse->centerY(), style));
- ellipseValue->setRadiusX(pool.createValue(ellipse->radiusX(), style));
- ellipseValue->setRadiusY(pool.createValue(ellipse->radiusY(), style));
+ RefPtrWillBeRawPtr<CSSBasicShapeEllipse> ellipseValue = CSSBasicShapeEllipse::create();
+ ellipseValue->setCenterX(valueForCenterCoordinate(pool, style, ellipse->centerX(), HORIZONTAL));
+ ellipseValue->setCenterY(valueForCenterCoordinate(pool, style, ellipse->centerY(), VERTICAL));
+ ellipseValue->setRadiusX(basicShapeRadiusToCSSValue(pool, style, ellipse->radiusX()));
+ ellipseValue->setRadiusY(basicShapeRadiusToCSSValue(pool, style, ellipse->radiusY()));
basicShapeValue = ellipseValue.release();
break;
}
case BasicShape::BasicShapePolygonType: {
const BasicShapePolygon* polygon = static_cast<const BasicShapePolygon*>(basicShape);
- RefPtr<CSSBasicShapePolygon> polygonValue = CSSBasicShapePolygon::create();
+ RefPtrWillBeRawPtr<CSSBasicShapePolygon> polygonValue = CSSBasicShapePolygon::create();
polygonValue->setWindRule(polygon->windRule());
const Vector<Length>& values = polygon->values();
@@ -94,65 +104,117 @@ PassRefPtr<CSSValue> valueForBasicShape(const RenderStyle& style, const BasicSha
basicShapeValue = polygonValue.release();
break;
}
- case BasicShape::BasicShapeInsetRectangleType: {
- const BasicShapeInsetRectangle* rectangle = static_cast<const BasicShapeInsetRectangle*>(basicShape);
- RefPtr<CSSBasicShapeInsetRectangle> rectangleValue = CSSBasicShapeInsetRectangle::create();
-
- rectangleValue->setTop(cssValuePool().createValue(rectangle->top()));
- rectangleValue->setRight(cssValuePool().createValue(rectangle->right()));
- rectangleValue->setBottom(cssValuePool().createValue(rectangle->bottom()));
- rectangleValue->setLeft(cssValuePool().createValue(rectangle->left()));
- rectangleValue->setRadiusX(cssValuePool().createValue(rectangle->cornerRadiusX()));
- rectangleValue->setRadiusY(cssValuePool().createValue(rectangle->cornerRadiusY()));
-
- basicShapeValue = rectangleValue.release();
+ case BasicShape::BasicShapeInsetType: {
+ const BasicShapeInset* inset = static_cast<const BasicShapeInset*>(basicShape);
+ RefPtrWillBeRawPtr<CSSBasicShapeInset> insetValue = CSSBasicShapeInset::create();
+
+ insetValue->setTop(pool.createValue(inset->top(), style));
+ insetValue->setRight(pool.createValue(inset->right(), style));
+ insetValue->setBottom(pool.createValue(inset->bottom(), style));
+ insetValue->setLeft(pool.createValue(inset->left(), style));
+
+ insetValue->setTopLeftRadius(CSSPrimitiveValue::create(inset->topLeftRadius(), style));
+ insetValue->setTopRightRadius(CSSPrimitiveValue::create(inset->topRightRadius(), style));
+ insetValue->setBottomRightRadius(CSSPrimitiveValue::create(inset->bottomRightRadius(), style));
+ insetValue->setBottomLeftRadius(CSSPrimitiveValue::create(inset->bottomLeftRadius(), style));
+
+ basicShapeValue = insetValue.release();
break;
}
default:
break;
}
+
return pool.createValue(basicShapeValue.release());
}
static Length convertToLength(const StyleResolverState& state, CSSPrimitiveValue* value)
{
+ if (!value)
+ return Length(0, Fixed);
return value->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData());
}
+static LengthSize convertToLengthSize(const StyleResolverState& state, CSSPrimitiveValue* value)
+{
+ if (!value)
+ return LengthSize(Length(0, Fixed), Length(0, Fixed));
+
+ Pair* pair = value->getPairValue();
+ return LengthSize(convertToLength(state, pair->first()), convertToLength(state, pair->second()));
+}
+
+static BasicShapeCenterCoordinate convertToCenterCoordinate(const StyleResolverState& state, CSSPrimitiveValue* value)
+{
+ BasicShapeCenterCoordinate::Direction direction;
+ Length offset = Length(0, Fixed);
+
+ CSSValueID keyword = CSSValueTop;
+ if (!value) {
+ keyword = CSSValueCenter;
+ } else if (value->isValueID()) {
+ keyword = value->getValueID();
+ } else if (Pair* pair = value->getPairValue()) {
+ keyword = pair->first()->getValueID();
+ offset = convertToLength(state, pair->second());
+ } else {
+ offset = convertToLength(state, value);
+ }
+
+ switch (keyword) {
+ case CSSValueTop:
+ case CSSValueLeft:
+ direction = BasicShapeCenterCoordinate::TopLeft;
+ break;
+ case CSSValueRight:
+ case CSSValueBottom:
+ direction = BasicShapeCenterCoordinate::BottomRight;
+ break;
+ case CSSValueCenter:
+ direction = BasicShapeCenterCoordinate::TopLeft;
+ offset = Length(50, Percent);
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ direction = BasicShapeCenterCoordinate::TopLeft;
+ break;
+ }
+
+ return BasicShapeCenterCoordinate(direction, offset);
+}
+
+static BasicShapeRadius cssValueToBasicShapeRadius(const StyleResolverState& state, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radius)
+{
+ if (!radius)
+ return BasicShapeRadius(BasicShapeRadius::ClosestSide);
+
+ if (radius->isValueID()) {
+ switch (radius->getValueID()) {
+ case CSSValueClosestSide:
+ return BasicShapeRadius(BasicShapeRadius::ClosestSide);
+ case CSSValueFarthestSide:
+ return BasicShapeRadius(BasicShapeRadius::FarthestSide);
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+ }
+
+ return BasicShapeRadius(convertToLength(state, radius.get()));
+}
+
PassRefPtr<BasicShape> basicShapeForValue(const StyleResolverState& state, const CSSBasicShape* basicShapeValue)
{
RefPtr<BasicShape> basicShape;
switch (basicShapeValue->type()) {
- case CSSBasicShape::CSSBasicShapeRectangleType: {
- const CSSBasicShapeRectangle* rectValue = static_cast<const CSSBasicShapeRectangle *>(basicShapeValue);
- RefPtr<BasicShapeRectangle> rect = BasicShapeRectangle::create();
-
- rect->setX(convertToLength(state, rectValue->x()));
- rect->setY(convertToLength(state, rectValue->y()));
- rect->setWidth(convertToLength(state, rectValue->width()));
- rect->setHeight(convertToLength(state, rectValue->height()));
- if (rectValue->radiusX()) {
- Length radiusX = convertToLength(state, rectValue->radiusX());
- rect->setCornerRadiusX(radiusX);
- if (rectValue->radiusY())
- rect->setCornerRadiusY(convertToLength(state, rectValue->radiusY()));
- else
- rect->setCornerRadiusY(radiusX);
- } else {
- rect->setCornerRadiusX(Length(0, Fixed));
- rect->setCornerRadiusY(Length(0, Fixed));
- }
- basicShape = rect.release();
- break;
- }
case CSSBasicShape::CSSBasicShapeCircleType: {
const CSSBasicShapeCircle* circleValue = static_cast<const CSSBasicShapeCircle *>(basicShapeValue);
RefPtr<BasicShapeCircle> circle = BasicShapeCircle::create();
- circle->setCenterX(convertToLength(state, circleValue->centerX()));
- circle->setCenterY(convertToLength(state, circleValue->centerY()));
- circle->setRadius(convertToLength(state, circleValue->radius()));
+ circle->setCenterX(convertToCenterCoordinate(state, circleValue->centerX()));
+ circle->setCenterY(convertToCenterCoordinate(state, circleValue->centerY()));
+ circle->setRadius(cssValueToBasicShapeRadius(state, circleValue->radius()));
basicShape = circle.release();
break;
@@ -161,10 +223,10 @@ PassRefPtr<BasicShape> basicShapeForValue(const StyleResolverState& state, const
const CSSBasicShapeEllipse* ellipseValue = static_cast<const CSSBasicShapeEllipse *>(basicShapeValue);
RefPtr<BasicShapeEllipse> ellipse = BasicShapeEllipse::create();
- ellipse->setCenterX(convertToLength(state, ellipseValue->centerX()));
- ellipse->setCenterY(convertToLength(state, ellipseValue->centerY()));
- ellipse->setRadiusX(convertToLength(state, ellipseValue->radiusX()));
- ellipse->setRadiusY(convertToLength(state, ellipseValue->radiusY()));
+ ellipse->setCenterX(convertToCenterCoordinate(state, ellipseValue->centerX()));
+ ellipse->setCenterY(convertToCenterCoordinate(state, ellipseValue->centerY()));
+ ellipse->setRadiusX(cssValueToBasicShapeRadius(state, ellipseValue->radiusX()));
+ ellipse->setRadiusY(cssValueToBasicShapeRadius(state, ellipseValue->radiusY()));
basicShape = ellipse.release();
break;
@@ -174,38 +236,45 @@ PassRefPtr<BasicShape> basicShapeForValue(const StyleResolverState& state, const
RefPtr<BasicShapePolygon> polygon = BasicShapePolygon::create();
polygon->setWindRule(polygonValue->windRule());
- const Vector<RefPtr<CSSPrimitiveValue> >& values = polygonValue->values();
+ const WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue> >& values = polygonValue->values();
for (unsigned i = 0; i < values.size(); i += 2)
polygon->appendPoint(convertToLength(state, values.at(i).get()), convertToLength(state, values.at(i + 1).get()));
basicShape = polygon.release();
break;
}
- case CSSBasicShape::CSSBasicShapeInsetRectangleType: {
- const CSSBasicShapeInsetRectangle* rectValue = static_cast<const CSSBasicShapeInsetRectangle *>(basicShapeValue);
- RefPtr<BasicShapeInsetRectangle> rect = BasicShapeInsetRectangle::create();
+ case CSSBasicShape::CSSBasicShapeInsetType: {
+ const CSSBasicShapeInset* rectValue = static_cast<const CSSBasicShapeInset* >(basicShapeValue);
+ RefPtr<BasicShapeInset> rect = BasicShapeInset::create();
rect->setTop(convertToLength(state, rectValue->top()));
rect->setRight(convertToLength(state, rectValue->right()));
rect->setBottom(convertToLength(state, rectValue->bottom()));
rect->setLeft(convertToLength(state, rectValue->left()));
- if (rectValue->radiusX()) {
- Length radiusX = convertToLength(state, rectValue->radiusX());
- rect->setCornerRadiusX(radiusX);
- if (rectValue->radiusY())
- rect->setCornerRadiusY(convertToLength(state, rectValue->radiusY()));
- else
- rect->setCornerRadiusY(radiusX);
- } else {
- rect->setCornerRadiusX(Length(0, Fixed));
- rect->setCornerRadiusY(Length(0, Fixed));
- }
+
+ rect->setTopLeftRadius(convertToLengthSize(state, rectValue->topLeftRadius()));
+ rect->setTopRightRadius(convertToLengthSize(state, rectValue->topRightRadius()));
+ rect->setBottomRightRadius(convertToLengthSize(state, rectValue->bottomRightRadius()));
+ rect->setBottomLeftRadius(convertToLengthSize(state, rectValue->bottomLeftRadius()));
+
basicShape = rect.release();
break;
}
default:
break;
}
+
return basicShape.release();
}
+
+FloatPoint floatPointForCenterCoordinate(const BasicShapeCenterCoordinate& centerX, const BasicShapeCenterCoordinate& centerY, FloatSize boxSize)
+{
+ FloatPoint p;
+ float offset = floatValueForLength(centerX.length(), boxSize.width());
+ p.setX(centerX.direction() == BasicShapeCenterCoordinate::TopLeft ? offset : boxSize.width() - offset);
+ offset = floatValueForLength(centerY.length(), boxSize.height());
+ p.setY(centerY.direction() == BasicShapeCenterCoordinate::TopLeft ? offset : boxSize.height() - offset);
+ return p;
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.h b/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.h
index 7d07e311a2e..ab1fdcc93ca 100644
--- a/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.h
+++ b/chromium/third_party/WebKit/Source/core/css/BasicShapeFunctions.h
@@ -30,6 +30,8 @@
#ifndef BasicShapeFunctions_h
#define BasicShapeFunctions_h
+#include "core/rendering/style/BasicShapes.h"
+#include "platform/heap/Handle.h"
#include "wtf/PassRefPtr.h"
namespace WebCore {
@@ -37,11 +39,13 @@ namespace WebCore {
class BasicShape;
class CSSBasicShape;
class CSSValue;
+class FloatPoint;
class StyleResolverState;
class RenderStyle;
-PassRefPtr<CSSValue> valueForBasicShape(const RenderStyle&, const BasicShape*);
+PassRefPtrWillBeRawPtr<CSSValue> valueForBasicShape(const RenderStyle&, const BasicShape*);
PassRefPtr<BasicShape> basicShapeForValue(const StyleResolverState&, const CSSBasicShape*);
+FloatPoint floatPointForCenterCoordinate(const BasicShapeCenterCoordinate&, const BasicShapeCenterCoordinate&, FloatSize);
}
#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.cpp b/chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.cpp
new file mode 100644
index 00000000000..c32f8ede4e9
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.cpp
@@ -0,0 +1,37 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/BinaryDataFontFaceSource.h"
+
+#include "platform/SharedBuffer.h"
+#include "platform/fonts/FontCustomPlatformData.h"
+#include "platform/fonts/FontDescription.h"
+#include "platform/fonts/SimpleFontData.h"
+
+namespace WebCore {
+
+BinaryDataFontFaceSource::BinaryDataFontFaceSource(SharedBuffer* data)
+ : m_customPlatformData(FontCustomPlatformData::create(data))
+{
+}
+
+BinaryDataFontFaceSource::~BinaryDataFontFaceSource()
+{
+}
+
+bool BinaryDataFontFaceSource::isValid() const
+{
+ return m_customPlatformData;
+}
+
+PassRefPtr<SimpleFontData> BinaryDataFontFaceSource::createFontData(const FontDescription& fontDescription)
+{
+ return SimpleFontData::create(
+ m_customPlatformData->fontPlatformData(fontDescription.effectiveFontSize(),
+ fontDescription.isSyntheticBold(), fontDescription.isSyntheticItalic(),
+ fontDescription.orientation(), fontDescription.widthVariant()), CustomFontData::create());
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.h b/chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.h
new file mode 100644
index 00000000000..766bbbb3b32
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/BinaryDataFontFaceSource.h
@@ -0,0 +1,30 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef BinaryDataFontFaceSource_h
+#define BinaryDataFontFaceSource_h
+
+#include "core/css/CSSFontFaceSource.h"
+#include "wtf/OwnPtr.h"
+
+namespace WebCore {
+
+class FontCustomPlatformData;
+class SharedBuffer;
+
+class BinaryDataFontFaceSource FINAL : public CSSFontFaceSource {
+public:
+ explicit BinaryDataFontFaceSource(SharedBuffer*);
+ virtual ~BinaryDataFontFaceSource();
+ virtual bool isValid() const OVERRIDE;
+
+private:
+ virtual PassRefPtr<SimpleFontData> createFontData(const FontDescription&) OVERRIDE;
+
+ OwnPtr<FontCustomPlatformData> m_customPlatformData;
+};
+
+} // namespace WebCore
+
+#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/CSS.idl b/chromium/third_party/WebKit/Source/core/css/CSS.idl
index 4ba9ba74af4..36fe6dacce8 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSS.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSS.idl
@@ -29,7 +29,8 @@
[
NoInterfaceObject,
- ImplementedAs=DOMWindowCSS
+ ImplementedAs=DOMWindowCSS,
+ WillBeGarbageCollected
] interface CSS {
boolean supports(DOMString property, DOMString value);
boolean supports(DOMString conditionText);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.cpp
index 3ead9d8137b..1c1d6c44fe6 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.cpp
@@ -47,9 +47,9 @@ String CSSArrayFunctionValue::customCSSText() const
return "array(" + CSSValueList::customCSSText() + ')';
}
-PassRefPtr<CSSArrayFunctionValue> CSSArrayFunctionValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSArrayFunctionValue> CSSArrayFunctionValue::cloneForCSSOM() const
{
- return adoptRef(new CSSArrayFunctionValue(*this));
+ return adoptRefWillBeNoop(new CSSArrayFunctionValue(*this));
}
bool CSSArrayFunctionValue::equals(const CSSArrayFunctionValue& other) const
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.h b/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.h
index fffc616c32d..ebf1575a8e4 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSArrayFunctionValue.h
@@ -37,17 +37,19 @@ namespace WebCore {
class CSSArrayFunctionValue : public CSSValueList {
public:
- static PassRefPtr<CSSArrayFunctionValue> create()
+ static PassRefPtrWillBeRawPtr<CSSArrayFunctionValue> create()
{
- return adoptRef(new CSSArrayFunctionValue());
+ return adoptRefWillBeNoop(new CSSArrayFunctionValue());
}
String customCSSText() const;
- PassRefPtr<CSSArrayFunctionValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSArrayFunctionValue> cloneForCSSOM() const;
bool equals(const CSSArrayFunctionValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValueList::traceAfterDispatch(visitor); }
+
private:
CSSArrayFunctionValue();
explicit CSSArrayFunctionValue(const CSSArrayFunctionValue& cloneFrom);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSAspectRatioValue.h b/chromium/third_party/WebKit/Source/core/css/CSSAspectRatioValue.h
index a92ac34c2bb..bb86a0bffc9 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSAspectRatioValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSAspectRatioValue.h
@@ -35,9 +35,9 @@ namespace WebCore {
class CSSAspectRatioValue : public CSSValue {
public:
- static PassRefPtr<CSSAspectRatioValue> create(float numeratorValue, float denominatorValue)
+ static PassRefPtrWillBeRawPtr<CSSAspectRatioValue> create(float numeratorValue, float denominatorValue)
{
- return adoptRef(new CSSAspectRatioValue(numeratorValue, denominatorValue));
+ return adoptRefWillBeNoop(new CSSAspectRatioValue(numeratorValue, denominatorValue));
}
String customCSSText() const;
@@ -47,6 +47,8 @@ public:
bool equals(const CSSAspectRatioValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSAspectRatioValue(float numeratorValue, float denominatorValue)
: CSSValue(AspectRatioClass)
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.cpp b/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.cpp
index 1104f176ef9..2f326c9e0f2 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.cpp
@@ -30,91 +30,98 @@
#include "config.h"
#include "core/css/CSSBasicShapes.h"
+#include "core/css/CSSValuePool.h"
+#include "core/css/Pair.h"
+#include "platform/Length.h"
#include "wtf/text/StringBuilder.h"
using namespace WTF;
namespace WebCore {
-static String buildRectangleString(const String& x, const String& y, const String& width, const String& height, const String& radiusX, const String& radiusY)
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(CSSBasicShape)
+
+static String buildCircleString(const String& radius, const String& centerX, const String& centerY, const String& box)
{
- char opening[] = "rectangle(";
- char separator[] = ", ";
+ char at[] = "at";
+ char separator[] = " ";
StringBuilder result;
- // Compute the required capacity in advance to reduce allocations.
- result.reserveCapacity((sizeof(opening) - 1) + (5 * (sizeof(separator) - 1)) + 1 + x.length() + y.length() + width.length() + height.length() + radiusX.length() + radiusY.length());
- result.appendLiteral(opening);
- result.append(x);
- result.appendLiteral(separator);
- result.append(y);
- result.appendLiteral(separator);
- result.append(width);
- result.appendLiteral(separator);
- result.append(height);
- if (!radiusX.isNull()) {
- result.appendLiteral(separator);
- result.append(radiusX);
- if (!radiusY.isNull()) {
+ result.appendLiteral("circle(");
+ if (!radius.isNull())
+ result.append(radius);
+
+ if (!centerX.isNull() || !centerY.isNull()) {
+ if (!radius.isNull())
result.appendLiteral(separator);
- result.append(radiusY);
- }
+ result.append(at);
+ result.appendLiteral(separator);
+ result.append(centerX);
+ result.appendLiteral(separator);
+ result.append(centerY);
+ }
+ result.append(")");
+ if (box.length()) {
+ result.appendLiteral(separator);
+ result.append(box);
}
- result.append(')');
return result.toString();
}
-String CSSBasicShapeRectangle::cssText() const
+static String serializePositionOffset(const Pair& offset, const Pair& other)
{
- return buildRectangleString(m_x->cssText(),
- m_y->cssText(),
- m_width->cssText(),
- m_height->cssText(),
- m_radiusX.get() ? m_radiusX->cssText() : String(),
- m_radiusY.get() ? m_radiusY->cssText() : String());
+ if ((offset.first()->getValueID() == CSSValueLeft && other.first()->getValueID() == CSSValueTop)
+ || (offset.first()->getValueID() == CSSValueTop && other.first()->getValueID() == CSSValueLeft))
+ return offset.second()->cssText();
+ return offset.cssText();
}
-bool CSSBasicShapeRectangle::equals(const CSSBasicShape& shape) const
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> buildSerializablePositionOffset(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> offset, CSSValueID defaultSide)
{
- if (shape.type() != CSSBasicShapeRectangleType)
- return false;
+ CSSValueID side = defaultSide;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> amount = nullptr;
+
+ if (!offset) {
+ side = CSSValueCenter;
+ } else if (offset->isValueID()) {
+ side = offset->getValueID();
+ } else if (Pair* pair = offset->getPairValue()) {
+ side = pair->first()->getValueID();
+ amount = pair->second();
+ } else {
+ amount = offset;
+ }
- const CSSBasicShapeRectangle& other = static_cast<const CSSBasicShapeRectangle&>(shape);
- return compareCSSValuePtr(m_x, other.m_x)
- && compareCSSValuePtr(m_y, other.m_y)
- && compareCSSValuePtr(m_width, other.m_width)
- && compareCSSValuePtr(m_height, other.m_height)
- && compareCSSValuePtr(m_radiusX, other.m_radiusX)
- && compareCSSValuePtr(m_radiusY, other.m_radiusY);
-}
+ if (side == CSSValueCenter) {
+ side = defaultSide;
+ amount = cssValuePool().createValue(50, CSSPrimitiveValue::CSS_PERCENTAGE);
+ } else if ((side == CSSValueRight || side == CSSValueBottom)
+ && amount->isPercentage()) {
+ side = defaultSide;
+ amount = cssValuePool().createValue(100 - amount->getFloatValue(), CSSPrimitiveValue::CSS_PERCENTAGE);
+ } else if (amount->isLength() && !amount->getFloatValue()) {
+ if (side == CSSValueRight || side == CSSValueBottom)
+ amount = cssValuePool().createValue(100, CSSPrimitiveValue::CSS_PERCENTAGE);
+ else
+ amount = cssValuePool().createValue(0, CSSPrimitiveValue::CSS_PERCENTAGE);
+ side = defaultSide;
+ }
-String CSSBasicShapeRectangle::serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- return buildRectangleString(m_x->serializeResolvingVariables(variables),
- m_y->serializeResolvingVariables(variables),
- m_width->serializeResolvingVariables(variables),
- m_height->serializeResolvingVariables(variables),
- m_radiusX.get() ? m_radiusX->serializeResolvingVariables(variables) : String(),
- m_radiusY.get() ? m_radiusY->serializeResolvingVariables(variables) : String());
+ return cssValuePool().createValue(Pair::create(cssValuePool().createValue(side), amount.release(), Pair::KeepIdenticalValues));
}
-bool CSSBasicShapeRectangle::hasVariableReference() const
+String CSSBasicShapeCircle::cssText() const
{
- return m_x->hasVariableReference()
- || m_y->hasVariableReference()
- || m_width->hasVariableReference()
- || m_height->hasVariableReference()
- || (m_radiusX.get() && m_radiusX->hasVariableReference())
- || (m_radiusY.get() && m_radiusY->hasVariableReference());
-}
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> normalizedCX = buildSerializablePositionOffset(m_centerX, CSSValueLeft);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> normalizedCY = buildSerializablePositionOffset(m_centerY, CSSValueTop);
-static String buildCircleString(const String& x, const String& y, const String& radius)
-{
- return "circle(" + x + ", " + y + ", " + radius + ')';
-}
+ String radius;
+ if (m_radius && m_radius->getValueID() != CSSValueClosestSide)
+ radius = m_radius->cssText();
-String CSSBasicShapeCircle::cssText() const
-{
- return buildCircleString(m_centerX->cssText(), m_centerY->cssText(), m_radius->cssText());
+ return buildCircleString(radius,
+ serializePositionOffset(*normalizedCX->getPairValue(), *normalizedCY->getPairValue()),
+ serializePositionOffset(*normalizedCY->getPairValue(), *normalizedCX->getPairValue()),
+ m_referenceBox ? m_referenceBox->cssText() : String());
}
bool CSSBasicShapeCircle::equals(const CSSBasicShape& shape) const
@@ -125,31 +132,77 @@ bool CSSBasicShapeCircle::equals(const CSSBasicShape& shape) const
const CSSBasicShapeCircle& other = static_cast<const CSSBasicShapeCircle&>(shape);
return compareCSSValuePtr(m_centerX, other.m_centerX)
&& compareCSSValuePtr(m_centerY, other.m_centerY)
- && compareCSSValuePtr(m_radius, other.m_radius);
+ && compareCSSValuePtr(m_radius, other.m_radius)
+ && compareCSSValuePtr(m_referenceBox, other.m_referenceBox);
}
-String CSSBasicShapeCircle::serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
+void CSSBasicShapeCircle::trace(Visitor* visitor)
{
- return buildCircleString(m_centerX->serializeResolvingVariables(variables),
- m_centerY->serializeResolvingVariables(variables),
- m_radius->serializeResolvingVariables(variables));
+ visitor->trace(m_centerX);
+ visitor->trace(m_centerY);
+ visitor->trace(m_radius);
+ CSSBasicShape::trace(visitor);
}
-bool CSSBasicShapeCircle::hasVariableReference() const
+static String buildEllipseString(const String& radiusX, const String& radiusY, const String& centerX, const String& centerY, const String& box)
{
- return m_centerX->hasVariableReference()
- || m_centerY->hasVariableReference()
- || m_radius->hasVariableReference();
-}
+ char at[] = "at";
+ char separator[] = " ";
+ StringBuilder result;
+ result.appendLiteral("ellipse(");
+ bool needsSeparator = false;
+ if (!radiusX.isNull()) {
+ result.append(radiusX);
+ needsSeparator = true;
+ }
+ if (!radiusY.isNull()) {
+ if (needsSeparator)
+ result.appendLiteral(separator);
+ result.append(radiusY);
+ needsSeparator = true;
+ }
-static String buildEllipseString(const String& x, const String& y, const String& radiusX, const String& radiusY)
-{
- return "ellipse(" + x + ", " + y + ", " + radiusX + ", " + radiusY + ')';
+ if (!centerX.isNull() || !centerY.isNull()) {
+ if (needsSeparator)
+ result.appendLiteral(separator);
+ result.appendLiteral(at);
+ result.appendLiteral(separator);
+ result.append(centerX);
+ result.appendLiteral(separator);
+ result.append(centerY);
+ }
+ result.append(")");
+ if (box.length()) {
+ result.appendLiteral(separator);
+ result.append(box);
+ }
+ return result.toString();
}
String CSSBasicShapeEllipse::cssText() const
{
- return buildEllipseString(m_centerX->cssText(), m_centerY->cssText(), m_radiusX->cssText(), m_radiusY->cssText());
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> normalizedCX = buildSerializablePositionOffset(m_centerX, CSSValueLeft);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> normalizedCY = buildSerializablePositionOffset(m_centerY, CSSValueTop);
+
+ String radiusX;
+ String radiusY;
+ if (m_radiusX) {
+ bool shouldSerializeRadiusXValue = m_radiusX->getValueID() != CSSValueClosestSide;
+ bool shouldSerializeRadiusYValue = false;
+
+ if (m_radiusY) {
+ shouldSerializeRadiusYValue = m_radiusY->getValueID() != CSSValueClosestSide;
+ if (shouldSerializeRadiusYValue)
+ radiusY = m_radiusY->cssText();
+ }
+ if (shouldSerializeRadiusXValue || (!shouldSerializeRadiusXValue && shouldSerializeRadiusYValue))
+ radiusX = m_radiusX->cssText();
+ }
+
+ return buildEllipseString(radiusX, radiusY,
+ serializePositionOffset(*normalizedCX->getPairValue(), *normalizedCY->getPairValue()),
+ serializePositionOffset(*normalizedCY->getPairValue(), *normalizedCX->getPairValue()),
+ m_referenceBox ? m_referenceBox->cssText() : String());
}
bool CSSBasicShapeEllipse::equals(const CSSBasicShape& shape) const
@@ -161,34 +214,28 @@ bool CSSBasicShapeEllipse::equals(const CSSBasicShape& shape) const
return compareCSSValuePtr(m_centerX, other.m_centerX)
&& compareCSSValuePtr(m_centerY, other.m_centerY)
&& compareCSSValuePtr(m_radiusX, other.m_radiusX)
- && compareCSSValuePtr(m_radiusY, other.m_radiusY);
-}
-
-String CSSBasicShapeEllipse::serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- return buildEllipseString(m_centerX->serializeResolvingVariables(variables),
- m_centerY->serializeResolvingVariables(variables),
- m_radiusX->serializeResolvingVariables(variables),
- m_radiusY->serializeResolvingVariables(variables));
+ && compareCSSValuePtr(m_radiusY, other.m_radiusY)
+ && compareCSSValuePtr(m_referenceBox, other.m_referenceBox);
}
-bool CSSBasicShapeEllipse::hasVariableReference() const
+void CSSBasicShapeEllipse::trace(Visitor* visitor)
{
- return m_centerX->hasVariableReference()
- || m_centerY->hasVariableReference()
- || m_radiusX->hasVariableReference()
- || m_radiusY->hasVariableReference();
+ visitor->trace(m_centerX);
+ visitor->trace(m_centerY);
+ visitor->trace(m_radiusX);
+ visitor->trace(m_radiusY);
+ CSSBasicShape::trace(visitor);
}
-static String buildPolygonString(const WindRule& windRule, const Vector<String>& points)
+static String buildPolygonString(const WindRule& windRule, const Vector<String>& points, const String& box)
{
ASSERT(!(points.size() % 2));
StringBuilder result;
- char evenOddOpening[] = "polygon(evenodd, ";
- char nonZeroOpening[] = "polygon(nonzero, ";
- char commaSeparator[] = ", ";
- COMPILE_ASSERT(sizeof(evenOddOpening) == sizeof(nonZeroOpening), polygon_string_openings_have_same_length);
+ const char evenOddOpening[] = "polygon(evenodd, ";
+ const char nonZeroOpening[] = "polygon(";
+ const char commaSeparator[] = ", ";
+ COMPILE_ASSERT(sizeof(evenOddOpening) > sizeof(nonZeroOpening), polygon_string_openings_have_same_length);
// Compute the required capacity in advance to reduce allocations.
size_t length = sizeof(evenOddOpening) - 1;
@@ -198,6 +245,8 @@ static String buildPolygonString(const WindRule& windRule, const Vector<String>&
// add length of two strings, plus one for the space separator.
length += points[i].length() + 1 + points[i + 1].length();
}
+ if (!box.isEmpty())
+ length += box.length() + 1;
result.reserveCapacity(length);
if (windRule == RULE_EVENODD)
@@ -215,6 +264,11 @@ static String buildPolygonString(const WindRule& windRule, const Vector<String>&
result.append(')');
+ if (!box.isEmpty()) {
+ result.append(' ');
+ result.append(box);
+ }
+
return result.toString();
}
@@ -226,7 +280,7 @@ String CSSBasicShapePolygon::cssText() const
for (size_t i = 0; i < m_values.size(); ++i)
points.append(m_values.at(i)->cssText());
- return buildPolygonString(m_windRule, points);
+ return buildPolygonString(m_windRule, points, m_referenceBox ? m_referenceBox->cssText() : String());
}
bool CSSBasicShapePolygon::equals(const CSSBasicShape& shape) const
@@ -235,98 +289,163 @@ bool CSSBasicShapePolygon::equals(const CSSBasicShape& shape) const
return false;
const CSSBasicShapePolygon& rhs = static_cast<const CSSBasicShapePolygon&>(shape);
- return compareCSSValueVector<CSSPrimitiveValue>(m_values, rhs.m_values);
-}
-String CSSBasicShapePolygon::serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- Vector<String> points;
- points.reserveInitialCapacity(m_values.size());
+ if (!compareCSSValuePtr(m_referenceBox, rhs.m_referenceBox))
+ return false;
- for (size_t i = 0; i < m_values.size(); ++i)
- points.append(m_values.at(i)->serializeResolvingVariables(variables));
+ return compareCSSValueVector(m_values, rhs.m_values);
+}
- return buildPolygonString(m_windRule, points);
+void CSSBasicShapePolygon::trace(Visitor* visitor)
+{
+ visitor->trace(m_values);
+ CSSBasicShape::trace(visitor);
}
-bool CSSBasicShapePolygon::hasVariableReference() const
+static bool buildInsetRadii(Vector<String> &radii, const String& topLeftRadius, const String& topRightRadius, const String& bottomRightRadius, const String& bottomLeftRadius)
{
- for (size_t i = 0; i < m_values.size(); ++i) {
- if (m_values.at(i)->hasVariableReference())
- return true;
- }
- return false;
+ bool showBottomLeft = topRightRadius != bottomLeftRadius;
+ bool showBottomRight = showBottomLeft || (bottomRightRadius != topLeftRadius);
+ bool showTopRight = showBottomRight || (topRightRadius != topLeftRadius);
+
+ radii.append(topLeftRadius);
+ if (showTopRight)
+ radii.append(topRightRadius);
+ if (showBottomRight)
+ radii.append(bottomRightRadius);
+ if (showBottomLeft)
+ radii.append(bottomLeftRadius);
+
+ return radii.size() == 1 && radii[0] == "0px";
}
-static String buildInsetRectangleString(const String& top, const String& right, const String& bottom, const String& left, const String& radiusX, const String& radiusY)
+static String buildInsetString(const String& top, const String& right, const String& bottom, const String& left,
+ const String& topLeftRadiusWidth, const String& topLeftRadiusHeight,
+ const String& topRightRadiusWidth, const String& topRightRadiusHeight,
+ const String& bottomRightRadiusWidth, const String& bottomRightRadiusHeight,
+ const String& bottomLeftRadiusWidth, const String& bottomLeftRadiusHeight)
{
- char opening[] = "inset-rectangle(";
- char separator[] = ", ";
+ char opening[] = "inset(";
+ char separator[] = " ";
+ char cornersSeparator[] = "round";
StringBuilder result;
- // Compute the required capacity in advance to reduce allocations.
- result.reserveCapacity((sizeof(opening) - 1) + (5 * (sizeof(separator) - 1)) + 1 + top.length() + right.length() + bottom.length() + left.length() + radiusX.length() + radiusY.length());
result.appendLiteral(opening);
result.append(top);
- result.appendLiteral(separator);
- result.append(right);
- result.appendLiteral(separator);
- result.append(bottom);
- result.appendLiteral(separator);
- result.append(left);
- if (!radiusX.isNull()) {
+ bool showLeftArg = !left.isNull() && left != right;
+ bool showBottomArg = !bottom.isNull() && (bottom != top || showLeftArg);
+ bool showRightArg = !right.isNull() && (right != top || showBottomArg);
+ if (showRightArg) {
result.appendLiteral(separator);
- result.append(radiusX);
- if (!radiusY.isNull()) {
+ result.append(right);
+ }
+ if (showBottomArg) {
+ result.appendLiteral(separator);
+ result.append(bottom);
+ }
+ if (showLeftArg) {
+ result.appendLiteral(separator);
+ result.append(left);
+ }
+
+ if (!topLeftRadiusWidth.isNull() && !topLeftRadiusHeight.isNull()) {
+ Vector<String> horizontalRadii;
+ bool areDefaultCornerRadii = buildInsetRadii(horizontalRadii, topLeftRadiusWidth, topRightRadiusWidth, bottomRightRadiusWidth, bottomLeftRadiusWidth);
+
+ Vector<String> verticalRadii;
+ areDefaultCornerRadii &= buildInsetRadii(verticalRadii, topLeftRadiusHeight, topRightRadiusHeight, bottomRightRadiusHeight, bottomLeftRadiusHeight);
+
+ if (!areDefaultCornerRadii) {
result.appendLiteral(separator);
- result.append(radiusY);
+ result.appendLiteral(cornersSeparator);
+
+ for (size_t i = 0; i < horizontalRadii.size(); ++i) {
+ result.appendLiteral(separator);
+ result.append(horizontalRadii[i]);
+ }
+ if (horizontalRadii != verticalRadii) {
+ result.appendLiteral(separator);
+ result.appendLiteral("/");
+
+ for (size_t i = 0; i < verticalRadii.size(); ++i) {
+ result.appendLiteral(separator);
+ result.append(verticalRadii[i]);
+ }
+ }
}
}
result.append(')');
+
return result.toString();
}
-String CSSBasicShapeInsetRectangle::cssText() const
+static inline void updateCornerRadiusWidthAndHeight(CSSPrimitiveValue* corner, String& width, String& height)
+{
+ if (!corner)
+ return;
+
+ Pair* radius = corner->getPairValue();
+ width = radius->first() ? radius->first()->cssText() : String("0");
+ if (radius->second())
+ height = radius->second()->cssText();
+}
+
+String CSSBasicShapeInset::cssText() const
{
- return buildInsetRectangleString(m_top->cssText(),
- m_right->cssText(),
- m_bottom->cssText(),
- m_left->cssText(),
- m_radiusX.get() ? m_radiusX->cssText() : String(),
- m_radiusY.get() ? m_radiusY->cssText() : String());
+ String topLeftRadiusWidth;
+ String topLeftRadiusHeight;
+ String topRightRadiusWidth;
+ String topRightRadiusHeight;
+ String bottomRightRadiusWidth;
+ String bottomRightRadiusHeight;
+ String bottomLeftRadiusWidth;
+ String bottomLeftRadiusHeight;
+
+ updateCornerRadiusWidthAndHeight(topLeftRadius(), topLeftRadiusWidth, topLeftRadiusHeight);
+ updateCornerRadiusWidthAndHeight(topRightRadius(), topRightRadiusWidth, topRightRadiusHeight);
+ updateCornerRadiusWidthAndHeight(bottomRightRadius(), bottomRightRadiusWidth, bottomRightRadiusHeight);
+ updateCornerRadiusWidthAndHeight(bottomLeftRadius(), bottomLeftRadiusWidth, bottomLeftRadiusHeight);
+
+ return buildInsetString(m_top ? m_top->cssText() : String(),
+ m_right ? m_right->cssText() : String(),
+ m_bottom ? m_bottom->cssText() : String(),
+ m_left ? m_left->cssText() : String(),
+ topLeftRadiusWidth,
+ topLeftRadiusHeight,
+ topRightRadiusWidth,
+ topRightRadiusHeight,
+ bottomRightRadiusWidth,
+ bottomRightRadiusHeight,
+ bottomLeftRadiusWidth,
+ bottomLeftRadiusHeight);
}
-bool CSSBasicShapeInsetRectangle::equals(const CSSBasicShape& shape) const
+bool CSSBasicShapeInset::equals(const CSSBasicShape& shape) const
{
- if (shape.type() != CSSBasicShapeInsetRectangleType)
+ if (shape.type() != CSSBasicShapeInsetType)
return false;
- const CSSBasicShapeInsetRectangle& other = static_cast<const CSSBasicShapeInsetRectangle&>(shape);
+ const CSSBasicShapeInset& other = static_cast<const CSSBasicShapeInset&>(shape);
return compareCSSValuePtr(m_top, other.m_top)
&& compareCSSValuePtr(m_right, other.m_right)
&& compareCSSValuePtr(m_bottom, other.m_bottom)
&& compareCSSValuePtr(m_left, other.m_left)
- && compareCSSValuePtr(m_radiusX, other.m_radiusX)
- && compareCSSValuePtr(m_radiusY, other.m_radiusY);
-}
-
-String CSSBasicShapeInsetRectangle::serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- return buildInsetRectangleString(m_top->serializeResolvingVariables(variables),
- m_right->serializeResolvingVariables(variables),
- m_bottom->serializeResolvingVariables(variables),
- m_left->serializeResolvingVariables(variables),
- m_radiusX.get() ? m_radiusX->serializeResolvingVariables(variables) : String(),
- m_radiusY.get() ? m_radiusY->serializeResolvingVariables(variables) : String());
+ && compareCSSValuePtr(m_topLeftRadius, other.m_topLeftRadius)
+ && compareCSSValuePtr(m_topRightRadius, other.m_topRightRadius)
+ && compareCSSValuePtr(m_bottomRightRadius, other.m_bottomRightRadius)
+ && compareCSSValuePtr(m_bottomLeftRadius, other.m_bottomLeftRadius);
}
-bool CSSBasicShapeInsetRectangle::hasVariableReference() const
+void CSSBasicShapeInset::trace(Visitor* visitor)
{
- return m_top->hasVariableReference()
- || m_right->hasVariableReference()
- || m_bottom->hasVariableReference()
- || m_left->hasVariableReference()
- || (m_radiusX.get() && m_radiusX->hasVariableReference())
- || (m_radiusY.get() && m_radiusY->hasVariableReference());
+ visitor->trace(m_top);
+ visitor->trace(m_right);
+ visitor->trace(m_bottom);
+ visitor->trace(m_left);
+ visitor->trace(m_topLeftRadius);
+ visitor->trace(m_topRightRadius);
+ visitor->trace(m_bottomRightRadius);
+ visitor->trace(m_bottomLeftRadius);
+ CSSBasicShape::trace(visitor);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.h b/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.h
index ca8c661fc47..4c510e0ca5c 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSBasicShapes.h
@@ -38,181 +38,107 @@
namespace WebCore {
-class CSSBasicShape : public RefCounted<CSSBasicShape> {
+class CSSBasicShape : public RefCountedWillBeGarbageCollected<CSSBasicShape> {
+ DECLARE_EMPTY_VIRTUAL_DESTRUCTOR_WILL_BE_REMOVED(CSSBasicShape);
public:
enum Type {
- CSSBasicShapeRectangleType = 1,
- CSSBasicShapeCircleType = 2,
- CSSBasicShapeEllipseType = 3,
- CSSBasicShapePolygonType = 4,
- CSSBasicShapeInsetRectangleType = 5
+ CSSBasicShapeEllipseType,
+ CSSBasicShapePolygonType,
+ CSSBasicShapeCircleType,
+ CSSBasicShapeInsetType
};
virtual Type type() const = 0;
virtual String cssText() const = 0;
virtual bool equals(const CSSBasicShape&) const = 0;
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const = 0;
- virtual bool hasVariableReference() const = 0;
+ CSSPrimitiveValue* referenceBox() const { return m_referenceBox.get(); }
+ void setReferenceBox(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> referenceBox) { m_referenceBox = referenceBox; }
-public:
- virtual ~CSSBasicShape() { }
+ virtual void trace(Visitor* visitor) { visitor->trace(m_referenceBox); }
protected:
CSSBasicShape() { }
+ RefPtrWillBeMember<CSSPrimitiveValue> m_referenceBox;
};
-class CSSBasicShapeRectangle : public CSSBasicShape {
+class CSSBasicShapeCircle FINAL : public CSSBasicShape {
public:
- static PassRefPtr<CSSBasicShapeRectangle> create() { return adoptRef(new CSSBasicShapeRectangle); }
-
- CSSPrimitiveValue* x() const { return m_x.get(); }
- CSSPrimitiveValue* y() const { return m_y.get(); }
- CSSPrimitiveValue* width() const { return m_width.get(); }
- CSSPrimitiveValue* height() const { return m_height.get(); }
- CSSPrimitiveValue* radiusX() const { return m_radiusX.get(); }
- CSSPrimitiveValue* radiusY() const { return m_radiusY.get(); }
-
- void setX(PassRefPtr<CSSPrimitiveValue> x) { m_x = x; }
- void setY(PassRefPtr<CSSPrimitiveValue> y) { m_y = y; }
- void setWidth(PassRefPtr<CSSPrimitiveValue> width) { m_width = width; }
- void setHeight(PassRefPtr<CSSPrimitiveValue> height) { m_height = height; }
- void setRadiusX(PassRefPtr<CSSPrimitiveValue> radiusX) { m_radiusX = radiusX; }
- void setRadiusY(PassRefPtr<CSSPrimitiveValue> radiusY) { m_radiusY = radiusY; }
-
- virtual Type type() const { return CSSBasicShapeRectangleType; }
- virtual String cssText() const;
- virtual bool equals(const CSSBasicShape&) const;
-
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- virtual bool hasVariableReference() const;
-
-private:
- CSSBasicShapeRectangle() { }
-
- RefPtr<CSSPrimitiveValue> m_y;
- RefPtr<CSSPrimitiveValue> m_x;
- RefPtr<CSSPrimitiveValue> m_width;
- RefPtr<CSSPrimitiveValue> m_height;
- RefPtr<CSSPrimitiveValue> m_radiusX;
- RefPtr<CSSPrimitiveValue> m_radiusY;
-};
-
-class CSSBasicShapeInsetRectangle : public CSSBasicShape {
-public:
- static PassRefPtr<CSSBasicShapeInsetRectangle> create() { return adoptRef(new CSSBasicShapeInsetRectangle); }
-
- CSSPrimitiveValue* top() const { return m_top.get(); }
- CSSPrimitiveValue* right() const { return m_right.get(); }
- CSSPrimitiveValue* bottom() const { return m_bottom.get(); }
- CSSPrimitiveValue* left() const { return m_left.get(); }
- CSSPrimitiveValue* radiusX() const { return m_radiusX.get(); }
- CSSPrimitiveValue* radiusY() const { return m_radiusY.get(); }
+ static PassRefPtrWillBeRawPtr<CSSBasicShapeCircle> create() { return adoptRefWillBeNoop(new CSSBasicShapeCircle); }
- void setTop(PassRefPtr<CSSPrimitiveValue> top) { m_top = top; }
- void setRight(PassRefPtr<CSSPrimitiveValue> right) { m_right = right; }
- void setBottom(PassRefPtr<CSSPrimitiveValue> bottom) { m_bottom = bottom; }
- void setLeft(PassRefPtr<CSSPrimitiveValue> left) { m_left = left; }
- void setRadiusX(PassRefPtr<CSSPrimitiveValue> radiusX) { m_radiusX = radiusX; }
- void setRadiusY(PassRefPtr<CSSPrimitiveValue> radiusY) { m_radiusY = radiusY; }
-
- virtual Type type() const { return CSSBasicShapeInsetRectangleType; }
- virtual String cssText() const;
- virtual bool equals(const CSSBasicShape&) const;
-
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- virtual bool hasVariableReference() const;
-
-private:
- CSSBasicShapeInsetRectangle() { }
-
- RefPtr<CSSPrimitiveValue> m_right;
- RefPtr<CSSPrimitiveValue> m_top;
- RefPtr<CSSPrimitiveValue> m_bottom;
- RefPtr<CSSPrimitiveValue> m_left;
- RefPtr<CSSPrimitiveValue> m_radiusX;
- RefPtr<CSSPrimitiveValue> m_radiusY;
-};
-
-class CSSBasicShapeCircle : public CSSBasicShape {
-public:
- static PassRefPtr<CSSBasicShapeCircle> create() { return adoptRef(new CSSBasicShapeCircle); }
+ virtual Type type() const OVERRIDE { return CSSBasicShapeCircleType; }
+ virtual String cssText() const OVERRIDE;
+ virtual bool equals(const CSSBasicShape&) const OVERRIDE;
CSSPrimitiveValue* centerX() const { return m_centerX.get(); }
CSSPrimitiveValue* centerY() const { return m_centerY.get(); }
CSSPrimitiveValue* radius() const { return m_radius.get(); }
- void setCenterX(PassRefPtr<CSSPrimitiveValue> centerX) { m_centerX = centerX; }
- void setCenterY(PassRefPtr<CSSPrimitiveValue> centerY) { m_centerY = centerY; }
- void setRadius(PassRefPtr<CSSPrimitiveValue> radius) { m_radius = radius; }
-
- virtual Type type() const { return CSSBasicShapeCircleType; }
- virtual String cssText() const;
- virtual bool equals(const CSSBasicShape&) const;
+ void setCenterX(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> centerX) { m_centerX = centerX; }
+ void setCenterY(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> centerY) { m_centerY = centerY; }
+ void setRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radius) { m_radius = radius; }
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- virtual bool hasVariableReference() const;
+ virtual void trace(Visitor*);
private:
CSSBasicShapeCircle() { }
- RefPtr<CSSPrimitiveValue> m_centerY;
- RefPtr<CSSPrimitiveValue> m_centerX;
- RefPtr<CSSPrimitiveValue> m_radius;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_centerX;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_centerY;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_radius;
};
-class CSSBasicShapeEllipse : public CSSBasicShape {
+class CSSBasicShapeEllipse FINAL : public CSSBasicShape {
public:
- static PassRefPtr<CSSBasicShapeEllipse> create() { return adoptRef(new CSSBasicShapeEllipse); }
+ static PassRefPtrWillBeRawPtr<CSSBasicShapeEllipse> create() { return adoptRefWillBeNoop(new CSSBasicShapeEllipse); }
+
+ virtual Type type() const OVERRIDE { return CSSBasicShapeEllipseType; }
+ virtual String cssText() const OVERRIDE;
+ virtual bool equals(const CSSBasicShape&) const OVERRIDE;
CSSPrimitiveValue* centerX() const { return m_centerX.get(); }
CSSPrimitiveValue* centerY() const { return m_centerY.get(); }
CSSPrimitiveValue* radiusX() const { return m_radiusX.get(); }
CSSPrimitiveValue* radiusY() const { return m_radiusY.get(); }
- void setCenterX(PassRefPtr<CSSPrimitiveValue> centerX) { m_centerX = centerX; }
- void setCenterY(PassRefPtr<CSSPrimitiveValue> centerY) { m_centerY = centerY; }
- void setRadiusX(PassRefPtr<CSSPrimitiveValue> radiusX) { m_radiusX = radiusX; }
- void setRadiusY(PassRefPtr<CSSPrimitiveValue> radiusY) { m_radiusY = radiusY; }
-
- virtual Type type() const { return CSSBasicShapeEllipseType; }
- virtual String cssText() const;
- virtual bool equals(const CSSBasicShape&) const;
+ void setCenterX(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> centerX) { m_centerX = centerX; }
+ void setCenterY(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> centerY) { m_centerY = centerY; }
+ void setRadiusX(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radiusX) { m_radiusX = radiusX; }
+ void setRadiusY(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radiusY) { m_radiusY = radiusY; }
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- virtual bool hasVariableReference() const;
+ virtual void trace(Visitor*);
private:
CSSBasicShapeEllipse() { }
- RefPtr<CSSPrimitiveValue> m_centerX;
- RefPtr<CSSPrimitiveValue> m_centerY;
- RefPtr<CSSPrimitiveValue> m_radiusX;
- RefPtr<CSSPrimitiveValue> m_radiusY;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_centerX;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_centerY;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_radiusX;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_radiusY;
};
-class CSSBasicShapePolygon : public CSSBasicShape {
+class CSSBasicShapePolygon FINAL : public CSSBasicShape {
public:
- static PassRefPtr<CSSBasicShapePolygon> create() { return adoptRef(new CSSBasicShapePolygon); }
+ static PassRefPtrWillBeRawPtr<CSSBasicShapePolygon> create() { return adoptRefWillBeNoop(new CSSBasicShapePolygon); }
- void appendPoint(PassRefPtr<CSSPrimitiveValue> x, PassRefPtr<CSSPrimitiveValue> y)
+ void appendPoint(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> x, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> y)
{
m_values.append(x);
m_values.append(y);
}
- PassRefPtr<CSSPrimitiveValue> getXAt(unsigned i) const { return m_values.at(i * 2); }
- PassRefPtr<CSSPrimitiveValue> getYAt(unsigned i) const { return m_values.at(i * 2 + 1); }
- const Vector<RefPtr<CSSPrimitiveValue> >& values() const { return m_values; }
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> getXAt(unsigned i) const { return m_values.at(i * 2); }
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> getYAt(unsigned i) const { return m_values.at(i * 2 + 1); }
+ const WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue> >& values() const { return m_values; }
void setWindRule(WindRule w) { m_windRule = w; }
WindRule windRule() const { return m_windRule; }
- virtual Type type() const { return CSSBasicShapePolygonType; }
- virtual String cssText() const;
- virtual bool equals(const CSSBasicShape&) const;
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- virtual bool hasVariableReference() const;
+ virtual Type type() const OVERRIDE { return CSSBasicShapePolygonType; }
+ virtual String cssText() const OVERRIDE;
+ virtual bool equals(const CSSBasicShape&) const OVERRIDE;
+
+ virtual void trace(Visitor*);
private:
CSSBasicShapePolygon()
@@ -220,10 +146,78 @@ private:
{
}
- Vector<RefPtr<CSSPrimitiveValue> > m_values;
+ WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue> > m_values;
WindRule m_windRule;
};
+class CSSBasicShapeInset : public CSSBasicShape {
+public:
+ static PassRefPtrWillBeRawPtr<CSSBasicShapeInset> create() { return adoptRefWillBeNoop(new CSSBasicShapeInset); }
+
+ CSSPrimitiveValue* top() const { return m_top.get(); }
+ CSSPrimitiveValue* right() const { return m_right.get(); }
+ CSSPrimitiveValue* bottom() const { return m_bottom.get(); }
+ CSSPrimitiveValue* left() const { return m_left.get(); }
+
+ CSSPrimitiveValue* topLeftRadius() const { return m_topLeftRadius.get(); }
+ CSSPrimitiveValue* topRightRadius() const { return m_topRightRadius.get(); }
+ CSSPrimitiveValue* bottomRightRadius() const { return m_bottomRightRadius.get(); }
+ CSSPrimitiveValue* bottomLeftRadius() const { return m_bottomLeftRadius.get(); }
+
+ void setTop(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> top) { m_top = top; }
+ void setRight(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> right) { m_right = right; }
+ void setBottom(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> bottom) { m_bottom = bottom; }
+ void setLeft(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> left) { m_left = left; }
+
+ void updateShapeSize4Values(CSSPrimitiveValue* top, CSSPrimitiveValue* right, CSSPrimitiveValue* bottom, CSSPrimitiveValue* left)
+ {
+ setTop(top);
+ setRight(right);
+ setBottom(bottom);
+ setLeft(left);
+ }
+
+ void updateShapeSize1Value(CSSPrimitiveValue* value1)
+ {
+ updateShapeSize4Values(value1, value1, value1, value1);
+ }
+
+ void updateShapeSize2Values(CSSPrimitiveValue* value1, CSSPrimitiveValue* value2)
+ {
+ updateShapeSize4Values(value1, value2, value1, value2);
+ }
+
+ void updateShapeSize3Values(CSSPrimitiveValue* value1, CSSPrimitiveValue* value2, CSSPrimitiveValue* value3)
+ {
+ updateShapeSize4Values(value1, value2, value3, value2);
+ }
+
+
+ void setTopLeftRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radius) { m_topLeftRadius = radius; }
+ void setTopRightRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radius) { m_topRightRadius = radius; }
+ void setBottomRightRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radius) { m_bottomRightRadius = radius; }
+ void setBottomLeftRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> radius) { m_bottomLeftRadius = radius; }
+
+ virtual Type type() const OVERRIDE { return CSSBasicShapeInsetType; }
+ virtual String cssText() const OVERRIDE;
+ virtual bool equals(const CSSBasicShape&) const OVERRIDE;
+
+ virtual void trace(Visitor*);
+
+private:
+ CSSBasicShapeInset() { }
+
+ RefPtrWillBeMember<CSSPrimitiveValue> m_top;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_right;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_bottom;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_left;
+
+ RefPtrWillBeMember<CSSPrimitiveValue> m_topLeftRadius;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_topRightRadius;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_bottomRightRadius;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_bottomLeftRadius;
+};
+
} // namespace WebCore
#endif // CSSBasicShapes_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.cpp b/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.cpp
index d62711ddef7..fd05d0f5ff8 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.cpp
@@ -22,15 +22,15 @@
namespace WebCore {
-PassRefPtr<CSSValueList> createBorderImageValue(PassRefPtr<CSSValue> image, PassRefPtr<CSSValue> imageSlice, PassRefPtr<CSSValue> borderSlice,
- PassRefPtr<CSSValue> outset, PassRefPtr<CSSValue> repeat)
+PassRefPtrWillBeRawPtr<CSSValueList> createBorderImageValue(PassRefPtrWillBeRawPtr<CSSValue> image, PassRefPtrWillBeRawPtr<CSSValue> imageSlice,
+ PassRefPtrWillBeRawPtr<CSSValue> borderSlice, PassRefPtrWillBeRawPtr<CSSValue> outset, PassRefPtrWillBeRawPtr<CSSValue> repeat)
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (image)
list->append(image);
if (borderSlice || outset) {
- RefPtr<CSSValueList> listSlash = CSSValueList::createSlashSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> listSlash = CSSValueList::createSlashSeparated();
if (imageSlice)
listSlash->append(imageSlice);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.h b/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.h
index bdf13fefd19..b9066fa29bf 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSBorderImage.h
@@ -26,8 +26,8 @@
namespace WebCore {
-PassRefPtr<CSSValueList> createBorderImageValue(PassRefPtr<CSSValue> image, PassRefPtr<CSSValue> imageSlice, PassRefPtr<CSSValue> borderSlice,
- PassRefPtr<CSSValue> outset, PassRefPtr<CSSValue> repeat);
+PassRefPtrWillBeRawPtr<CSSValueList> createBorderImageValue(PassRefPtrWillBeRawPtr<CSSValue> image, PassRefPtrWillBeRawPtr<CSSValue> imageSlice, PassRefPtrWillBeRawPtr<CSSValue> borderSlice,
+ PassRefPtrWillBeRawPtr<CSSValue> outset, PassRefPtrWillBeRawPtr<CSSValue> repeat);
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.cpp
index 7ffac3afb9b..34400a81137 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.cpp
@@ -30,7 +30,7 @@
namespace WebCore {
-CSSBorderImageSliceValue::CSSBorderImageSliceValue(PassRefPtr<CSSPrimitiveValue> slices, bool fill)
+CSSBorderImageSliceValue::CSSBorderImageSliceValue(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> slices, bool fill)
: CSSValue(BorderImageSliceClass)
, m_slices(slices)
, m_fill(fill)
@@ -53,4 +53,10 @@ bool CSSBorderImageSliceValue::equals(const CSSBorderImageSliceValue& other) con
return m_fill == other.m_fill && compareCSSValuePtr(m_slices, other.m_slices);
}
+void CSSBorderImageSliceValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_slices);
+ CSSValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.h b/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.h
index 7d297ea9be0..c2b4716d790 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSBorderImageSliceValue.h
@@ -36,9 +36,9 @@ class Rect;
class CSSBorderImageSliceValue : public CSSValue {
public:
- static PassRefPtr<CSSBorderImageSliceValue> create(PassRefPtr<CSSPrimitiveValue> slices, bool fill)
+ static PassRefPtrWillBeRawPtr<CSSBorderImageSliceValue> create(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> slices, bool fill)
{
- return adoptRef(new CSSBorderImageSliceValue(slices, fill));
+ return adoptRefWillBeNoop(new CSSBorderImageSliceValue(slices, fill));
}
String customCSSText() const;
@@ -47,13 +47,15 @@ public:
bool equals(const CSSBorderImageSliceValue&) const;
+ void traceAfterDispatch(Visitor*);
+
// These four values are used to make "cuts" in the border image. They can be numbers
// or percentages.
- RefPtr<CSSPrimitiveValue> m_slices;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_slices;
bool m_fill;
private:
- CSSBorderImageSliceValue(PassRefPtr<CSSPrimitiveValue> slices, bool fill);
+ CSSBorderImageSliceValue(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> slices, bool fill);
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSBorderImageSliceValue, isBorderImageSliceValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.cpp
index e27cba3a66d..79de5eb33bf 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.cpp
@@ -47,7 +47,7 @@ enum ParseState {
namespace WebCore {
-static CalculationCategory unitCategory(CSSPrimitiveValue::UnitTypes type)
+static CalculationCategory unitCategory(CSSPrimitiveValue::UnitType type)
{
switch (type) {
case CSSPrimitiveValue::CSS_NUMBER:
@@ -65,15 +65,19 @@ static CalculationCategory unitCategory(CSSPrimitiveValue::UnitTypes type)
case CSSPrimitiveValue::CSS_PC:
case CSSPrimitiveValue::CSS_REMS:
case CSSPrimitiveValue::CSS_CHS:
+ case CSSPrimitiveValue::CSS_VW:
+ case CSSPrimitiveValue::CSS_VH:
+ case CSSPrimitiveValue::CSS_VMIN:
+ case CSSPrimitiveValue::CSS_VMAX:
return CalcLength;
- case CSSPrimitiveValue::CSS_VARIABLE_NAME:
- return CalcVariable;
+ // FIXME: Support angle, time and frequency units.
+ // http://www.w3.org/TR/css3-values/#calc-notation
default:
return CalcOther;
}
}
-static bool hasDoubleValue(CSSPrimitiveValue::UnitTypes type)
+static bool hasDoubleValue(CSSPrimitiveValue::UnitType type)
{
switch (type) {
case CSSPrimitiveValue::CSS_NUMBER:
@@ -126,7 +130,6 @@ static bool hasDoubleValue(CSSPrimitiveValue::UnitTypes type)
case CSSPrimitiveValue::CSS_CALC:
case CSSPrimitiveValue::CSS_CALC_PERCENTAGE_WITH_NUMBER:
case CSSPrimitiveValue::CSS_CALC_PERCENTAGE_WITH_LENGTH:
- case CSSPrimitiveValue::CSS_VARIABLE_NAME:
case CSSPrimitiveValue::CSS_PROPERTY_ID:
case CSSPrimitiveValue::CSS_VALUE_ID:
return false;
@@ -158,16 +161,6 @@ bool CSSCalcValue::equals(const CSSCalcValue& other) const
return compareCSSValuePtr(m_expression, other.m_expression);
}
-String CSSCalcValue::customSerializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- return buildCSSText(m_expression->serializeResolvingVariables(variables));
-}
-
-bool CSSCalcValue::hasVariableReference() const
-{
- return m_expression->hasVariableReference();
-}
-
double CSSCalcValue::clampToPermittedRange(double value) const
{
return m_nonNegative && value < 0 ? 0 : value;
@@ -183,71 +176,50 @@ double CSSCalcValue::computeLengthPx(const CSSToLengthConversionData& conversion
return clampToPermittedRange(m_expression->computeLengthPx(conversionData));
}
-CSSCalcExpressionNode::~CSSCalcExpressionNode()
-{
-}
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(CSSCalcExpressionNode)
-class CSSCalcPrimitiveValue : public CSSCalcExpressionNode {
- WTF_MAKE_FAST_ALLOCATED;
+class CSSCalcPrimitiveValue FINAL : public CSSCalcExpressionNode {
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- static PassRefPtr<CSSCalcPrimitiveValue> create(PassRefPtr<CSSPrimitiveValue> value, bool isInteger)
+ static PassRefPtrWillBeRawPtr<CSSCalcPrimitiveValue> create(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> value, bool isInteger)
{
- return adoptRef(new CSSCalcPrimitiveValue(value, isInteger));
+ return adoptRefWillBeNoop(new CSSCalcPrimitiveValue(value, isInteger));
}
- static PassRefPtr<CSSCalcPrimitiveValue> create(double value, CSSPrimitiveValue::UnitTypes type, bool isInteger)
+ static PassRefPtrWillBeRawPtr<CSSCalcPrimitiveValue> create(double value, CSSPrimitiveValue::UnitType type, bool isInteger)
{
if (std::isnan(value) || std::isinf(value))
- return 0;
- return adoptRef(new CSSCalcPrimitiveValue(CSSPrimitiveValue::create(value, type).get(), isInteger));
+ return nullptr;
+ return adoptRefWillBeNoop(new CSSCalcPrimitiveValue(CSSPrimitiveValue::create(value, type).get(), isInteger));
}
- virtual bool isZero() const
+ virtual bool isZero() const OVERRIDE
{
return !m_value->getDoubleValue();
}
- virtual String customCSSText() const
+ virtual String customCSSText() const OVERRIDE
{
return m_value->cssText();
}
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
- {
- return m_value->customSerializeResolvingVariables(variables);
- }
-
- virtual bool hasVariableReference() const
- {
- return m_value->isVariableName();
- }
-
- virtual PassOwnPtr<CalcExpressionNode> toCalcValue(const CSSToLengthConversionData& conversionData) const
+ virtual void accumulatePixelsAndPercent(const CSSToLengthConversionData& conversionData, PixelsAndPercent& value, float multiplier) const OVERRIDE
{
switch (m_category) {
- case CalcNumber:
- return adoptPtr(new CalcExpressionNumber(m_value->getFloatValue()));
case CalcLength:
- return adoptPtr(new CalcExpressionLength(Length(m_value->computeLength<float>(conversionData), WebCore::Fixed)));
+ value.pixels += m_value->computeLength<float>(conversionData) * multiplier;
+ break;
case CalcPercent:
- case CalcPercentLength: {
- CSSPrimitiveValue* primitiveValue = m_value.get();
- return adoptPtr(new CalcExpressionLength(primitiveValue
- ? primitiveValue->convertToLength<FixedConversion | PercentConversion>(conversionData)
- : Length(Undefined)));
- }
- // Only types that could be part of a Length expression can be converted
- // to a CalcExpressionNode. CalcPercentNumber makes no sense as a Length.
- case CalcPercentNumber:
- case CalcVariable:
- case CalcOther:
+ ASSERT(m_value->isPercentage());
+ value.percent += m_value->getDoubleValue() * multiplier;
+ break;
+ default:
ASSERT_NOT_REACHED();
}
- return nullptr;
}
- virtual double doubleValue() const
+ virtual double doubleValue() const OVERRIDE
{
if (hasDoubleValue(primitiveType()))
return m_value->getDoubleValue();
@@ -255,7 +227,7 @@ public:
return 0;
}
- virtual double computeLengthPx(const CSSToLengthConversionData& conversionData) const
+ virtual double computeLengthPx(const CSSToLengthConversionData& conversionData) const OVERRIDE
{
switch (m_category) {
case CalcLength:
@@ -265,7 +237,6 @@ public:
return m_value->getDoubleValue();
case CalcPercentLength:
case CalcPercentNumber:
- case CalcVariable:
case CalcOther:
ASSERT_NOT_REACHED();
break;
@@ -274,7 +245,13 @@ public:
return 0;
}
- virtual bool equals(const CSSCalcExpressionNode& other) const
+ virtual void accumulateLengthArray(CSSLengthArray& lengthArray, double multiplier) const
+ {
+ ASSERT(category() != CalcNumber);
+ m_value->accumulateLengthArray(lengthArray, multiplier);
+ }
+
+ virtual bool equals(const CSSCalcExpressionNode& other) const OVERRIDE
{
if (type() != other.type())
return false;
@@ -282,20 +259,27 @@ public:
return compareCSSValuePtr(m_value, static_cast<const CSSCalcPrimitiveValue&>(other).m_value);
}
- virtual Type type() const { return CssCalcPrimitiveValue; }
- virtual CSSPrimitiveValue::UnitTypes primitiveType() const
+ virtual Type type() const OVERRIDE { return CssCalcPrimitiveValue; }
+ virtual CSSPrimitiveValue::UnitType primitiveType() const OVERRIDE
{
- return CSSPrimitiveValue::UnitTypes(m_value->primitiveType());
+ return m_value->primitiveType();
+ }
+
+
+ virtual void trace(Visitor* visitor)
+ {
+ visitor->trace(m_value);
+ CSSCalcExpressionNode::trace(visitor);
}
private:
- explicit CSSCalcPrimitiveValue(PassRefPtr<CSSPrimitiveValue> value, bool isInteger)
- : CSSCalcExpressionNode(unitCategory((CSSPrimitiveValue::UnitTypes)value->primitiveType()), isInteger)
+ CSSCalcPrimitiveValue(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> value, bool isInteger)
+ : CSSCalcExpressionNode(unitCategory(value->primitiveType()), isInteger)
, m_value(value)
{
}
- RefPtr<CSSPrimitiveValue> m_value;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_value;
};
static const CalculationCategory addSubtractResult[CalcOther][CalcOther] = {
@@ -315,9 +299,6 @@ static CalculationCategory determineCategory(const CSSCalcExpressionNode& leftSi
if (leftCategory == CalcOther || rightCategory == CalcOther)
return CalcOther;
- if (leftCategory == CalcVariable || rightCategory == CalcVariable)
- return CalcVariable;
-
switch (op) {
case CalcAdd:
case CalcSubtract:
@@ -344,21 +325,20 @@ static bool isIntegerResult(const CSSCalcExpressionNode* leftSide, const CSSCalc
return op != CalcDivide && leftSide->isInteger() && rightSide->isInteger();
}
-class CSSCalcBinaryOperation : public CSSCalcExpressionNode {
-
+class CSSCalcBinaryOperation FINAL : public CSSCalcExpressionNode {
public:
- static PassRefPtr<CSSCalcExpressionNode> create(PassRefPtr<CSSCalcExpressionNode> leftSide, PassRefPtr<CSSCalcExpressionNode> rightSide, CalcOperator op)
+ static PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> create(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> leftSide, PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> rightSide, CalcOperator op)
{
ASSERT(leftSide->category() != CalcOther && rightSide->category() != CalcOther);
CalculationCategory newCategory = determineCategory(*leftSide, *rightSide, op);
if (newCategory == CalcOther)
- return 0;
+ return nullptr;
- return adoptRef(new CSSCalcBinaryOperation(leftSide, rightSide, op, newCategory));
+ return adoptRefWillBeNoop(new CSSCalcBinaryOperation(leftSide, rightSide, op, newCategory));
}
- static PassRefPtr<CSSCalcExpressionNode> createSimplified(PassRefPtr<CSSCalcExpressionNode> leftSide, PassRefPtr<CSSCalcExpressionNode> rightSide, CalcOperator op)
+ static PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> createSimplified(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> leftSide, PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> rightSide, CalcOperator op)
{
CalculationCategory leftCategory = leftSide->category();
CalculationCategory rightCategory = rightSide->category();
@@ -368,21 +348,21 @@ public:
// Simplify numbers.
if (leftCategory == CalcNumber && rightCategory == CalcNumber) {
- CSSPrimitiveValue::UnitTypes evaluationType = isInteger ? CSSPrimitiveValue::CSS_PARSER_INTEGER : CSSPrimitiveValue::CSS_NUMBER;
+ CSSPrimitiveValue::UnitType evaluationType = isInteger ? CSSPrimitiveValue::CSS_PARSER_INTEGER : CSSPrimitiveValue::CSS_NUMBER;
return CSSCalcPrimitiveValue::create(evaluateOperator(leftSide->doubleValue(), rightSide->doubleValue(), op), evaluationType, isInteger);
}
// Simplify addition and subtraction between same types.
if (op == CalcAdd || op == CalcSubtract) {
if (leftCategory == rightSide->category()) {
- CSSPrimitiveValue::UnitTypes leftType = leftSide->primitiveType();
+ CSSPrimitiveValue::UnitType leftType = leftSide->primitiveType();
if (hasDoubleValue(leftType)) {
- CSSPrimitiveValue::UnitTypes rightType = rightSide->primitiveType();
+ CSSPrimitiveValue::UnitType rightType = rightSide->primitiveType();
if (leftType == rightType)
return CSSCalcPrimitiveValue::create(evaluateOperator(leftSide->doubleValue(), rightSide->doubleValue(), op), leftType, isInteger);
CSSPrimitiveValue::UnitCategory leftUnitCategory = CSSPrimitiveValue::unitCategory(leftType);
if (leftUnitCategory != CSSPrimitiveValue::UOther && leftUnitCategory == CSSPrimitiveValue::unitCategory(rightType)) {
- CSSPrimitiveValue::UnitTypes canonicalType = CSSPrimitiveValue::canonicalUnitTypeForCategory(leftUnitCategory);
+ CSSPrimitiveValue::UnitType canonicalType = CSSPrimitiveValue::canonicalUnitTypeForCategory(leftUnitCategory);
if (canonicalType != CSSPrimitiveValue::CSS_UNKNOWN) {
double leftValue = leftSide->doubleValue() * CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(leftType);
double rightValue = rightSide->doubleValue() * CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(rightType);
@@ -398,16 +378,16 @@ public:
if (!numberSide)
return create(leftSide, rightSide, op);
if (numberSide == leftSide && op == CalcDivide)
- return 0;
+ return nullptr;
CSSCalcExpressionNode* otherSide = leftSide == numberSide ? rightSide.get() : leftSide.get();
double number = numberSide->doubleValue();
if (std::isnan(number) || std::isinf(number))
- return 0;
+ return nullptr;
if (op == CalcDivide && !number)
- return 0;
+ return nullptr;
- CSSPrimitiveValue::UnitTypes otherType = otherSide->primitiveType();
+ CSSPrimitiveValue::UnitType otherType = otherSide->primitiveType();
if (hasDoubleValue(otherType))
return CSSCalcPrimitiveValue::create(evaluateOperator(otherSide->doubleValue(), number, op), otherType, isInteger);
}
@@ -415,34 +395,77 @@ public:
return create(leftSide, rightSide, op);
}
- virtual bool isZero() const
+ virtual bool isZero() const OVERRIDE
{
return !doubleValue();
}
- virtual PassOwnPtr<CalcExpressionNode> toCalcValue(const CSSToLengthConversionData& conversionData) const
+ virtual void accumulatePixelsAndPercent(const CSSToLengthConversionData& conversionData, PixelsAndPercent& value, float multiplier) const OVERRIDE
{
- OwnPtr<CalcExpressionNode> left(m_leftSide->toCalcValue(conversionData));
- if (!left)
- return nullptr;
- OwnPtr<CalcExpressionNode> right(m_rightSide->toCalcValue(conversionData));
- if (!right)
- return nullptr;
- return adoptPtr(new CalcExpressionBinaryOperation(left.release(), right.release(), m_operator));
+ switch (m_operator) {
+ case CalcAdd:
+ m_leftSide->accumulatePixelsAndPercent(conversionData, value, multiplier);
+ m_rightSide->accumulatePixelsAndPercent(conversionData, value, multiplier);
+ break;
+ case CalcSubtract:
+ m_leftSide->accumulatePixelsAndPercent(conversionData, value, multiplier);
+ m_rightSide->accumulatePixelsAndPercent(conversionData, value, -multiplier);
+ break;
+ case CalcMultiply:
+ ASSERT((m_leftSide->category() == CalcNumber) != (m_rightSide->category() == CalcNumber));
+ if (m_leftSide->category() == CalcNumber)
+ m_rightSide->accumulatePixelsAndPercent(conversionData, value, multiplier * m_leftSide->doubleValue());
+ else
+ m_leftSide->accumulatePixelsAndPercent(conversionData, value, multiplier * m_rightSide->doubleValue());
+ break;
+ case CalcDivide:
+ ASSERT(m_rightSide->category() == CalcNumber);
+ m_leftSide->accumulatePixelsAndPercent(conversionData, value, multiplier / m_rightSide->doubleValue());
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ }
}
- virtual double doubleValue() const
+ virtual double doubleValue() const OVERRIDE
{
return evaluate(m_leftSide->doubleValue(), m_rightSide->doubleValue());
}
- virtual double computeLengthPx(const CSSToLengthConversionData& conversionData) const
+ virtual double computeLengthPx(const CSSToLengthConversionData& conversionData) const OVERRIDE
{
const double leftValue = m_leftSide->computeLengthPx(conversionData);
const double rightValue = m_rightSide->computeLengthPx(conversionData);
return evaluate(leftValue, rightValue);
}
+ virtual void accumulateLengthArray(CSSLengthArray& lengthArray, double multiplier) const
+ {
+ switch (m_operator) {
+ case CalcAdd:
+ m_leftSide->accumulateLengthArray(lengthArray, multiplier);
+ m_rightSide->accumulateLengthArray(lengthArray, multiplier);
+ break;
+ case CalcSubtract:
+ m_leftSide->accumulateLengthArray(lengthArray, multiplier);
+ m_rightSide->accumulateLengthArray(lengthArray, -multiplier);
+ break;
+ case CalcMultiply:
+ ASSERT((m_leftSide->category() == CalcNumber) != (m_rightSide->category() == CalcNumber));
+ if (m_leftSide->category() == CalcNumber)
+ m_rightSide->accumulateLengthArray(lengthArray, multiplier * m_leftSide->doubleValue());
+ else
+ m_leftSide->accumulateLengthArray(lengthArray, multiplier * m_rightSide->doubleValue());
+ break;
+ case CalcDivide:
+ ASSERT(m_rightSide->category() == CalcNumber);
+ m_leftSide->accumulateLengthArray(lengthArray, multiplier / m_rightSide->doubleValue());
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ }
+ }
+
static String buildCSSText(const String& leftExpression, const String& rightExpression, CalcOperator op)
{
StringBuilder result;
@@ -457,22 +480,12 @@ public:
return result.toString();
}
- virtual String customCSSText() const
+ virtual String customCSSText() const OVERRIDE
{
return buildCSSText(m_leftSide->customCSSText(), m_rightSide->customCSSText(), m_operator);
}
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
- {
- return buildCSSText(m_leftSide->serializeResolvingVariables(variables), m_rightSide->serializeResolvingVariables(variables), m_operator);
- }
-
- virtual bool hasVariableReference() const
- {
- return m_leftSide->hasVariableReference() || m_rightSide->hasVariableReference();
- }
-
- virtual bool equals(const CSSCalcExpressionNode& exp) const
+ virtual bool equals(const CSSCalcExpressionNode& exp) const OVERRIDE
{
if (type() != exp.type())
return false;
@@ -483,9 +496,9 @@ public:
&& m_operator == other.m_operator;
}
- virtual Type type() const { return CssCalcBinaryOperation; }
+ virtual Type type() const OVERRIDE { return CssCalcBinaryOperation; }
- virtual CSSPrimitiveValue::UnitTypes primitiveType() const
+ virtual CSSPrimitiveValue::UnitType primitiveType() const OVERRIDE
{
switch (m_category) {
case CalcNumber:
@@ -499,13 +512,11 @@ public:
return m_rightSide->primitiveType();
if (m_rightSide->category() == CalcNumber)
return m_leftSide->primitiveType();
- CSSPrimitiveValue::UnitTypes leftType = m_leftSide->primitiveType();
+ CSSPrimitiveValue::UnitType leftType = m_leftSide->primitiveType();
if (leftType == m_rightSide->primitiveType())
return leftType;
return CSSPrimitiveValue::CSS_UNKNOWN;
}
- case CalcVariable:
- return CSSPrimitiveValue::CSS_VARIABLE_NAME;
case CalcPercentLength:
case CalcPercentNumber:
case CalcOther:
@@ -515,9 +526,15 @@ public:
return CSSPrimitiveValue::CSS_UNKNOWN;
}
+ virtual void trace(Visitor* visitor)
+ {
+ visitor->trace(m_leftSide);
+ visitor->trace(m_rightSide);
+ CSSCalcExpressionNode::trace(visitor);
+ }
private:
- CSSCalcBinaryOperation(PassRefPtr<CSSCalcExpressionNode> leftSide, PassRefPtr<CSSCalcExpressionNode> rightSide, CalcOperator op, CalculationCategory category)
+ CSSCalcBinaryOperation(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> leftSide, PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> rightSide, CalcOperator op, CalculationCategory category)
: CSSCalcExpressionNode(category, isIntegerResult(leftSide.get(), rightSide.get(), op))
, m_leftSide(leftSide)
, m_rightSide(rightSide)
@@ -556,8 +573,8 @@ private:
return 0;
}
- const RefPtr<CSSCalcExpressionNode> m_leftSide;
- const RefPtr<CSSCalcExpressionNode> m_rightSide;
+ const RefPtrWillBeMember<CSSCalcExpressionNode> m_leftSide;
+ const RefPtrWillBeMember<CSSCalcExpressionNode> m_rightSide;
const CalcOperator m_operator;
};
@@ -572,21 +589,24 @@ static ParseState checkDepthAndIndex(int* depth, unsigned index, CSSParserValueL
}
class CSSCalcExpressionNodeParser {
+ STACK_ALLOCATED();
public:
- PassRefPtr<CSSCalcExpressionNode> parseCalc(CSSParserValueList* tokens)
+ PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> parseCalc(CSSParserValueList* tokens)
{
unsigned index = 0;
Value result;
bool ok = parseValueExpression(tokens, 0, &index, &result);
ASSERT_WITH_SECURITY_IMPLICATION(index <= tokens->size());
if (!ok || index != tokens->size())
- return 0;
+ return nullptr;
return result.value;
}
private:
struct Value {
- RefPtr<CSSCalcExpressionNode> value;
+ STACK_ALLOCATED();
+ public:
+ RefPtrWillBeMember<CSSCalcExpressionNode> value;
};
char operatorValue(CSSParserValueList* tokens, unsigned index)
@@ -603,14 +623,18 @@ private:
bool parseValue(CSSParserValueList* tokens, unsigned* index, Value* result)
{
CSSParserValue* parserValue = tokens->valueAt(*index);
- if (parserValue->unit == CSSParserValue::Operator || parserValue->unit == CSSParserValue::Function)
+ if (parserValue->unit == CSSParserValue::Operator)
return false;
- RefPtr<CSSValue> value = parserValue->createCSSValue();
+ RefPtrWillBeRawPtr<CSSValue> value = parserValue->createCSSValue();
if (!value || !value->isPrimitiveValue())
return false;
- result->value = CSSCalcPrimitiveValue::create(toCSSPrimitiveValue(value.get()), parserValue->isInt);
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value.get());
+ if (unitCategory(primitiveValue->primitiveType()) == CalcOther)
+ return false;
+
+ result->value = CSSCalcPrimitiveValue::create(primitiveValue, parserValue->isInt);
++*index;
return true;
@@ -695,96 +719,45 @@ private:
}
};
-PassRefPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(PassRefPtr<CSSPrimitiveValue> value, bool isInteger)
+PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> value, bool isInteger)
{
return CSSCalcPrimitiveValue::create(value, isInteger);
}
-PassRefPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(PassRefPtr<CSSCalcExpressionNode> leftSide, PassRefPtr<CSSCalcExpressionNode> rightSide, CalcOperator op)
+PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> leftSide, PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> rightSide, CalcOperator op)
{
return CSSCalcBinaryOperation::create(leftSide, rightSide, op);
}
-PassRefPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(const CalcExpressionNode* node, float zoom)
-{
- switch (node->type()) {
- case CalcExpressionNodeNumber: {
- float value = toCalcExpressionNumber(node)->value();
- return createExpressionNode(CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER), value == trunc(value));
- }
- case CalcExpressionNodeLength:
- return createExpressionNode(toCalcExpressionLength(node)->length(), zoom);
- case CalcExpressionNodeBinaryOperation: {
- const CalcExpressionBinaryOperation* binaryNode = toCalcExpressionBinaryOperation(node);
- return createExpressionNode(createExpressionNode(binaryNode->leftSide(), zoom), createExpressionNode(binaryNode->rightSide(), zoom), binaryNode->getOperator());
- }
- case CalcExpressionNodeBlendLength: {
- // FIXME(crbug.com/269320): Create a CSSCalcExpressionNode equivalent of CalcExpressionBlendLength.
- const CalcExpressionBlendLength* blendNode = toCalcExpressionBlendLength(node);
- const double progress = blendNode->progress();
- const bool isInteger = !progress || (progress == 1);
- return createExpressionNode(
- createExpressionNode(
- createExpressionNode(blendNode->from(), zoom),
- createExpressionNode(CSSPrimitiveValue::create(1 - progress, CSSPrimitiveValue::CSS_NUMBER), isInteger),
- CalcMultiply),
- createExpressionNode(
- createExpressionNode(blendNode->to(), zoom),
- createExpressionNode(CSSPrimitiveValue::create(progress, CSSPrimitiveValue::CSS_NUMBER), isInteger),
- CalcMultiply),
- CalcAdd);
- }
- case CalcExpressionNodeUndefined:
- ASSERT_NOT_REACHED();
- return 0;
- }
- ASSERT_NOT_REACHED();
- return 0;
-}
-
-PassRefPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(const Length& length, float zoom)
+PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> CSSCalcValue::createExpressionNode(double pixels, double percent)
{
- switch (length.type()) {
- case Percent:
- case ViewportPercentageWidth:
- case ViewportPercentageHeight:
- case ViewportPercentageMin:
- case ViewportPercentageMax:
- case Fixed:
- return createExpressionNode(CSSPrimitiveValue::create(length, zoom), length.value() == trunc(length.value()));
- case Calculated:
- return createExpressionNode(length.calculationValue()->expression(), zoom);
- case Auto:
- case Intrinsic:
- case MinIntrinsic:
- case MinContent:
- case MaxContent:
- case FillAvailable:
- case FitContent:
- case ExtendToZoom:
- case Undefined:
- ASSERT_NOT_REACHED();
- return 0;
- }
- ASSERT_NOT_REACHED();
- return 0;
+ return createExpressionNode(
+ createExpressionNode(CSSPrimitiveValue::create(pixels, CSSPrimitiveValue::CSS_PX), pixels == trunc(pixels)),
+ createExpressionNode(CSSPrimitiveValue::create(percent, CSSPrimitiveValue::CSS_PERCENTAGE), percent == trunc(percent)),
+ CalcAdd);
}
-PassRefPtr<CSSCalcValue> CSSCalcValue::create(CSSParserString name, CSSParserValueList* parserValueList, ValueRange range)
+PassRefPtrWillBeRawPtr<CSSCalcValue> CSSCalcValue::create(CSSParserString name, CSSParserValueList* parserValueList, ValueRange range)
{
CSSCalcExpressionNodeParser parser;
- RefPtr<CSSCalcExpressionNode> expression;
+ RefPtrWillBeRawPtr<CSSCalcExpressionNode> expression = nullptr;
if (equalIgnoringCase(name, "calc(") || equalIgnoringCase(name, "-webkit-calc("))
expression = parser.parseCalc(parserValueList);
// FIXME calc (http://webkit.org/b/16662) Add parsing for min and max here
- return expression ? adoptRef(new CSSCalcValue(expression, range)) : 0;
+ return expression ? adoptRefWillBeNoop(new CSSCalcValue(expression, range)) : nullptr;
+}
+
+PassRefPtrWillBeRawPtr<CSSCalcValue> CSSCalcValue::create(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> expression, ValueRange range)
+{
+ return adoptRefWillBeNoop(new CSSCalcValue(expression, range));
}
-PassRefPtr<CSSCalcValue> CSSCalcValue::create(PassRefPtr<CSSCalcExpressionNode> expression, ValueRange range)
+void CSSCalcValue::traceAfterDispatch(Visitor* visitor)
{
- return adoptRef(new CSSCalcValue(expression, range));
+ visitor->trace(m_expression);
+ CSSValue::traceAfterDispatch(visitor);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.h b/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.h
index 6d58d608931..a7678850ffb 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCalculationValue.h
@@ -47,43 +47,51 @@ class CalculationValue;
class CalcExpressionNode;
class Length;
+enum CalcOperator {
+ CalcAdd = '+',
+ CalcSubtract = '-',
+ CalcMultiply = '*',
+ CalcDivide = '/'
+};
+
enum CalculationCategory {
CalcNumber = 0,
CalcLength,
CalcPercent,
CalcPercentNumber,
CalcPercentLength,
- CalcVariable,
CalcOther
};
-class CSSCalcExpressionNode : public RefCounted<CSSCalcExpressionNode> {
+class CSSCalcExpressionNode : public RefCountedWillBeGarbageCollected<CSSCalcExpressionNode> {
+ DECLARE_EMPTY_VIRTUAL_DESTRUCTOR_WILL_BE_REMOVED(CSSCalcExpressionNode);
public:
enum Type {
CssCalcPrimitiveValue = 1,
CssCalcBinaryOperation
};
- virtual ~CSSCalcExpressionNode() = 0;
virtual bool isZero() const = 0;
- virtual PassOwnPtr<CalcExpressionNode> toCalcValue(const CSSToLengthConversionData&) const = 0;
virtual double doubleValue() const = 0;
virtual double computeLengthPx(const CSSToLengthConversionData&) const = 0;
+ virtual void accumulateLengthArray(CSSLengthArray&, double multiplier) const = 0;
+ virtual void accumulatePixelsAndPercent(const CSSToLengthConversionData&, PixelsAndPercent&, float multiplier = 1) const = 0;
virtual String customCSSText() const = 0;
- virtual String serializeResolvingVariables(const HashMap<AtomicString, String>&) const = 0;
- virtual bool hasVariableReference() const = 0;
virtual bool equals(const CSSCalcExpressionNode& other) const { return m_category == other.m_category && m_isInteger == other.m_isInteger; }
virtual Type type() const = 0;
CalculationCategory category() const { return m_category; }
- virtual CSSPrimitiveValue::UnitTypes primitiveType() const = 0;
+ virtual CSSPrimitiveValue::UnitType primitiveType() const = 0;
bool isInteger() const { return m_isInteger; }
+ virtual void trace(Visitor*) { }
+
protected:
CSSCalcExpressionNode(CalculationCategory category, bool isInteger)
: m_category(category)
, m_isInteger(isInteger)
{
+ ASSERT(category != CalcOther);
}
CalculationCategory m_category;
@@ -92,18 +100,18 @@ protected:
class CSSCalcValue : public CSSValue {
public:
- static PassRefPtr<CSSCalcValue> create(CSSParserString name, CSSParserValueList*, ValueRange);
- static PassRefPtr<CSSCalcValue> create(PassRefPtr<CSSCalcExpressionNode>, ValueRange = ValueRangeAll);
- static PassRefPtr<CSSCalcValue> create(const CalculationValue* value, float zoom) { return adoptRef(new CSSCalcValue(value, zoom)); }
+ static PassRefPtrWillBeRawPtr<CSSCalcValue> create(CSSParserString name, CSSParserValueList*, ValueRange);
+ static PassRefPtrWillBeRawPtr<CSSCalcValue> create(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode>, ValueRange = ValueRangeAll);
- static PassRefPtr<CSSCalcExpressionNode> createExpressionNode(PassRefPtr<CSSPrimitiveValue>, bool isInteger = false);
- static PassRefPtr<CSSCalcExpressionNode> createExpressionNode(PassRefPtr<CSSCalcExpressionNode>, PassRefPtr<CSSCalcExpressionNode>, CalcOperator);
- static PassRefPtr<CSSCalcExpressionNode> createExpressionNode(const CalcExpressionNode*, float zoom);
- static PassRefPtr<CSSCalcExpressionNode> createExpressionNode(const Length&, float zoom);
+ static PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> createExpressionNode(PassRefPtrWillBeRawPtr<CSSPrimitiveValue>, bool isInteger = false);
+ static PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> createExpressionNode(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode>, PassRefPtrWillBeRawPtr<CSSCalcExpressionNode>, CalcOperator);
+ static PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> createExpressionNode(double pixels, double percent);
PassRefPtr<CalculationValue> toCalcValue(const CSSToLengthConversionData& conversionData) const
{
- return CalculationValue::create(m_expression->toCalcValue(conversionData), m_nonNegative ? ValueRangeNonNegative : ValueRangeAll);
+ PixelsAndPercent value(0, 0);
+ m_expression->accumulatePixelsAndPercent(conversionData, value);
+ return CalculationValue::create(value, m_nonNegative ? ValueRangeNonNegative : ValueRangeAll);
}
CalculationCategory category() const { return m_expression->category(); }
bool isInt() const { return m_expression->isInteger(); }
@@ -111,30 +119,25 @@ public:
bool isNegative() const { return m_expression->doubleValue() < 0; }
ValueRange permittedValueRange() { return m_nonNegative ? ValueRangeNonNegative : ValueRangeAll; }
double computeLengthPx(const CSSToLengthConversionData&) const;
+ void accumulateLengthArray(CSSLengthArray& lengthArray, double multiplier) const { m_expression->accumulateLengthArray(lengthArray, multiplier); }
CSSCalcExpressionNode* expressionNode() const { return m_expression.get(); }
String customCSSText() const;
bool equals(const CSSCalcValue&) const;
- String customSerializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- bool hasVariableReference() const;
+
+ void traceAfterDispatch(Visitor*);
private:
- CSSCalcValue(PassRefPtr<CSSCalcExpressionNode> expression, ValueRange range)
+ CSSCalcValue(PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> expression, ValueRange range)
: CSSValue(CalculationClass)
, m_expression(expression)
, m_nonNegative(range == ValueRangeNonNegative)
{
}
- CSSCalcValue(const CalculationValue* value, float zoom)
- : CSSValue(CalculationClass)
- , m_expression(createExpressionNode(value->expression(), zoom))
- , m_nonNegative(value->isNonNegative())
- {
- }
double clampToPermittedRange(double) const;
- const RefPtr<CSSCalcExpressionNode> m_expression;
+ const RefPtrWillBeMember<CSSCalcExpressionNode> m_expression;
const bool m_nonNegative;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCalculationValueTest.cpp b/chromium/third_party/WebKit/Source/core/css/CSSCalculationValueTest.cpp
index 57875523784..76179e5c653 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCalculationValueTest.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCalculationValueTest.cpp
@@ -33,116 +33,166 @@
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSToLengthConversionData.h"
+#include "core/css/StylePropertySet.h"
#include "core/rendering/style/RenderStyle.h"
#include "core/rendering/style/StyleInheritedData.h"
#include <gtest/gtest.h>
+
+namespace WebCore {
+
+void PrintTo(const CSSLengthArray& lengthArray, ::std::ostream* os)
+{
+ for (size_t i = 0; i < CSSPrimitiveValue::LengthUnitTypeCount; ++i)
+ *os << lengthArray.at(i) << ' ';
+}
+
+}
+
using namespace WebCore;
namespace {
-void testExpression(PassRefPtr<CSSCalcExpressionNode> expression, const RenderStyle* style)
+void testAccumulatePixelsAndPercent(const CSSToLengthConversionData& conversionData, PassRefPtrWillBeRawPtr<CSSCalcExpressionNode> expression, float expectedPixels, float expectedPercent)
{
- EXPECT_TRUE(
- expression->equals(
- *CSSCalcValue::createExpressionNode(
- expression->toCalcValue(CSSToLengthConversionData(style, style)).get(),
- style->effectiveZoom()).get()));
+ PixelsAndPercent value(0, 0);
+ expression->accumulatePixelsAndPercent(conversionData, value);
+ EXPECT_EQ(expectedPixels, value.pixels);
+ EXPECT_EQ(expectedPercent, value.percent);
}
-TEST(CSSCalculationValue, CreateExpressionNodeFromLength)
+void initLengthArray(CSSLengthArray& lengthArray)
{
- RefPtr<RenderStyle> style = RenderStyle::create();
- RefPtr<CSSCalcExpressionNode> expected;
- RefPtr<CSSCalcExpressionNode> actual;
+ lengthArray.resize(CSSPrimitiveValue::LengthUnitTypeCount);
+ for (size_t i = 0; i < CSSPrimitiveValue::LengthUnitTypeCount; ++i)
+ lengthArray.at(i) = 0;
+}
- expected = CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(10, CSSPrimitiveValue::CSS_PX), true);
- actual = CSSCalcValue::createExpressionNode(Length(10, WebCore::Fixed), style->effectiveZoom());
- EXPECT_TRUE(actual->equals(*expected.get()));
+CSSLengthArray& setLengthArray(CSSLengthArray& lengthArray, String text)
+{
+ initLengthArray(lengthArray);
+ RefPtr<MutableStylePropertySet> propertySet = MutableStylePropertySet::create();
+ propertySet->setProperty(CSSPropertyLeft, text);
+ toCSSPrimitiveValue(propertySet->getPropertyCSSValue(CSSPropertyLeft).get())->accumulateLengthArray(lengthArray);
+ return lengthArray;
+}
- expected = CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(10, CSSPrimitiveValue::CSS_PX), true),
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(20, CSSPrimitiveValue::CSS_PX), true),
- CalcAdd);
- actual = CSSCalcValue::createExpressionNode(
- Length(CalculationValue::create(
- adoptPtr(new CalcExpressionBinaryOperation(
- adoptPtr(new CalcExpressionLength(Length(10, WebCore::Fixed))),
- adoptPtr(new CalcExpressionLength(Length(20, WebCore::Fixed))),
- CalcAdd)),
- ValueRangeAll)),
- style->effectiveZoom());
- EXPECT_TRUE(actual->equals(*expected.get()));
-
- expected = CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(30, CSSPrimitiveValue::CSS_PX), true),
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(40, CSSPrimitiveValue::CSS_NUMBER), true),
- CalcMultiply);
- actual = CSSCalcValue::createExpressionNode(
- Length(CalculationValue::create(
- adoptPtr(new CalcExpressionBinaryOperation(
- adoptPtr(new CalcExpressionLength(Length(30, WebCore::Fixed))),
- adoptPtr(new CalcExpressionNumber(40)),
- CalcMultiply)),
- ValueRangeAll)),
- style->effectiveZoom());
- EXPECT_TRUE(actual->equals(*expected.get()));
-
- expected = CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(50, CSSPrimitiveValue::CSS_PX), true),
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(0.25, CSSPrimitiveValue::CSS_NUMBER), false),
- CalcMultiply),
- CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(60, CSSPrimitiveValue::CSS_PX), true),
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(0.75, CSSPrimitiveValue::CSS_NUMBER), false),
- CalcMultiply),
- CalcAdd);
- actual = CSSCalcValue::createExpressionNode(
- Length(CalculationValue::create(
- adoptPtr(new CalcExpressionBlendLength(Length(50, WebCore::Fixed), Length(60, WebCore::Fixed), 0.75)),
- ValueRangeAll)),
- style->effectiveZoom());
- EXPECT_TRUE(actual->equals(*expected.get()));
+bool lengthArraysEqual(CSSLengthArray& a, CSSLengthArray& b)
+{
+ for (size_t i = 0; i < CSSPrimitiveValue::LengthUnitTypeCount; ++i) {
+ if (a.at(i) != b.at(i))
+ return false;
+ }
+ return true;
}
-TEST(CSSCalculationValue, CreateExpressionNodeFromLengthFromExpressionNode)
+TEST(CSSCalculationValue, AccumulatePixelsAndPercent)
{
- RefPtr<CSSCalcExpressionNode> expression;
RefPtr<RenderStyle> style = RenderStyle::createDefaultStyle();
style->setEffectiveZoom(5);
+ CSSToLengthConversionData conversionData(style.get(), style.get(), 0);
- testExpression(
+ testAccumulatePixelsAndPercent(conversionData,
CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(10, CSSPrimitiveValue::CSS_PX), true),
- style.get());
+ 50, 0);
- testExpression(
+ testAccumulatePixelsAndPercent(conversionData,
CSSCalcValue::createExpressionNode(
CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(10, CSSPrimitiveValue::CSS_PX), true),
CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(20, CSSPrimitiveValue::CSS_PX), true),
CalcAdd),
- style.get());
+ 150, 0);
- testExpression(
+ testAccumulatePixelsAndPercent(conversionData,
CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(30, CSSPrimitiveValue::CSS_PX), true),
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(40, CSSPrimitiveValue::CSS_NUMBER), true),
+ CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(1, CSSPrimitiveValue::CSS_IN), true),
+ CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(2, CSSPrimitiveValue::CSS_NUMBER), true),
CalcMultiply),
- style.get());
+ 960, 0);
- testExpression(
+ testAccumulatePixelsAndPercent(conversionData,
CSSCalcValue::createExpressionNode(
CSSCalcValue::createExpressionNode(
CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(50, CSSPrimitiveValue::CSS_PX), true),
CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(0.25, CSSPrimitiveValue::CSS_NUMBER), false),
CalcMultiply),
CSSCalcValue::createExpressionNode(
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(60, CSSPrimitiveValue::CSS_PX), true),
- CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(0.75, CSSPrimitiveValue::CSS_NUMBER), false),
- CalcMultiply),
- CalcAdd),
- style.get());
+ CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(20, CSSPrimitiveValue::CSS_PX), true),
+ CSSCalcValue::createExpressionNode(CSSPrimitiveValue::create(40, CSSPrimitiveValue::CSS_PERCENTAGE), false),
+ CalcSubtract),
+ CalcSubtract),
+ -37.5, 40);
+}
+
+TEST(CSSCalculationValue, RefCount)
+{
+ RefPtr<CalculationValue> calc = CalculationValue::create(PixelsAndPercent(1, 2), ValueRangeAll);
+ Length lengthA(calc);
+ EXPECT_EQ(calc->refCount(), 2);
+
+ Length lengthB;
+ lengthB = lengthA;
+ EXPECT_EQ(calc->refCount(), 3);
+
+ Length lengthC(calc);
+ lengthC = lengthA;
+ EXPECT_EQ(calc->refCount(), 4);
+
+ Length lengthD(CalculationValue::create(PixelsAndPercent(1, 2), ValueRangeAll));
+ lengthD = lengthA;
+ EXPECT_EQ(calc->refCount(), 5);
+}
+
+TEST(CSSCalculationValue, RefCountLeak)
+{
+ RefPtr<CalculationValue> calc = CalculationValue::create(PixelsAndPercent(1, 2), ValueRangeAll);
+ Length lengthA(calc);
+
+ Length lengthB = lengthA;
+ for (int i = 0; i < 100; ++i)
+ lengthB = lengthA;
+ EXPECT_EQ(calc->refCount(), 3);
+
+ Length lengthC(lengthA);
+ for (int i = 0; i < 100; ++i)
+ lengthC = lengthA;
+ EXPECT_EQ(calc->refCount(), 4);
+
+ Length lengthD(calc);
+ for (int i = 0; i < 100; ++i)
+ lengthD = lengthA;
+ EXPECT_EQ(calc->refCount(), 5);
+
+ lengthD = Length();
+ EXPECT_EQ(calc->refCount(), 4);
+}
+
+TEST(CSSCalculationValue, AddToLengthUnitValues)
+{
+ CSSLengthArray expectation, actual;
+ initLengthArray(expectation);
+ EXPECT_TRUE(lengthArraysEqual(expectation, setLengthArray(actual, "0")));
+
+ expectation.at(CSSPrimitiveValue::UnitTypePixels) = 10;
+ EXPECT_TRUE(lengthArraysEqual(expectation, setLengthArray(actual, "10px")));
+
+ expectation.at(CSSPrimitiveValue::UnitTypePixels) = 0;
+ expectation.at(CSSPrimitiveValue::UnitTypePercentage) = 20;
+ EXPECT_TRUE(lengthArraysEqual(expectation, setLengthArray(actual, "20%%")));
+
+ expectation.at(CSSPrimitiveValue::UnitTypePixels) = 30;
+ expectation.at(CSSPrimitiveValue::UnitTypePercentage) = -40;
+ EXPECT_TRUE(lengthArraysEqual(expectation, setLengthArray(actual, "calc(30px - 40%%)")));
+
+ expectation.at(CSSPrimitiveValue::UnitTypePixels) = 90;
+ expectation.at(CSSPrimitiveValue::UnitTypePercentage) = 10;
+ EXPECT_TRUE(lengthArraysEqual(expectation, setLengthArray(actual, "calc(1in + 10%% - 6px)")));
+
+ expectation.at(CSSPrimitiveValue::UnitTypePixels) = 15;
+ expectation.at(CSSPrimitiveValue::UnitTypeFontSize) = 20;
+ expectation.at(CSSPrimitiveValue::UnitTypePercentage) = -40;
+ EXPECT_TRUE(lengthArraysEqual(expectation, setLengthArray(actual, "calc((1 * 2) * (5px + 20em / 2) - 80%% / (3 - 1) + 5px)")));
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.cpp
index ce46f047472..d770846aa40 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.cpp
@@ -33,8 +33,10 @@ namespace WebCore {
CSSCanvasValue::~CSSCanvasValue()
{
+#if !ENABLE(OILPAN)
if (m_element)
- m_element->removeObserver(&m_canvasObserver);
+ m_element->removeObserver(m_canvasObserver.get());
+#endif
}
String CSSCanvasValue::customCSSText() const
@@ -61,11 +63,13 @@ void CSSCanvasValue::canvasResized(HTMLCanvasElement*)
const_cast<RenderObject*>(curr->key)->imageChanged(static_cast<WrappedImagePtr>(this));
}
+#if !ENABLE(OILPAN)
void CSSCanvasValue::canvasDestroyed(HTMLCanvasElement* element)
{
ASSERT_UNUSED(element, element == m_element);
- m_element = 0;
+ m_element = nullptr;
}
+#endif
IntSize CSSCanvasValue::fixedSize(const RenderObject* renderer)
{
@@ -77,10 +81,8 @@ IntSize CSSCanvasValue::fixedSize(const RenderObject* renderer)
HTMLCanvasElement* CSSCanvasValue::element(Document* document)
{
if (!m_element) {
- m_element = document->getCSSCanvasElement(m_name);
- if (!m_element)
- return 0;
- m_element->addObserver(&m_canvasObserver);
+ m_element = &document->getCSSCanvasElement(m_name);
+ m_element->addObserver(m_canvasObserver.get());
}
return m_element;
}
@@ -90,7 +92,7 @@ PassRefPtr<Image> CSSCanvasValue::image(RenderObject* renderer, const IntSize& /
ASSERT(clients().contains(renderer));
HTMLCanvasElement* elt = element(&renderer->document());
if (!elt || !elt->buffer())
- return 0;
+ return nullptr;
return elt->copiedImage();
}
@@ -99,4 +101,11 @@ bool CSSCanvasValue::equals(const CSSCanvasValue& other) const
return m_name == other.m_name;
}
+void CSSCanvasValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_canvasObserver);
+ visitor->trace(m_element);
+ CSSImageGeneratorValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.h b/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.h
index bb2325f2b8b..3e23b7eb0eb 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCanvasValue.h
@@ -35,7 +35,10 @@ class Document;
class CSSCanvasValue : public CSSImageGeneratorValue {
public:
- static PassRefPtr<CSSCanvasValue> create(const String& name) { return adoptRef(new CSSCanvasValue(name)); }
+ static PassRefPtrWillBeRawPtr<CSSCanvasValue> create(const String& name)
+ {
+ return adoptRefWillBeNoop(new CSSCanvasValue(name));
+ }
~CSSCanvasValue();
String customCSSText() const;
@@ -49,49 +52,63 @@ public:
bool equals(const CSSCanvasValue&) const;
+ void traceAfterDispatch(Visitor*);
+
private:
explicit CSSCanvasValue(const String& name)
: CSSImageGeneratorValue(CanvasClass)
- , m_canvasObserver(this)
+ , m_canvasObserver(adoptPtrWillBeNoop(new CanvasObserverProxy(this)))
, m_name(name)
- , m_element(0)
+ , m_element(nullptr)
{
}
// NOTE: We put the CanvasObserver in a member instead of inheriting from it
// to avoid adding a vptr to CSSCanvasValue.
- class CanvasObserverProxy : public CanvasObserver {
+ class CanvasObserverProxy FINAL : public NoBaseWillBeGarbageCollected<CanvasObserverProxy>, public CanvasObserver {
+ WILL_BE_USING_GARBAGE_COLLECTED_MIXIN(CanvasObserverProxy);
public:
- CanvasObserverProxy(CSSCanvasValue* ownerValue) : m_ownerValue(ownerValue) { }
- virtual ~CanvasObserverProxy() { }
- virtual void canvasChanged(HTMLCanvasElement* canvas, const FloatRect& changedRect)
+ explicit CanvasObserverProxy(CSSCanvasValue* ownerValue) : m_ownerValue(ownerValue) { }
+
+ virtual void canvasChanged(HTMLCanvasElement* canvas, const FloatRect& changedRect) OVERRIDE
{
m_ownerValue->canvasChanged(canvas, changedRect);
}
- virtual void canvasResized(HTMLCanvasElement* canvas)
+ virtual void canvasResized(HTMLCanvasElement* canvas) OVERRIDE
{
m_ownerValue->canvasResized(canvas);
}
- virtual void canvasDestroyed(HTMLCanvasElement* canvas)
+#if !ENABLE(OILPAN)
+ virtual void canvasDestroyed(HTMLCanvasElement* canvas) OVERRIDE
{
m_ownerValue->canvasDestroyed(canvas);
}
+#endif
+ virtual void trace(Visitor* visitor) OVERRIDE
+ {
+ visitor->trace(m_ownerValue);
+ CanvasObserver::trace(visitor);
+ }
+
private:
- CSSCanvasValue* m_ownerValue;
+ RawPtrWillBeMember<CSSCanvasValue> m_ownerValue;
};
void canvasChanged(HTMLCanvasElement*, const FloatRect& changedRect);
void canvasResized(HTMLCanvasElement*);
+
+#if !ENABLE(OILPAN)
void canvasDestroyed(HTMLCanvasElement*);
+#endif
HTMLCanvasElement* element(Document*);
- CanvasObserverProxy m_canvasObserver;
+ OwnPtrWillBeMember<CanvasObserverProxy> m_canvasObserver;
// The name of the canvas.
String m_name;
// The document supplies the element and owns it.
- HTMLCanvasElement* m_element;
+ RawPtrWillBeWeakMember<HTMLCanvasElement> m_element;
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSCanvasValue, isCanvasValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.h b/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.h
index 26ae5fd793f..01c3a306c4a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.h
@@ -28,11 +28,11 @@ namespace WebCore {
class ExceptionState;
-class CSSCharsetRule : public CSSRule {
+class CSSCharsetRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSCharsetRule> create(CSSStyleSheet* parent, const String& encoding)
+ static PassRefPtrWillBeRawPtr<CSSCharsetRule> create(CSSStyleSheet* parent, const String& encoding)
{
- return adoptRef(new CSSCharsetRule(parent, encoding));
+ return adoptRefWillBeNoop(new CSSCharsetRule(parent, encoding));
}
virtual ~CSSCharsetRule() { }
@@ -44,6 +44,8 @@ public:
const String& encoding() const { return m_encoding; }
void setEncoding(const String& encoding) { m_encoding = encoding; }
+ virtual void trace(Visitor* visitor) OVERRIDE { CSSRule::trace(visitor); }
+
private:
CSSCharsetRule(CSSStyleSheet* parent, const String& encoding);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.idl b/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.idl
index 18216075aba..1635a719012 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCharsetRule.idl
@@ -19,5 +19,5 @@
*/
interface CSSCharsetRule : CSSRule {
- attribute DOMString encoding;
+ [MeasureAs=CSSCharsetRuleEncoding] attribute DOMString encoding;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.cpp b/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.cpp
index d5888386226..733191a5147 100755..100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.cpp
@@ -24,11 +24,9 @@
#include "config.h"
#include "core/css/CSSComputedStyleDeclaration.h"
-#include "CSSPropertyNames.h"
-#include "FontFamilyNames.h"
-#include "RuntimeEnabledFeatures.h"
-#include "StylePropertyShorthand.h"
#include "bindings/v8/ExceptionState.h"
+#include "core/CSSPropertyNames.h"
+#include "core/StylePropertyShorthand.h"
#include "core/animation/DocumentAnimations.h"
#include "core/css/BasicShapeFunctions.h"
#include "core/css/CSSArrayFunctionValue.h"
@@ -39,10 +37,9 @@
#include "core/css/CSSFontValue.h"
#include "core/css/CSSFunctionValue.h"
#include "core/css/CSSGridLineNamesValue.h"
-#include "core/css/CSSGridTemplateValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
#include "core/css/CSSLineBoxContainValue.h"
-#include "core/css/CSSMixFunctionValue.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSPrimitiveValueMappings.h"
#include "core/css/CSSReflectValue.h"
@@ -60,23 +57,16 @@
#include "core/dom/Document.h"
#include "core/dom/ExceptionCode.h"
#include "core/dom/PseudoElement.h"
-#include "core/frame/animation/AnimationController.h"
#include "core/rendering/RenderBox.h"
#include "core/rendering/RenderGrid.h"
-#include "core/rendering/RenderView.h"
#include "core/rendering/style/ContentData.h"
#include "core/rendering/style/CounterContent.h"
-#include "core/rendering/style/CursorList.h"
#include "core/rendering/style/RenderStyle.h"
#include "core/rendering/style/ShadowList.h"
#include "core/rendering/style/ShapeValue.h"
-#include "core/rendering/style/StyleCustomFilterProgram.h"
+#include "platform/FontFamilyNames.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/fonts/FontFeatureSettings.h"
-#include "platform/graphics/filters/custom/CustomFilterArrayParameter.h"
-#include "platform/graphics/filters/custom/CustomFilterNumberParameter.h"
-#include "platform/graphics/filters/custom/CustomFilterOperation.h"
-#include "platform/graphics/filters/custom/CustomFilterParameter.h"
-#include "platform/graphics/filters/custom/CustomFilterTransformParameter.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
@@ -141,10 +131,12 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyFontSize,
CSSPropertyFontStyle,
CSSPropertyFontVariant,
+ CSSPropertyFontVariantLigatures,
CSSPropertyFontWeight,
CSSPropertyHeight,
CSSPropertyImageRendering,
CSSPropertyIsolation,
+ CSSPropertyJustifySelf,
CSSPropertyLeft,
CSSPropertyLetterSpacing,
CSSPropertyLineHeight,
@@ -182,6 +174,7 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyPosition,
CSSPropertyResize,
CSSPropertyRight,
+ CSSPropertyScrollBehavior,
CSSPropertySpeak,
CSSPropertyTableLayout,
CSSPropertyTabSize,
@@ -211,6 +204,7 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyWhiteSpace,
CSSPropertyWidows,
CSSPropertyWidth,
+ CSSPropertyWillChange,
CSSPropertyWordBreak,
CSSPropertyWordSpacing,
CSSPropertyWordWrap,
@@ -226,6 +220,7 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyWebkitAnimationPlayState,
CSSPropertyWebkitAnimationTimingFunction,
CSSPropertyWebkitAppearance,
+ CSSPropertyBackfaceVisibility,
CSSPropertyWebkitBackfaceVisibility,
CSSPropertyWebkitBackgroundClip,
CSSPropertyWebkitBackgroundComposite,
@@ -250,10 +245,8 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyWebkitColumnBreakAfter,
CSSPropertyWebkitColumnBreakBefore,
CSSPropertyWebkitColumnBreakInside,
- CSSPropertyWebkitColumnAxis,
CSSPropertyWebkitColumnCount,
CSSPropertyWebkitColumnGap,
- CSSPropertyWebkitColumnProgression,
CSSPropertyWebkitColumnRuleColor,
CSSPropertyWebkitColumnRuleStyle,
CSSPropertyWebkitColumnRuleWidth,
@@ -270,24 +263,21 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyFlexWrap,
CSSPropertyJustifyContent,
CSSPropertyWebkitFontSmoothing,
- CSSPropertyWebkitFontVariantLigatures,
CSSPropertyGridAutoColumns,
CSSPropertyGridAutoFlow,
CSSPropertyGridAutoRows,
CSSPropertyGridColumnEnd,
CSSPropertyGridColumnStart,
- CSSPropertyGridDefinitionColumns,
- CSSPropertyGridDefinitionRows,
+ CSSPropertyGridTemplateAreas,
+ CSSPropertyGridTemplateColumns,
+ CSSPropertyGridTemplateRows,
CSSPropertyGridRowEnd,
CSSPropertyGridRowStart,
CSSPropertyWebkitHighlight,
CSSPropertyWebkitHyphenateCharacter,
- CSSPropertyWebkitLineAlign,
CSSPropertyWebkitLineBoxContain,
CSSPropertyWebkitLineBreak,
CSSPropertyWebkitLineClamp,
- CSSPropertyWebkitLineGrid,
- CSSPropertyWebkitLineSnap,
CSSPropertyWebkitLocale,
CSSPropertyWebkitMarginBeforeCollapse,
CSSPropertyWebkitMarginAfterCollapse,
@@ -305,13 +295,13 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyWebkitMaskRepeat,
CSSPropertyWebkitMaskSize,
CSSPropertyOrder,
+ CSSPropertyPerspective,
CSSPropertyWebkitPerspective,
+ CSSPropertyPerspectiveOrigin,
CSSPropertyWebkitPerspectiveOrigin,
CSSPropertyWebkitPrintColorAdjust,
CSSPropertyWebkitRtlOrdering,
- CSSPropertyShapeInside,
CSSPropertyShapeOutside,
- CSSPropertyShapePadding,
CSSPropertyShapeImageThreshold,
CSSPropertyShapeMargin,
CSSPropertyWebkitTapHighlightColor,
@@ -325,8 +315,11 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyWebkitTextSecurity,
CSSPropertyWebkitTextStrokeColor,
CSSPropertyWebkitTextStrokeWidth,
+ CSSPropertyTransform,
CSSPropertyWebkitTransform,
+ CSSPropertyTransformOrigin,
CSSPropertyWebkitTransformOrigin,
+ CSSPropertyTransformStyle,
CSSPropertyWebkitTransformStyle,
CSSPropertyWebkitTransitionDelay,
CSSPropertyWebkitTransitionDuration,
@@ -336,12 +329,6 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyWebkitUserModify,
CSSPropertyWebkitUserSelect,
CSSPropertyWebkitWritingMode,
- CSSPropertyWebkitFlowInto,
- CSSPropertyWebkitFlowFrom,
- CSSPropertyWebkitRegionBreakAfter,
- CSSPropertyWebkitRegionBreakBefore,
- CSSPropertyWebkitRegionBreakInside,
- CSSPropertyWebkitRegionFragment,
CSSPropertyWebkitAppRegion,
CSSPropertyWebkitWrapFlow,
CSSPropertyWebkitWrapThrough,
@@ -378,7 +365,6 @@ static const CSSPropertyID staticComputableProperties[] = {
CSSPropertyAlignmentBaseline,
CSSPropertyBaselineShift,
CSSPropertyDominantBaseline,
- CSSPropertyKerning,
CSSPropertyTextAnchor,
CSSPropertyWritingMode,
CSSPropertyGlyphOrientationHorizontal,
@@ -409,13 +395,13 @@ static CSSValueID valueForRepeatRule(int rule)
}
}
-static PassRefPtr<CSSBorderImageSliceValue> valueForNinePieceImageSlice(const NinePieceImage& image)
+static PassRefPtrWillBeRawPtr<CSSBorderImageSliceValue> valueForNinePieceImageSlice(const NinePieceImage& image)
{
// Create the slices.
- RefPtr<CSSPrimitiveValue> top;
- RefPtr<CSSPrimitiveValue> right;
- RefPtr<CSSPrimitiveValue> bottom;
- RefPtr<CSSPrimitiveValue> left;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> top = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> right = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> bottom = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> left = nullptr;
if (image.imageSlices().top().isPercent())
top = cssValuePool().createValue(image.imageSlices().top().value(), CSSPrimitiveValue::CSS_PERCENTAGE);
@@ -453,7 +439,7 @@ static PassRefPtr<CSSBorderImageSliceValue> valueForNinePieceImageSlice(const Ni
}
}
- RefPtr<Quad> quad = Quad::create();
+ RefPtrWillBeRawPtr<Quad> quad = Quad::create();
quad->setTop(top);
quad->setRight(right);
quad->setBottom(bottom);
@@ -462,13 +448,13 @@ static PassRefPtr<CSSBorderImageSliceValue> valueForNinePieceImageSlice(const Ni
return CSSBorderImageSliceValue::create(cssValuePool().createValue(quad.release()), image.fill());
}
-static PassRefPtr<CSSPrimitiveValue> valueForNinePieceImageQuad(const BorderImageLengthBox& box, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForNinePieceImageQuad(const BorderImageLengthBox& box, const RenderStyle& style)
{
// Create the slices.
- RefPtr<CSSPrimitiveValue> top;
- RefPtr<CSSPrimitiveValue> right;
- RefPtr<CSSPrimitiveValue> bottom;
- RefPtr<CSSPrimitiveValue> left;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> top = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> right = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> bottom = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> left = nullptr;
if (box.top().isNumber())
top = cssValuePool().createValue(box.top().number(), CSSPrimitiveValue::CSS_NUMBER);
@@ -505,7 +491,7 @@ static PassRefPtr<CSSPrimitiveValue> valueForNinePieceImageQuad(const BorderImag
}
}
- RefPtr<Quad> quad = Quad::create();
+ RefPtrWillBeRawPtr<Quad> quad = Quad::create();
quad->setTop(top);
quad->setRight(right);
quad->setBottom(bottom);
@@ -514,10 +500,10 @@ static PassRefPtr<CSSPrimitiveValue> valueForNinePieceImageQuad(const BorderImag
return cssValuePool().createValue(quad.release());
}
-static PassRefPtr<CSSValue> valueForNinePieceImageRepeat(const NinePieceImage& image)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForNinePieceImageRepeat(const NinePieceImage& image)
{
- RefPtr<CSSPrimitiveValue> horizontalRepeat;
- RefPtr<CSSPrimitiveValue> verticalRepeat;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> horizontalRepeat = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> verticalRepeat = nullptr;
horizontalRepeat = cssValuePool().createIdentifierValue(valueForRepeatRule(image.horizontalRule()));
if (image.horizontalRule() == image.verticalRule())
@@ -527,60 +513,60 @@ static PassRefPtr<CSSValue> valueForNinePieceImageRepeat(const NinePieceImage& i
return cssValuePool().createValue(Pair::create(horizontalRepeat.release(), verticalRepeat.release(), Pair::DropIdenticalValues));
}
-static PassRefPtr<CSSValue> valueForNinePieceImage(const NinePieceImage& image, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForNinePieceImage(const NinePieceImage& image, const RenderStyle& style)
{
if (!image.hasImage())
return cssValuePool().createIdentifierValue(CSSValueNone);
// Image first.
- RefPtr<CSSValue> imageValue;
+ RefPtrWillBeRawPtr<CSSValue> imageValue = nullptr;
if (image.image())
imageValue = image.image()->cssValue();
// Create the image slice.
- RefPtr<CSSBorderImageSliceValue> imageSlices = valueForNinePieceImageSlice(image);
+ RefPtrWillBeRawPtr<CSSBorderImageSliceValue> imageSlices = valueForNinePieceImageSlice(image);
// Create the border area slices.
- RefPtr<CSSValue> borderSlices = valueForNinePieceImageQuad(image.borderSlices(), style);
+ RefPtrWillBeRawPtr<CSSValue> borderSlices = valueForNinePieceImageQuad(image.borderSlices(), style);
// Create the border outset.
- RefPtr<CSSValue> outset = valueForNinePieceImageQuad(image.outset(), style);
+ RefPtrWillBeRawPtr<CSSValue> outset = valueForNinePieceImageQuad(image.outset(), style);
// Create the repeat rules.
- RefPtr<CSSValue> repeat = valueForNinePieceImageRepeat(image);
+ RefPtrWillBeRawPtr<CSSValue> repeat = valueForNinePieceImageRepeat(image);
return createBorderImageValue(imageValue.release(), imageSlices.release(), borderSlices.release(), outset.release(), repeat.release());
}
-inline static PassRefPtr<CSSPrimitiveValue> zoomAdjustedPixelValue(double value, const RenderStyle& style)
+inline static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> zoomAdjustedPixelValue(double value, const RenderStyle& style)
{
return cssValuePool().createValue(adjustFloatForAbsoluteZoom(value, style), CSSPrimitiveValue::CSS_PX);
}
-inline static PassRefPtr<CSSPrimitiveValue> zoomAdjustedNumberValue(double value, const RenderStyle& style)
+inline static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> zoomAdjustedNumberValue(double value, const RenderStyle& style)
{
return cssValuePool().createValue(value / style.effectiveZoom(), CSSPrimitiveValue::CSS_NUMBER);
}
-static PassRefPtr<CSSPrimitiveValue> zoomAdjustedPixelValueForLength(const Length& length, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> zoomAdjustedPixelValueForLength(const Length& length, const RenderStyle& style)
{
if (length.isFixed())
return zoomAdjustedPixelValue(length.value(), style);
return cssValuePool().createValue(length, style);
}
-static PassRefPtr<CSSValue> valueForReflection(const StyleReflection* reflection, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForReflection(const StyleReflection* reflection, const RenderStyle& style)
{
if (!reflection)
return cssValuePool().createIdentifierValue(CSSValueNone);
- RefPtr<CSSPrimitiveValue> offset;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> offset = nullptr;
if (reflection->offset().isPercent())
offset = cssValuePool().createValue(reflection->offset().percent(), CSSPrimitiveValue::CSS_PERCENTAGE);
else
offset = zoomAdjustedPixelValue(reflection->offset().value(), style);
- RefPtr<CSSPrimitiveValue> direction;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> direction = nullptr;
switch (reflection->direction()) {
case ReflectionBelow:
direction = cssValuePool().createIdentifierValue(CSSValueBelow);
@@ -599,9 +585,9 @@ static PassRefPtr<CSSValue> valueForReflection(const StyleReflection* reflection
return CSSReflectValue::create(direction.release(), offset.release(), valueForNinePieceImage(reflection->mask(), style));
}
-static PassRefPtr<CSSValueList> createPositionListForLayer(CSSPropertyID propertyID, const FillLayer* layer, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValueList> createPositionListForLayer(CSSPropertyID propertyID, const FillLayer* layer, const RenderStyle& style)
{
- RefPtr<CSSValueList> positionList = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> positionList = CSSValueList::createSpaceSeparated();
if (layer->isBackgroundXOriginSet()) {
ASSERT_UNUSED(propertyID, propertyID == CSSPropertyBackgroundPosition || propertyID == CSSPropertyWebkitMaskPosition);
positionList->append(cssValuePool().createValue(layer->backgroundXOrigin()));
@@ -615,7 +601,7 @@ static PassRefPtr<CSSValueList> createPositionListForLayer(CSSPropertyID propert
return positionList.release();
}
-static PassRefPtr<CSSValue> valueForPositionOffset(RenderStyle& style, CSSPropertyID propertyID, const RenderObject* renderer, RenderView* renderView)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForPositionOffset(RenderStyle& style, CSSPropertyID propertyID, const RenderObject* renderer)
{
Length l;
switch (propertyID) {
@@ -632,38 +618,34 @@ static PassRefPtr<CSSValue> valueForPositionOffset(RenderStyle& style, CSSProper
l = style.bottom();
break;
default:
- return 0;
+ return nullptr;
}
if (l.isPercent() && renderer && renderer->isBox()) {
LayoutUnit containingBlockSize = (propertyID == CSSPropertyLeft || propertyID == CSSPropertyRight) ?
toRenderBox(renderer)->containingBlockLogicalWidthForContent() :
toRenderBox(renderer)->containingBlockLogicalHeightForContent(ExcludeMarginBorderPadding);
- return zoomAdjustedPixelValue(valueForLength(l, containingBlockSize, 0), style);
+ return zoomAdjustedPixelValue(valueForLength(l, containingBlockSize), style);
}
- if (l.isViewportPercentage())
- return zoomAdjustedPixelValue(valueForLength(l, 0, renderView), style);
if (l.isAuto()) {
// FIXME: It's not enough to simply return "auto" values for one offset if the other side is defined.
// In other words if left is auto and right is not auto, then left's computed value is negative right().
// So we should get the opposite length unit and see if it is auto.
- return cssValuePool().createValue(l);
+ return cssValuePool().createIdentifierValue(CSSValueAuto);
}
return zoomAdjustedPixelValueForLength(l, style);
}
-PassRefPtr<CSSPrimitiveValue> CSSComputedStyleDeclaration::currentColorOrValidColor(const RenderStyle& style, const Color& color) const
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSComputedStyleDeclaration::currentColorOrValidColor(const RenderStyle& style, const StyleColor& color) const
{
// This function does NOT look at visited information, so that computed style doesn't expose that.
- if (!color.isValid())
- return cssValuePool().createColorValue(style.color().rgb());
- return cssValuePool().createColorValue(color.rgb());
+ return cssValuePool().createColorValue(color.resolve(style.color()).rgb());
}
-static PassRefPtr<CSSValueList> valuesForBorderRadiusCorner(LengthSize radius, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValueList> valuesForBorderRadiusCorner(LengthSize radius, const RenderStyle& style)
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (radius.width().type() == Percent)
list->append(cssValuePool().createValue(radius.width().percent(), CSSPrimitiveValue::CSS_PERCENTAGE));
else
@@ -675,17 +657,17 @@ static PassRefPtr<CSSValueList> valuesForBorderRadiusCorner(LengthSize radius, c
return list.release();
}
-static PassRefPtr<CSSValue> valueForBorderRadiusCorner(LengthSize radius, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForBorderRadiusCorner(LengthSize radius, const RenderStyle& style)
{
- RefPtr<CSSValueList> list = valuesForBorderRadiusCorner(radius, style);
+ RefPtrWillBeRawPtr<CSSValueList> list = valuesForBorderRadiusCorner(radius, style);
if (list->item(0)->equals(*list->item(1)))
return list->item(0);
return list.release();
}
-static PassRefPtr<CSSValueList> valueForBorderRadiusShorthand(const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValueList> valueForBorderRadiusShorthand(const RenderStyle& style)
{
- RefPtr<CSSValueList> list = CSSValueList::createSlashSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSlashSeparated();
bool showHorizontalBottomLeft = style.borderTopRightRadius().width() != style.borderBottomLeftRadius().width();
bool showHorizontalBottomRight = showHorizontalBottomLeft || (style.borderBottomRightRadius().width() != style.borderTopLeftRadius().width());
@@ -695,12 +677,12 @@ static PassRefPtr<CSSValueList> valueForBorderRadiusShorthand(const RenderStyle&
bool showVerticalBottomRight = showVerticalBottomLeft || (style.borderBottomRightRadius().height() != style.borderTopLeftRadius().height());
bool showVerticalTopRight = showVerticalBottomRight || (style.borderTopRightRadius().height() != style.borderTopLeftRadius().height());
- RefPtr<CSSValueList> topLeftRadius = valuesForBorderRadiusCorner(style.borderTopLeftRadius(), style);
- RefPtr<CSSValueList> topRightRadius = valuesForBorderRadiusCorner(style.borderTopRightRadius(), style);
- RefPtr<CSSValueList> bottomRightRadius = valuesForBorderRadiusCorner(style.borderBottomRightRadius(), style);
- RefPtr<CSSValueList> bottomLeftRadius = valuesForBorderRadiusCorner(style.borderBottomLeftRadius(), style);
+ RefPtrWillBeRawPtr<CSSValueList> topLeftRadius = valuesForBorderRadiusCorner(style.borderTopLeftRadius(), style);
+ RefPtrWillBeRawPtr<CSSValueList> topRightRadius = valuesForBorderRadiusCorner(style.borderTopRightRadius(), style);
+ RefPtrWillBeRawPtr<CSSValueList> bottomRightRadius = valuesForBorderRadiusCorner(style.borderBottomRightRadius(), style);
+ RefPtrWillBeRawPtr<CSSValueList> bottomLeftRadius = valuesForBorderRadiusCorner(style.borderBottomLeftRadius(), style);
- RefPtr<CSSValueList> horizontalRadii = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> horizontalRadii = CSSValueList::createSpaceSeparated();
horizontalRadii->append(topLeftRadius->item(0));
if (showHorizontalTopRight)
horizontalRadii->append(topRightRadius->item(0));
@@ -711,7 +693,7 @@ static PassRefPtr<CSSValueList> valueForBorderRadiusShorthand(const RenderStyle&
list->append(horizontalRadii.release());
- RefPtr<CSSValueList> verticalRadii = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> verticalRadii = CSSValueList::createSpaceSeparated();
verticalRadii->append(topLeftRadius->item(1));
if (showVerticalTopRight)
verticalRadii->append(topRightRadius->item(1));
@@ -735,9 +717,9 @@ static LayoutRect sizingBox(RenderObject* renderer)
return box->style()->boxSizing() == BORDER_BOX ? box->borderBoxRect() : box->computedCSSContentBoxRect();
}
-static PassRefPtr<CSSTransformValue> valueForMatrixTransform(const TransformationMatrix& transform, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSTransformValue> valueForMatrixTransform(const TransformationMatrix& transform, const RenderStyle& style)
{
- RefPtr<CSSTransformValue> transformValue;
+ RefPtrWillBeRawPtr<CSSTransformValue> transformValue = nullptr;
if (transform.isAffine()) {
transformValue = CSSTransformValue::create(CSSTransformValue::MatrixTransformOperation);
@@ -774,7 +756,7 @@ static PassRefPtr<CSSTransformValue> valueForMatrixTransform(const Transformatio
return transformValue.release();
}
-static PassRefPtr<CSSValue> computedTransform(RenderObject* renderer, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValue> computedTransform(RenderObject* renderer, const RenderStyle& style)
{
if (!renderer || !renderer->hasTransform() || !style.hasTransform())
return cssValuePool().createIdentifierValue(CSSValueNone);
@@ -787,69 +769,24 @@ static PassRefPtr<CSSValue> computedTransform(RenderObject* renderer, const Rend
style.applyTransform(transform, box.size(), RenderStyle::ExcludeTransformOrigin);
// FIXME: Need to print out individual functions (https://bugs.webkit.org/show_bug.cgi?id=23924)
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
list->append(valueForMatrixTransform(transform, style));
return list.release();
}
-static PassRefPtr<CSSValue> valueForCustomFilterArrayParameter(const CustomFilterArrayParameter* arrayParameter)
-{
- RefPtr<CSSArrayFunctionValue> arrayParameterValue = CSSArrayFunctionValue::create();
- for (unsigned i = 0, size = arrayParameter->size(); i < size; ++i)
- arrayParameterValue->append(cssValuePool().createValue(arrayParameter->valueAt(i), CSSPrimitiveValue::CSS_NUMBER));
- return arrayParameterValue.release();
-}
-
-static PassRefPtr<CSSValue> valueForCustomFilterNumberParameter(const CustomFilterNumberParameter* numberParameter)
-{
- RefPtr<CSSValueList> numberParameterValue = CSSValueList::createSpaceSeparated();
- for (unsigned i = 0; i < numberParameter->size(); ++i)
- numberParameterValue->append(cssValuePool().createValue(numberParameter->valueAt(i), CSSPrimitiveValue::CSS_NUMBER));
- return numberParameterValue.release();
-}
-
-static PassRefPtr<CSSValue> valueForCustomFilterTransformParameter(const RenderObject* renderer, const RenderStyle& style, const CustomFilterTransformParameter* transformParameter)
-{
- IntSize size;
- if (renderer && renderer->isBox())
- size = pixelSnappedIntRect(toRenderBox(renderer)->borderBoxRect()).size();
-
- TransformationMatrix transform;
- transformParameter->applyTransform(transform, size);
- // FIXME: Need to print out individual functions (https://bugs.webkit.org/show_bug.cgi?id=23924)
- return valueForMatrixTransform(transform, style);
-}
-
-static PassRefPtr<CSSValue> valueForCustomFilterParameter(const RenderObject* renderer, const RenderStyle& style, const CustomFilterParameter* parameter)
-{
- // FIXME: Add here computed style for the other types: boolean, transform, matrix, texture.
- ASSERT(parameter);
- switch (parameter->parameterType()) {
- case CustomFilterParameter::Array:
- return valueForCustomFilterArrayParameter(static_cast<const CustomFilterArrayParameter*>(parameter));
- case CustomFilterParameter::Number:
- return valueForCustomFilterNumberParameter(static_cast<const CustomFilterNumberParameter*>(parameter));
- case CustomFilterParameter::Transform:
- return valueForCustomFilterTransformParameter(renderer, style, static_cast<const CustomFilterTransformParameter*>(parameter));
- }
-
- ASSERT_NOT_REACHED();
- return 0;
-}
-
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::valueForFilter(const RenderObject* renderer, const RenderStyle& style) const
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::valueForFilter(const RenderObject* renderer, const RenderStyle& style) const
{
if (style.filter().operations().isEmpty())
return cssValuePool().createIdentifierValue(CSSValueNone);
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- RefPtr<CSSFilterValue> filterValue;
+ RefPtrWillBeRawPtr<CSSFilterValue> filterValue = nullptr;
Vector<RefPtr<FilterOperation> >::const_iterator end = style.filter().operations().end();
for (Vector<RefPtr<FilterOperation> >::const_iterator it = style.filter().operations().begin(); it != end; ++it) {
- FilterOperation* filterOperation = (*it).get();
+ FilterOperation* filterOperation = it->get();
switch (filterOperation->type()) {
case FilterOperation::REFERENCE:
filterValue = CSSFilterValue::create(CSSFilterValue::ReferenceFilterOperation);
@@ -899,68 +836,6 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::valueForFilter(const RenderObj
filterValue->append(valueForShadowData(shadow, style, false));
break;
}
- case FilterOperation::VALIDATED_CUSTOM:
- // ValidatedCustomFilterOperation is not supposed to end up in the RenderStyle.
- ASSERT_NOT_REACHED();
- break;
- case FilterOperation::CUSTOM: {
- CustomFilterOperation* customOperation = toCustomFilterOperation(filterOperation);
- filterValue = CSSFilterValue::create(CSSFilterValue::CustomFilterOperation);
-
- // The output should be verbose, even if the values are the default ones.
-
- ASSERT(customOperation->program());
- StyleCustomFilterProgram* program = static_cast<StyleCustomFilterProgram*>(customOperation->program());
-
- RefPtr<CSSValueList> shadersList = CSSValueList::createSpaceSeparated();
- if (program->vertexShader())
- shadersList->append(program->vertexShader()->cssValue());
- else
- shadersList->append(cssValuePool().createIdentifierValue(CSSValueNone));
-
- const CustomFilterProgramMixSettings mixSettings = program->mixSettings();
- if (program->fragmentShader()) {
- if (program->programType() == ProgramTypeBlendsElementTexture) {
- RefPtr<CSSMixFunctionValue> mixFunction = CSSMixFunctionValue::create();
- mixFunction->append(program->fragmentShader()->cssValue());
- mixFunction->append(cssValuePool().createValue(mixSettings.blendMode));
- mixFunction->append(cssValuePool().createValue(mixSettings.compositeOperator));
- shadersList->append(mixFunction.release());
- } else
- shadersList->append(program->fragmentShader()->cssValue());
- }
- else
- shadersList->append(cssValuePool().createIdentifierValue(CSSValueNone));
-
- filterValue->append(shadersList.release());
-
- RefPtr<CSSValueList> meshParameters = CSSValueList::createSpaceSeparated();
- meshParameters->append(cssValuePool().createValue(customOperation->meshColumns(), CSSPrimitiveValue::CSS_NUMBER));
- meshParameters->append(cssValuePool().createValue(customOperation->meshRows(), CSSPrimitiveValue::CSS_NUMBER));
-
- // FIXME: The specification doesn't have any "attached" identifier. Should we add one?
- // https://bugs.webkit.org/show_bug.cgi?id=72700
- if (customOperation->meshType() == MeshTypeDetached)
- meshParameters->append(cssValuePool().createIdentifierValue(CSSValueDetached));
-
- filterValue->append(meshParameters.release());
-
- const CustomFilterParameterList& parameters = customOperation->parameters();
- size_t parametersSize = parameters.size();
- if (!parametersSize)
- break;
- RefPtr<CSSValueList> parametersCSSValue = CSSValueList::createCommaSeparated();
- for (size_t i = 0; i < parametersSize; ++i) {
- const CustomFilterParameter* parameter = parameters.at(i).get();
- RefPtr<CSSValueList> parameterCSSNameAndValue = CSSValueList::createSpaceSeparated();
- parameterCSSNameAndValue->append(cssValuePool().createValue(parameter->name(), CSSPrimitiveValue::CSS_STRING));
- parameterCSSNameAndValue->append(valueForCustomFilterParameter(renderer, style, parameter));
- parametersCSSValue->append(parameterCSSNameAndValue.release());
- }
-
- filterValue->append(parametersCSSValue.release());
- break;
- }
default:
filterValue = CSSFilterValue::create(CSSFilterValue::UnknownFilterOperation);
break;
@@ -971,7 +846,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::valueForFilter(const RenderObj
return list.release();
}
-static PassRefPtr<CSSValue> specifiedValueForGridTrackBreadth(const GridLength& trackBreadth, const RenderStyle& style, RenderView* renderView)
+static PassRefPtrWillBeRawPtr<CSSValue> specifiedValueForGridTrackBreadth(const GridLength& trackBreadth, const RenderStyle& style)
{
if (!trackBreadth.isLength())
return cssValuePool().createValue(trackBreadth.flex(), CSSPrimitiveValue::CSS_FR);
@@ -979,24 +854,22 @@ static PassRefPtr<CSSValue> specifiedValueForGridTrackBreadth(const GridLength&
const Length& trackBreadthLength = trackBreadth.length();
if (trackBreadthLength.isAuto())
return cssValuePool().createIdentifierValue(CSSValueAuto);
- if (trackBreadthLength.isViewportPercentage())
- return zoomAdjustedPixelValue(valueForLength(trackBreadthLength, 0, renderView), style);
return zoomAdjustedPixelValueForLength(trackBreadthLength, style);
}
-static PassRefPtr<CSSValue> specifiedValueForGridTrackSize(const GridTrackSize& trackSize, const RenderStyle& style, RenderView* renderView)
+static PassRefPtrWillBeRawPtr<CSSValue> specifiedValueForGridTrackSize(const GridTrackSize& trackSize, const RenderStyle& style)
{
switch (trackSize.type()) {
case LengthTrackSizing:
- return specifiedValueForGridTrackBreadth(trackSize.length(), style, renderView);
+ return specifiedValueForGridTrackBreadth(trackSize.length(), style);
case MinMaxTrackSizing:
- RefPtr<CSSValueList> minMaxTrackBreadths = CSSValueList::createCommaSeparated();
- minMaxTrackBreadths->append(specifiedValueForGridTrackBreadth(trackSize.minTrackBreadth(), style, renderView));
- minMaxTrackBreadths->append(specifiedValueForGridTrackBreadth(trackSize.maxTrackBreadth(), style, renderView));
+ RefPtrWillBeRawPtr<CSSValueList> minMaxTrackBreadths = CSSValueList::createCommaSeparated();
+ minMaxTrackBreadths->append(specifiedValueForGridTrackBreadth(trackSize.minTrackBreadth(), style));
+ minMaxTrackBreadths->append(specifiedValueForGridTrackBreadth(trackSize.maxTrackBreadth(), style));
return CSSFunctionValue::create("minmax(", minMaxTrackBreadths);
}
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
static void addValuesForNamedGridLinesAtIndex(const OrderedNamedGridLines& orderedNamedGridLines, size_t i, CSSValueList& list)
@@ -1005,15 +878,15 @@ static void addValuesForNamedGridLinesAtIndex(const OrderedNamedGridLines& order
if (namedGridLines.isEmpty())
return;
- RefPtr<CSSGridLineNamesValue> lineNames = CSSGridLineNamesValue::create();
+ RefPtrWillBeRawPtr<CSSGridLineNamesValue> lineNames = CSSGridLineNamesValue::create();
for (size_t j = 0; j < namedGridLines.size(); ++j)
lineNames->append(cssValuePool().createValue(namedGridLines[j], CSSPrimitiveValue::CSS_STRING));
list.append(lineNames.release());
}
-static PassRefPtr<CSSValue> valueForGridTrackList(GridTrackSizingDirection direction, RenderObject* renderer, const RenderStyle& style, RenderView* renderView)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForGridTrackList(GridTrackSizingDirection direction, RenderObject* renderer, const RenderStyle& style)
{
- const Vector<GridTrackSize>& trackSizes = direction == ForColumns ? style.gridDefinitionColumns() : style.gridDefinitionRows();
+ const Vector<GridTrackSize>& trackSizes = direction == ForColumns ? style.gridTemplateColumns() : style.gridTemplateRows();
const OrderedNamedGridLines& orderedNamedGridLines = direction == ForColumns ? style.orderedNamedGridColumnLines() : style.orderedNamedGridRowLines();
// Handle the 'none' case here.
@@ -1022,7 +895,7 @@ static PassRefPtr<CSSValue> valueForGridTrackList(GridTrackSizingDirection direc
return cssValuePool().createIdentifierValue(CSSValueNone);
}
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (renderer && renderer->isRenderGrid()) {
const Vector<LayoutUnit>& trackPositions = direction == ForColumns ? toRenderGrid(renderer)->columnPositions() : toRenderGrid(renderer)->rowPositions();
// There are at least #tracks + 1 grid lines (trackPositions). Apart from that, the grid container can generate implicit grid tracks,
@@ -1036,7 +909,7 @@ static PassRefPtr<CSSValue> valueForGridTrackList(GridTrackSizingDirection direc
} else {
for (size_t i = 0; i < trackSizes.size(); ++i) {
addValuesForNamedGridLinesAtIndex(orderedNamedGridLines, i, *list);
- list->append(specifiedValueForGridTrackSize(trackSizes[i], style, renderView));
+ list->append(specifiedValueForGridTrackSize(trackSizes[i], style));
}
}
// Those are the trailing <string>* allowed in the syntax.
@@ -1044,7 +917,7 @@ static PassRefPtr<CSSValue> valueForGridTrackList(GridTrackSizingDirection direc
return list.release();
}
-static PassRefPtr<CSSValue> valueForGridPosition(const GridPosition& position)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForGridPosition(const GridPosition& position)
{
if (position.isAuto())
return cssValuePool().createIdentifierValue(CSSValueAuto);
@@ -1052,7 +925,7 @@ static PassRefPtr<CSSValue> valueForGridPosition(const GridPosition& position)
if (position.isNamedGridArea())
return cssValuePool().createValue(position.namedGridLine(), CSSPrimitiveValue::CSS_STRING);
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (position.isSpan()) {
list->append(cssValuePool().createIdentifierValue(CSSValueSpan));
list->append(cssValuePool().createValue(position.spanPosition(), CSSPrimitiveValue::CSS_NUMBER));
@@ -1063,55 +936,71 @@ static PassRefPtr<CSSValue> valueForGridPosition(const GridPosition& position)
list->append(cssValuePool().createValue(position.namedGridLine(), CSSPrimitiveValue::CSS_STRING));
return list;
}
-static PassRefPtr<CSSValue> createTransitionPropertyValue(const CSSAnimationData* animation)
+
+static PassRefPtrWillBeRawPtr<CSSValue> createTransitionPropertyValue(const CSSTransitionData::TransitionProperty& property)
{
- RefPtr<CSSValue> propertyValue;
- if (animation->animationMode() == CSSAnimationData::AnimateNone)
- propertyValue = cssValuePool().createIdentifierValue(CSSValueNone);
- else if (animation->animationMode() == CSSAnimationData::AnimateAll)
- propertyValue = cssValuePool().createIdentifierValue(CSSValueAll);
- else
- propertyValue = cssValuePool().createValue(getPropertyNameString(animation->property()), CSSPrimitiveValue::CSS_STRING);
- return propertyValue.release();
+ if (property.propertyType == CSSTransitionData::TransitionNone)
+ return cssValuePool().createIdentifierValue(CSSValueNone);
+ if (property.propertyType == CSSTransitionData::TransitionAll)
+ return cssValuePool().createIdentifierValue(CSSValueAll);
+ if (property.propertyType == CSSTransitionData::TransitionUnknown)
+ return cssValuePool().createValue(property.propertyString, CSSPrimitiveValue::CSS_STRING);
+ ASSERT(property.propertyType == CSSTransitionData::TransitionSingleProperty);
+ return cssValuePool().createValue(getPropertyNameString(property.propertyId), CSSPrimitiveValue::CSS_STRING);
}
-static PassRefPtr<CSSValue> valueForTransitionProperty(const CSSAnimationDataList* animList)
+
+static PassRefPtrWillBeRawPtr<CSSValue> valueForTransitionProperty(const CSSTransitionData* transitionData)
{
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- if (animList) {
- for (size_t i = 0; i < animList->size(); ++i)
- list->append(createTransitionPropertyValue(animList->animation(i)));
- } else
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ if (transitionData) {
+ for (size_t i = 0; i < transitionData->propertyList().size(); ++i)
+ list->append(createTransitionPropertyValue(transitionData->propertyList()[i]));
+ } else {
list->append(cssValuePool().createIdentifierValue(CSSValueAll));
+ }
return list.release();
}
-static PassRefPtr<CSSValue> valueForAnimationDelay(const CSSAnimationDataList* animList)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationDelay(const CSSTimingData* timingData)
{
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- if (animList) {
- for (size_t i = 0; i < animList->size(); ++i)
- list->append(cssValuePool().createValue(animList->animation(i)->delay(), CSSPrimitiveValue::CSS_S));
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ if (timingData) {
+ for (size_t i = 0; i < timingData->delayList().size(); ++i)
+ list->append(cssValuePool().createValue(timingData->delayList()[i], CSSPrimitiveValue::CSS_S));
} else {
- // Note that initialAnimationDelay() is used for both transitions and animations
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationDelay(), CSSPrimitiveValue::CSS_S));
+ list->append(cssValuePool().createValue(CSSTimingData::initialDelay(), CSSPrimitiveValue::CSS_S));
}
return list.release();
}
-static PassRefPtr<CSSValue> valueForAnimationDuration(const CSSAnimationDataList* animList)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationDuration(const CSSTimingData* timingData)
{
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- if (animList) {
- for (size_t i = 0; i < animList->size(); ++i)
- list->append(cssValuePool().createValue(animList->animation(i)->duration(), CSSPrimitiveValue::CSS_S));
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ if (timingData) {
+ for (size_t i = 0; i < timingData->durationList().size(); ++i)
+ list->append(cssValuePool().createValue(timingData->durationList()[i], CSSPrimitiveValue::CSS_S));
} else {
- // Note that initialAnimationDuration() is used for both transitions and animations
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationDuration(), CSSPrimitiveValue::CSS_S));
+ list->append(cssValuePool().createValue(CSSTimingData::initialDuration(), CSSPrimitiveValue::CSS_S));
}
return list.release();
}
-static PassRefPtr<CSSValue> createTimingFunctionValue(const TimingFunction* timingFunction)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationIterationCount(double iterationCount)
+{
+ if (iterationCount == std::numeric_limits<double>::infinity())
+ return cssValuePool().createIdentifierValue(CSSValueInfinite);
+ return cssValuePool().createValue(iterationCount, CSSPrimitiveValue::CSS_NUMBER);
+}
+
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationPlayState(EAnimPlayState playState)
+{
+ if (playState == AnimPlayStatePlaying)
+ return cssValuePool().createIdentifierValue(CSSValueRunning);
+ ASSERT(playState == AnimPlayStatePaused);
+ return cssValuePool().createIdentifierValue(CSSValuePaused);
+}
+
+static PassRefPtrWillBeRawPtr<CSSValue> createTimingFunctionValue(const TimingFunction* timingFunction)
{
switch (timingFunction->type()) {
case TimingFunction::CubicBezierFunction:
@@ -1134,7 +1023,7 @@ static PassRefPtr<CSSValue> createTimingFunctionValue(const TimingFunction* timi
break;
default:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
return cssValuePool().createIdentifierValue(valueId);
}
@@ -1145,7 +1034,8 @@ static PassRefPtr<CSSValue> createTimingFunctionValue(const TimingFunction* timi
{
const StepsTimingFunction* stepsTimingFunction = toStepsTimingFunction(timingFunction);
if (stepsTimingFunction->subType() == StepsTimingFunction::Custom)
- return CSSStepsTimingFunctionValue::create(stepsTimingFunction->numberOfSteps(), stepsTimingFunction->stepAtStart());
+ return CSSStepsTimingFunctionValue::create(stepsTimingFunction->numberOfSteps(), stepsTimingFunction->stepAtPosition());
+
CSSValueID valueId;
switch (stepsTimingFunction->subType()) {
case StepsTimingFunction::Start:
@@ -1156,7 +1046,7 @@ static PassRefPtr<CSSValue> createTimingFunctionValue(const TimingFunction* timi
break;
default:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
return cssValuePool().createIdentifierValue(valueId);
}
@@ -1166,63 +1056,79 @@ static PassRefPtr<CSSValue> createTimingFunctionValue(const TimingFunction* timi
}
}
-static PassRefPtr<CSSValue> valueForAnimationTimingFunction(const CSSAnimationDataList* animList)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationTimingFunction(const CSSTimingData* timingData)
{
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- if (animList) {
- for (size_t i = 0; i < animList->size(); ++i)
- list->append(createTimingFunctionValue(animList->animation(i)->timingFunction()));
- } else
- // Note that initialAnimationTimingFunction() is used for both transitions and animations
- list->append(createTimingFunctionValue(CSSAnimationData::initialAnimationTimingFunction().get()));
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ if (timingData) {
+ for (size_t i = 0; i < timingData->timingFunctionList().size(); ++i)
+ list->append(createTimingFunctionValue(timingData->timingFunctionList()[i].get()));
+ } else {
+ list->append(createTimingFunctionValue(CSSTimingData::initialTimingFunction().get()));
+ }
return list.release();
}
-static PassRefPtr<CSSValue> valueForAnimationFillMode(unsigned fillMode)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationFillMode(Timing::FillMode fillMode)
{
switch (fillMode) {
- case AnimationFillModeNone:
+ case Timing::FillModeNone:
return cssValuePool().createIdentifierValue(CSSValueNone);
- case AnimationFillModeForwards:
+ case Timing::FillModeForwards:
return cssValuePool().createIdentifierValue(CSSValueForwards);
- case AnimationFillModeBackwards:
+ case Timing::FillModeBackwards:
return cssValuePool().createIdentifierValue(CSSValueBackwards);
- case AnimationFillModeBoth:
+ case Timing::FillModeBoth:
return cssValuePool().createIdentifierValue(CSSValueBoth);
default:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
}
-static PassRefPtr<CSSValue> valueForAnimationDirection(CSSAnimationData::AnimationDirection direction)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForAnimationDirection(Timing::PlaybackDirection direction)
{
switch (direction) {
- case CSSAnimationData::AnimationDirectionNormal:
+ case Timing::PlaybackDirectionNormal:
return cssValuePool().createIdentifierValue(CSSValueNormal);
- case CSSAnimationData::AnimationDirectionAlternate:
+ case Timing::PlaybackDirectionAlternate:
return cssValuePool().createIdentifierValue(CSSValueAlternate);
- case CSSAnimationData::AnimationDirectionReverse:
+ case Timing::PlaybackDirectionReverse:
return cssValuePool().createIdentifierValue(CSSValueReverse);
- case CSSAnimationData::AnimationDirectionAlternateReverse:
+ case Timing::PlaybackDirectionAlternateReverse:
return cssValuePool().createIdentifierValue(CSSValueAlternateReverse);
default:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
}
-static PassRefPtr<CSSValue> createLineBoxContainValue(unsigned lineBoxContain)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForWillChange(const Vector<CSSPropertyID>& willChangeProperties, bool willChangeContents, bool willChangeScrollPosition)
+{
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ if (willChangeContents)
+ list->append(cssValuePool().createIdentifierValue(CSSValueContents));
+ if (willChangeScrollPosition)
+ list->append(cssValuePool().createIdentifierValue(CSSValueScrollPosition));
+ for (size_t i = 0; i < willChangeProperties.size(); ++i)
+ list->append(cssValuePool().createIdentifierValue(willChangeProperties[i]));
+ if (!list->length())
+ list->append(cssValuePool().createIdentifierValue(CSSValueAuto));
+ return list.release();
+}
+
+static PassRefPtrWillBeRawPtr<CSSValue> createLineBoxContainValue(unsigned lineBoxContain)
{
if (!lineBoxContain)
return cssValuePool().createIdentifierValue(CSSValueNone);
return CSSLineBoxContainValue::create(lineBoxContain);
}
-CSSComputedStyleDeclaration::CSSComputedStyleDeclaration(PassRefPtr<Node> n, bool allowVisitedStyle, const String& pseudoElementName)
+CSSComputedStyleDeclaration::CSSComputedStyleDeclaration(PassRefPtrWillBeRawPtr<Node> n, bool allowVisitedStyle, const String& pseudoElementName)
: m_node(n)
, m_allowVisitedStyle(allowVisitedStyle)
+#if !ENABLE(OILPAN)
, m_refCount(1)
+#endif
{
unsigned nameWithoutColonsStart = pseudoElementName[0] == ':' ? (pseudoElementName[1] == ':' ? 2 : 1) : 0;
m_pseudoElementSpecifier = CSSSelector::pseudoId(CSSSelector::parsePseudoType(
@@ -1233,6 +1139,7 @@ CSSComputedStyleDeclaration::~CSSComputedStyleDeclaration()
{
}
+#if !ENABLE(OILPAN)
void CSSComputedStyleDeclaration::ref()
{
++m_refCount;
@@ -1244,6 +1151,7 @@ void CSSComputedStyleDeclaration::deref()
if (!--m_refCount)
delete this;
}
+#endif
String CSSComputedStyleDeclaration::cssText() const
{
@@ -1274,16 +1182,16 @@ static CSSValueID cssIdentifierForFontSizeKeyword(int keywordSize)
return static_cast<CSSValueID>(CSSValueXxSmall + keywordSize - 1);
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getFontSizeCSSValuePreferringKeyword() const
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::getFontSizeCSSValuePreferringKeyword() const
{
if (!m_node)
- return 0;
+ return nullptr;
m_node->document().updateLayoutIgnorePendingStylesheets();
RefPtr<RenderStyle> style = m_node->computedStyle(m_pseudoElementSpecifier);
if (!style)
- return 0;
+ return nullptr;
if (int keywordSize = style->fontDescription().keywordSize())
return cssValuePool().createIdentifierValue(cssIdentifierForFontSizeKeyword(keywordSize));
@@ -1304,34 +1212,29 @@ bool CSSComputedStyleDeclaration::useFixedFontDefaultSize() const
return style->fontDescription().useFixedDefaultSize();
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::valueForShadowData(const ShadowData& shadow, const RenderStyle& style, bool useSpread) const
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::valueForShadowData(const ShadowData& shadow, const RenderStyle& style, bool useSpread) const
{
- RefPtr<CSSPrimitiveValue> x = zoomAdjustedPixelValue(shadow.x(), style);
- RefPtr<CSSPrimitiveValue> y = zoomAdjustedPixelValue(shadow.y(), style);
- RefPtr<CSSPrimitiveValue> blur = zoomAdjustedPixelValue(shadow.blur(), style);
- RefPtr<CSSPrimitiveValue> spread = useSpread ? zoomAdjustedPixelValue(shadow.spread(), style) : PassRefPtr<CSSPrimitiveValue>();
- RefPtr<CSSPrimitiveValue> shadowStyle = shadow.style() == Normal ? PassRefPtr<CSSPrimitiveValue>() : cssValuePool().createIdentifierValue(CSSValueInset);
- RefPtr<CSSPrimitiveValue> color = currentColorOrValidColor(style, shadow.color());
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> x = zoomAdjustedPixelValue(shadow.x(), style);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> y = zoomAdjustedPixelValue(shadow.y(), style);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> blur = zoomAdjustedPixelValue(shadow.blur(), style);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> spread = useSpread ? zoomAdjustedPixelValue(shadow.spread(), style) : PassRefPtrWillBeRawPtr<CSSPrimitiveValue>(nullptr);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> shadowStyle = shadow.style() == Normal ? PassRefPtrWillBeRawPtr<CSSPrimitiveValue>(nullptr) : cssValuePool().createIdentifierValue(CSSValueInset);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> color = currentColorOrValidColor(style, shadow.color());
return CSSShadowValue::create(x.release(), y.release(), blur.release(), spread.release(), shadowStyle.release(), color.release());
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::valueForShadowList(const ShadowList* shadowList, const RenderStyle& style, bool useSpread) const
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::valueForShadowList(const ShadowList* shadowList, const RenderStyle& style, bool useSpread) const
{
if (!shadowList)
return cssValuePool().createIdentifierValue(CSSValueNone);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
size_t shadowCount = shadowList->shadows().size();
for (size_t i = 0; i < shadowCount; ++i)
list->append(valueForShadowData(shadowList->shadows()[i], style, useSpread));
return list.release();
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropertyID propertyID) const
-{
- return getPropertyCSSValue(propertyID, UpdateLayout);
-}
-
static CSSValueID identifierForFamily(const AtomicString& family)
{
if (family == FontFamilyNames::webkit_cursive)
@@ -1349,17 +1252,17 @@ static CSSValueID identifierForFamily(const AtomicString& family)
return CSSValueInvalid;
}
-static PassRefPtr<CSSPrimitiveValue> valueForFamily(const AtomicString& family)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForFamily(const AtomicString& family)
{
if (CSSValueID familyIdentifier = identifierForFamily(family))
return cssValuePool().createIdentifierValue(familyIdentifier);
return cssValuePool().createValue(family.string(), CSSPrimitiveValue::CSS_STRING);
}
-static PassRefPtr<CSSValue> renderTextDecorationFlagsToCSSValue(int textDecoration)
+static PassRefPtrWillBeRawPtr<CSSValue> renderTextDecorationFlagsToCSSValue(int textDecoration)
{
// Blink value is ignored.
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (textDecoration & TextDecorationUnderline)
list->append(cssValuePool().createIdentifierValue(CSSValueUnderline));
if (textDecoration & TextDecorationOverline)
@@ -1372,7 +1275,7 @@ static PassRefPtr<CSSValue> renderTextDecorationFlagsToCSSValue(int textDecorati
return list.release();
}
-static PassRefPtr<CSSValue> valueForTextDecorationStyle(TextDecorationStyle textDecorationStyle)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForTextDecorationStyle(TextDecorationStyle textDecorationStyle)
{
switch (textDecorationStyle) {
case TextDecorationStyleSolid:
@@ -1391,7 +1294,7 @@ static PassRefPtr<CSSValue> valueForTextDecorationStyle(TextDecorationStyle text
return cssValuePool().createExplicitInitialValue();
}
-static PassRefPtr<CSSValue> valueForFillRepeat(EFillRepeat xRepeat, EFillRepeat yRepeat)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForFillRepeat(EFillRepeat xRepeat, EFillRepeat yRepeat)
{
// For backwards compatibility, if both values are equal, just return one of them. And
// if the two values are equivalent to repeat-x or repeat-y, just return the shorthand.
@@ -1402,13 +1305,13 @@ static PassRefPtr<CSSValue> valueForFillRepeat(EFillRepeat xRepeat, EFillRepeat
if (xRepeat == NoRepeatFill && yRepeat == RepeatFill)
return cssValuePool().createIdentifierValue(CSSValueRepeatY);
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
list->append(cssValuePool().createValue(xRepeat));
list->append(cssValuePool().createValue(yRepeat));
return list.release();
}
-static PassRefPtr<CSSValue> valueForFillSourceType(EMaskSourceType type)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForFillSourceType(EMaskSourceType type)
{
switch (type) {
case MaskAlpha:
@@ -1419,10 +1322,10 @@ static PassRefPtr<CSSValue> valueForFillSourceType(EMaskSourceType type)
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
-static PassRefPtr<CSSValue> valueForFillSize(const FillSize& fillSize, const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForFillSize(const FillSize& fillSize, const RenderStyle& style)
{
if (fillSize.type == Contain)
return cssValuePool().createIdentifierValue(CSSValueContain);
@@ -1433,15 +1336,15 @@ static PassRefPtr<CSSValue> valueForFillSize(const FillSize& fillSize, const Ren
if (fillSize.size.height().isAuto())
return zoomAdjustedPixelValueForLength(fillSize.size.width(), style);
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
list->append(zoomAdjustedPixelValueForLength(fillSize.size.width(), style));
list->append(zoomAdjustedPixelValueForLength(fillSize.size.height(), style));
return list.release();
}
-static PassRefPtr<CSSValue> valueForContentData(const RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForContentData(const RenderStyle& style)
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
for (const ContentData* contentData = style.contentData(); contentData; contentData = contentData->next()) {
if (contentData->isCounter()) {
const CounterContent* counter = static_cast<const CounterContentData*>(contentData)->counter();
@@ -1454,18 +1357,16 @@ static PassRefPtr<CSSValue> valueForContentData(const RenderStyle& style)
} else if (contentData->isText())
list->append(cssValuePool().createValue(static_cast<const TextContentData*>(contentData)->text(), CSSPrimitiveValue::CSS_STRING));
}
- if (style.hasFlowFrom())
- list->append(cssValuePool().createValue(style.regionThread(), CSSPrimitiveValue::CSS_STRING));
return list.release();
}
-static PassRefPtr<CSSValue> valueForCounterDirectives(const RenderStyle& style, CSSPropertyID propertyID)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForCounterDirectives(const RenderStyle& style, CSSPropertyID propertyID)
{
const CounterDirectiveMap* map = style.counterDirectives();
if (!map)
- return 0;
+ return nullptr;
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
for (CounterDirectiveMap::const_iterator it = map->begin(); it != map->end(); ++it) {
list->append(cssValuePool().createValue(it->key, CSSPrimitiveValue::CSS_STRING));
short number = propertyID == CSSPropertyCounterIncrement ? it->value.incrementValue() : it->value.resetValue();
@@ -1483,44 +1384,44 @@ static void logUnimplementedPropertyID(CSSPropertyID propertyID)
WTF_LOG_ERROR("WebKit does not yet implement getComputedStyle for '%s'.", getPropertyName(propertyID));
}
-static PassRefPtr<CSSValueList> valueForFontFamily(RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSValueList> valueForFontFamily(RenderStyle& style)
{
const FontFamily& firstFamily = style.fontDescription().family();
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FontFamily* family = &firstFamily; family; family = family->next())
list->append(valueForFamily(family->family()));
return list.release();
}
-static PassRefPtr<CSSPrimitiveValue> valueForLineHeight(RenderStyle& style, RenderView* renderView)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForLineHeight(RenderStyle& style)
{
Length length = style.lineHeight();
if (length.isNegative())
return cssValuePool().createIdentifierValue(CSSValueNormal);
- return zoomAdjustedPixelValue(floatValueForLength(length, style.fontDescription().specifiedSize(), renderView), style);
+ return zoomAdjustedPixelValue(floatValueForLength(length, style.fontDescription().specifiedSize()), style);
}
-static PassRefPtr<CSSPrimitiveValue> valueForFontSize(RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForFontSize(RenderStyle& style)
{
return zoomAdjustedPixelValue(style.fontDescription().computedPixelSize(), style);
}
-static PassRefPtr<CSSPrimitiveValue> valueForFontStyle(RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForFontStyle(RenderStyle& style)
{
- if (style.fontDescription().italic())
+ if (style.fontDescription().style() == FontStyleItalic)
return cssValuePool().createIdentifierValue(CSSValueItalic);
return cssValuePool().createIdentifierValue(CSSValueNormal);
}
-static PassRefPtr<CSSPrimitiveValue> valueForFontVariant(RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForFontVariant(RenderStyle& style)
{
- if (style.fontDescription().smallCaps())
+ if (style.fontDescription().variant() == FontVariantSmallCaps)
return cssValuePool().createIdentifierValue(CSSValueSmallCaps);
return cssValuePool().createIdentifierValue(CSSValueNormal);
}
-static PassRefPtr<CSSPrimitiveValue> valueForFontWeight(RenderStyle& style)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueForFontWeight(RenderStyle& style)
{
switch (style.fontDescription().weight()) {
case FontWeight100:
@@ -1546,20 +1447,44 @@ static PassRefPtr<CSSPrimitiveValue> valueForFontWeight(RenderStyle& style)
return cssValuePool().createIdentifierValue(CSSValueNormal);
}
-static PassRefPtr<CSSValue> touchActionFlagsToCSSValue(TouchAction touchAction)
+static PassRefPtrWillBeRawPtr<CSSValue> valueForShape(const RenderStyle& style, ShapeValue* shapeValue)
+{
+ if (!shapeValue)
+ return cssValuePool().createIdentifierValue(CSSValueNone);
+ if (shapeValue->type() == ShapeValue::Box)
+ return cssValuePool().createValue(shapeValue->cssBox());
+ if (shapeValue->type() == ShapeValue::Image) {
+ if (shapeValue->image())
+ return shapeValue->image()->cssValue();
+ return cssValuePool().createIdentifierValue(CSSValueNone);
+ }
+
+ ASSERT(shapeValue->type() == ShapeValue::Shape);
+
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ list->append(valueForBasicShape(style, shapeValue->shape()));
+ if (shapeValue->cssBox() != BoxMissing)
+ list->append(cssValuePool().createValue(shapeValue->cssBox()));
+ return list.release();
+}
+
+static PassRefPtrWillBeRawPtr<CSSValue> touchActionFlagsToCSSValue(TouchAction touchAction)
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (touchAction == TouchActionAuto)
list->append(cssValuePool().createIdentifierValue(CSSValueAuto));
if (touchAction & TouchActionNone) {
ASSERT(touchAction == TouchActionNone);
list->append(cssValuePool().createIdentifierValue(CSSValueNone));
}
- if (touchAction & TouchActionPanX)
- list->append(cssValuePool().createIdentifierValue(CSSValuePanX));
- if (touchAction & TouchActionPanY)
- list->append(cssValuePool().createIdentifierValue(CSSValuePanY));
-
+ if (touchAction == (TouchActionPanX | TouchActionPanY | TouchActionPinchZoom)) {
+ list->append(cssValuePool().createIdentifierValue(CSSValueManipulation));
+ } else {
+ if (touchAction & TouchActionPanX)
+ list->append(cssValuePool().createIdentifierValue(CSSValuePanX));
+ if (touchAction & TouchActionPanY)
+ list->append(cssValuePool().createIdentifierValue(CSSValuePanY));
+ }
ASSERT(list->length());
return list.release();
}
@@ -1573,14 +1498,17 @@ static bool isLayoutDependent(CSSPropertyID propertyID, PassRefPtr<RenderStyle>
// FIXME: Some of these cases could be narrowed down or optimized better.
switch (propertyID) {
case CSSPropertyBottom:
- case CSSPropertyGridDefinitionColumns:
- case CSSPropertyGridDefinitionRows:
+ case CSSPropertyGridTemplateColumns:
+ case CSSPropertyGridTemplateRows:
case CSSPropertyHeight:
case CSSPropertyLeft:
case CSSPropertyRight:
case CSSPropertyTop:
+ case CSSPropertyPerspectiveOrigin:
case CSSPropertyWebkitPerspectiveOrigin:
+ case CSSPropertyTransform:
case CSSPropertyWebkitTransform:
+ case CSSPropertyTransformOrigin:
case CSSPropertyWebkitTransformOrigin:
case CSSPropertyWidth:
case CSSPropertyWebkitFilter:
@@ -1614,16 +1542,6 @@ PassRefPtr<RenderStyle> CSSComputedStyleDeclaration::computeRenderStyle(CSSPrope
{
Node* styledNode = this->styledNode();
ASSERT(styledNode);
- RenderObject* renderer = styledNode->renderer();
- if (renderer && renderer->compositingState() == PaintsIntoOwnBacking
- && !RuntimeEnabledFeatures::webAnimationsCSSEnabled() && AnimationController::supportsAcceleratedAnimationOfProperty(propertyID)) {
- AnimationUpdateBlock animationUpdateBlock(renderer->animation());
- if (m_pseudoElementSpecifier && !styledNode->isPseudoElement()) {
- // FIXME: This cached pseudo style will only exist if the animation has been run at least once.
- return renderer->animation().getAnimatedStyleForRenderer(renderer)->getCachedPseudoStyle(m_pseudoElementSpecifier);
- }
- return renderer->animation().getAnimatedStyleForRenderer(renderer);
- }
return styledNode->computedStyle(styledNode->isPseudoElement() ? NOPSEUDO : m_pseudoElementSpecifier);
}
@@ -1638,22 +1556,30 @@ Node* CSSComputedStyleDeclaration::styledNode() const
return m_node.get();
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropertyID propertyID, EUpdateLayout updateLayout) const
+static PassRefPtrWillBeRawPtr<CSSValueList> valueForItemPositionWithOverflowAlignment(ItemPosition itemPosition, OverflowAlignment overflowAlignment)
+{
+ RefPtrWillBeRawPtr<CSSValueList> result = CSSValueList::createSpaceSeparated();
+ result->append(CSSPrimitiveValue::create(itemPosition));
+ if (itemPosition >= ItemPositionCenter && overflowAlignment != OverflowAlignmentDefault)
+ result->append(CSSPrimitiveValue::create(overflowAlignment));
+ return result.release();
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropertyID propertyID, EUpdateLayout updateLayout) const
{
Node* styledNode = this->styledNode();
if (!styledNode)
- return 0;
+ return nullptr;
RenderObject* renderer = styledNode->renderer();
RefPtr<RenderStyle> style;
if (updateLayout) {
Document& document = styledNode->document();
- // If a compositor animation is running we may need to service animations
- // in order to generate an up to date value.
- DocumentAnimations::serviceBeforeGetComputedStyle(*styledNode, propertyID);
+ // A timing update may be required if a compositor animation is running.
+ DocumentAnimations::updateAnimationTimingForGetComputedStyle(*styledNode, propertyID);
- document.updateStyleForNodeIfNeeded(styledNode);
+ document.updateRenderTreeForNodeIfNeeded(styledNode);
// The style recalc could have caused the styled node to be discarded or replaced
// if it was a PseudoElement so we need to update it.
@@ -1664,8 +1590,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
bool forceFullLayout = isLayoutDependent(propertyID, style, renderer)
|| styledNode->isInShadowTree()
- || (document.ownerElement() && document.ensureStyleResolver().hasViewportDependentMediaQueries())
- || document.seamlessParentIFrame();
+ || (document.ownerElement() && document.ensureStyleResolver().hasViewportDependentMediaQueries());
if (forceFullLayout) {
document.updateLayoutIgnorePendingStylesheets();
@@ -1678,17 +1603,16 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
}
if (!style)
- return 0;
+ return nullptr;
propertyID = CSSProperty::resolveDirectionAwareProperty(propertyID, style->direction(), style->writingMode());
switch (propertyID) {
case CSSPropertyInvalid:
- case CSSPropertyVariable:
break;
case CSSPropertyBackgroundColor:
- return cssValuePool().createColorValue(m_allowVisitedStyle? style->visitedDependentColor(CSSPropertyBackgroundColor).rgb() : style->backgroundColor().rgb());
+ return m_allowVisitedStyle ? cssValuePool().createColorValue(style->visitedDependentColor(CSSPropertyBackgroundColor).rgb()) : currentColorOrValidColor(*style, style->backgroundColor());
case CSSPropertyBackgroundImage:
case CSSPropertyWebkitMaskImage: {
const FillLayer* layers = propertyID == CSSPropertyWebkitMaskImage ? style->maskLayers() : style->backgroundLayers();
@@ -1702,7 +1626,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createIdentifierValue(CSSValueNone);
}
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next()) {
if (currLayer->image())
list->append(currLayer->image()->cssValue());
@@ -1718,7 +1642,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return valueForFillSize(layers->size(), *style);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(valueForFillSize(currLayer->size(), *style));
@@ -1730,7 +1654,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return valueForFillRepeat(layers->repeatX(), layers->repeatY());
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(valueForFillRepeat(currLayer->repeatX(), currLayer->repeatY()));
@@ -1745,7 +1669,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return valueForFillSourceType(layers->maskSourceType());
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(valueForFillSourceType(currLayer->maskSourceType()));
@@ -1757,7 +1681,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return cssValuePool().createValue(layers->composite());
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(cssValuePool().createValue(currLayer->composite()));
@@ -1768,7 +1692,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return cssValuePool().createValue(layers->attachment());
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(cssValuePool().createValue(currLayer->attachment()));
@@ -1787,7 +1711,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createValue(box);
}
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next()) {
EFillBox box = isClip ? currLayer->clip() : currLayer->origin();
list->append(cssValuePool().createValue(box));
@@ -1801,7 +1725,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return createPositionListForLayer(propertyID, layers, *style);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(createPositionListForLayer(propertyID, currLayer, *style));
return list.release();
@@ -1810,11 +1734,11 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyWebkitMaskPositionX: {
const FillLayer* layers = propertyID == CSSPropertyWebkitMaskPositionX ? style->maskLayers() : style->backgroundLayers();
if (!layers->next())
- return cssValuePool().createValue(layers->xPosition());
+ return zoomAdjustedPixelValueForLength(layers->xPosition(), *style);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
- list->append(cssValuePool().createValue(currLayer->xPosition()));
+ list->append(zoomAdjustedPixelValueForLength(currLayer->xPosition(), *style));
return list.release();
}
@@ -1822,11 +1746,11 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyWebkitMaskPositionY: {
const FillLayer* layers = propertyID == CSSPropertyWebkitMaskPositionY ? style->maskLayers() : style->backgroundLayers();
if (!layers->next())
- return cssValuePool().createValue(layers->yPosition());
+ return zoomAdjustedPixelValueForLength(layers->yPosition(), *style);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
- list->append(cssValuePool().createValue(currLayer->yPosition()));
+ list->append(zoomAdjustedPixelValueForLength(currLayer->yPosition(), *style));
return list.release();
}
@@ -1835,7 +1759,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createIdentifierValue(CSSValueCollapse);
return cssValuePool().createIdentifierValue(CSSValueSeparate);
case CSSPropertyBorderSpacing: {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
list->append(zoomAdjustedPixelValue(style->horizontalBorderSpacing(), *style));
list->append(zoomAdjustedPixelValue(style->verticalBorderSpacing(), *style));
return list.release();
@@ -1873,7 +1797,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyBorderLeftWidth:
return zoomAdjustedPixelValue(style->borderLeftWidth(), *style);
case CSSPropertyBottom:
- return valueForPositionOffset(*style, CSSPropertyBottom, renderer, m_node->document().renderView());
+ return valueForPositionOffset(*style, CSSPropertyBottom, renderer);
case CSSPropertyWebkitBoxAlign:
return cssValuePool().createValue(style->boxAlign());
case CSSPropertyWebkitBoxDecorationBreak:
@@ -1907,8 +1831,6 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createColorValue(m_allowVisitedStyle ? style->visitedDependentColor(CSSPropertyColor).rgb() : style->color().rgb());
case CSSPropertyWebkitPrintColorAdjust:
return cssValuePool().createValue(style->printColorAdjust());
- case CSSPropertyWebkitColumnAxis:
- return cssValuePool().createValue(style->columnAxis());
case CSSPropertyWebkitColumnCount:
if (style->hasAutoColumnCount())
return cssValuePool().createIdentifierValue(CSSValueAuto);
@@ -1916,13 +1838,11 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyColumnFill:
if (RuntimeEnabledFeatures::regionBasedColumnsEnabled())
return cssValuePool().createValue(style->columnFill());
- return 0;
+ return nullptr;
case CSSPropertyWebkitColumnGap:
if (style->hasNormalColumnGap())
return cssValuePool().createIdentifierValue(CSSValueNormal);
return zoomAdjustedPixelValue(style->columnGap(), *style);
- case CSSPropertyWebkitColumnProgression:
- return cssValuePool().createValue(style->columnProgression());
case CSSPropertyWebkitColumnRuleColor:
return m_allowVisitedStyle ? cssValuePool().createColorValue(style->visitedDependentColor(CSSPropertyOutlineColor).rgb()) : currentColorOrValidColor(*style, style->columnRuleColor());
case CSSPropertyWebkitColumnRuleStyle:
@@ -1943,14 +1863,8 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return zoomAdjustedPixelValue(style->columnWidth(), *style);
case CSSPropertyTabSize:
return cssValuePool().createValue(style->tabSize(), CSSPrimitiveValue::CSS_NUMBER);
- case CSSPropertyWebkitRegionBreakAfter:
- return cssValuePool().createValue(style->regionBreakAfter());
- case CSSPropertyWebkitRegionBreakBefore:
- return cssValuePool().createValue(style->regionBreakBefore());
- case CSSPropertyWebkitRegionBreakInside:
- return cssValuePool().createValue(style->regionBreakInside());
case CSSPropertyCursor: {
- RefPtr<CSSValueList> list;
+ RefPtrWillBeRawPtr<CSSValueList> list = nullptr;
CursorList* cursors = style->cursors();
if (cursors && cursors->size() > 0) {
list = CSSValueList::createCommaSeparated();
@@ -1958,7 +1872,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (StyleImage* image = cursors->at(i).image())
list->append(image->cssValue());
}
- RefPtr<CSSValue> value = cssValuePool().createValue(style->cursor());
+ RefPtrWillBeRawPtr<CSSValue> value = cssValuePool().createValue(style->cursor());
if (list) {
list->append(value.release());
return list.release();
@@ -1974,19 +1888,22 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyAlignContent:
return cssValuePool().createValue(style->alignContent());
case CSSPropertyAlignItems:
- return cssValuePool().createValue(style->alignItems());
- case CSSPropertyAlignSelf:
- if (style->alignSelf() == AlignAuto) {
+ return valueForItemPositionWithOverflowAlignment(style->alignItems(), style->alignItemsOverflowAlignment());
+ case CSSPropertyAlignSelf: {
+ ItemPosition alignSelf = style->alignSelf();
+ if (alignSelf == ItemPositionAuto) {
Node* parent = styledNode->parentNode();
if (parent && parent->computedStyle())
- return cssValuePool().createValue(parent->computedStyle()->alignItems());
- return cssValuePool().createValue(AlignStretch);
+ alignSelf = parent->computedStyle()->alignItems();
+ else
+ alignSelf = ItemPositionStretch;
}
- return cssValuePool().createValue(style->alignSelf());
+ return valueForItemPositionWithOverflowAlignment(alignSelf, style->alignSelfOverflowAlignment());
+ }
case CSSPropertyFlex:
return valuesForShorthandProperty(flexShorthand());
case CSSPropertyFlexBasis:
- return cssValuePool().createValue(style->flexBasis());
+ return zoomAdjustedPixelValueForLength(style->flexBasis(), *style);
case CSSPropertyFlexDirection:
return cssValuePool().createValue(style->flexDirection());
case CSSPropertyFlexFlow:
@@ -2006,17 +1923,17 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createIdentifierValue(CSSValueNone);
return cssValuePool().createValue(style->floating());
case CSSPropertyFont: {
- RefPtr<CSSFontValue> computedFont = CSSFontValue::create();
+ RefPtrWillBeRawPtr<CSSFontValue> computedFont = CSSFontValue::create();
computedFont->style = valueForFontStyle(*style);
computedFont->variant = valueForFontVariant(*style);
computedFont->weight = valueForFontWeight(*style);
computedFont->size = valueForFontSize(*style);
- computedFont->lineHeight = valueForLineHeight(*style, m_node->document().renderView());
+ computedFont->lineHeight = valueForLineHeight(*style);
computedFont->family = valueForFontFamily(*style);
return computedFont.release();
}
case CSSPropertyFontFamily: {
- RefPtr<CSSValueList> fontFamilyList = valueForFontFamily(*style);
+ RefPtrWillBeRawPtr<CSSValueList> fontFamilyList = valueForFontFamily(*style);
// If there's only a single family, return that as a CSSPrimitiveValue.
// NOTE: Gecko always returns this as a comma-separated CSSPrimitiveValue string.
if (fontFamilyList->length() == 1)
@@ -2035,10 +1952,10 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
const FontFeatureSettings* featureSettings = style->fontDescription().featureSettings();
if (!featureSettings || !featureSettings->size())
return cssValuePool().createIdentifierValue(CSSValueNormal);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (unsigned i = 0; i < featureSettings->size(); ++i) {
const FontFeature& feature = featureSettings->at(i);
- RefPtr<CSSFontFeatureValue> featureValue = CSSFontFeatureValue::create(feature.tag(), feature.value());
+ RefPtrWillBeRawPtr<CSSFontFeatureValue> featureValue = CSSFontFeatureValue::create(feature.tag(), feature.value());
list->append(featureValue.release());
}
return list.release();
@@ -2052,14 +1969,14 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
// depending on the size of the explicit grid or the number of implicit tracks added to the grid. See
// http://lists.w3.org/Archives/Public/www-style/2013Nov/0014.html
case CSSPropertyGridAutoColumns:
- return specifiedValueForGridTrackSize(style->gridAutoColumns(), *style, m_node->document().renderView());
+ return specifiedValueForGridTrackSize(style->gridAutoColumns(), *style);
case CSSPropertyGridAutoRows:
- return specifiedValueForGridTrackSize(style->gridAutoRows(), *style, m_node->document().renderView());
+ return specifiedValueForGridTrackSize(style->gridAutoRows(), *style);
- case CSSPropertyGridDefinitionColumns:
- return valueForGridTrackList(ForColumns, renderer, *style, m_node->document().renderView());
- case CSSPropertyGridDefinitionRows:
- return valueForGridTrackList(ForRows, renderer, *style, m_node->document().renderView());
+ case CSSPropertyGridTemplateColumns:
+ return valueForGridTrackList(ForColumns, renderer, *style);
+ case CSSPropertyGridTemplateRows:
+ return valueForGridTrackList(ForRows, renderer, *style);
case CSSPropertyGridColumnStart:
return valueForGridPosition(style->gridColumnStart());
@@ -2075,14 +1992,17 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return valuesForGridShorthand(gridRowShorthand());
case CSSPropertyGridArea:
return valuesForGridShorthand(gridAreaShorthand());
-
case CSSPropertyGridTemplate:
+ return valuesForGridShorthand(gridTemplateShorthand());
+ case CSSPropertyGrid:
+ return valuesForGridShorthand(gridShorthand());
+ case CSSPropertyGridTemplateAreas:
if (!style->namedGridAreaRowCount()) {
ASSERT(!style->namedGridAreaColumnCount());
return cssValuePool().createIdentifierValue(CSSValueNone);
}
- return CSSGridTemplateValue::create(style->namedGridArea(), style->namedGridAreaRowCount(), style->namedGridAreaColumnCount());
+ return CSSGridTemplateAreasValue::create(style->namedGridArea(), style->namedGridAreaRowCount(), style->namedGridAreaColumnCount());
case CSSPropertyHeight:
if (renderer) {
@@ -2109,8 +2029,10 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return CSSPrimitiveValue::create(style->imageRendering());
case CSSPropertyIsolation:
return cssValuePool().createValue(style->isolation());
+ case CSSPropertyJustifySelf:
+ return valueForItemPositionWithOverflowAlignment(style->justifySelf(), style->justifySelfOverflowAlignment());
case CSSPropertyLeft:
- return valueForPositionOffset(*style, CSSPropertyLeft, renderer, m_node->document().renderView());
+ return valueForPositionOffset(*style, CSSPropertyLeft, renderer);
case CSSPropertyLetterSpacing:
if (!style->letterSpacing())
return cssValuePool().createIdentifierValue(CSSValueNormal);
@@ -2120,7 +2042,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createIdentifierValue(CSSValueNone);
return cssValuePool().createValue(style->lineClamp().value(), style->lineClamp().isPercentage() ? CSSPrimitiveValue::CSS_PERCENTAGE : CSSPrimitiveValue::CSS_NUMBER);
case CSSPropertyLineHeight:
- return valueForLineHeight(*style, m_node->document().renderView());
+ return valueForLineHeight(*style);
case CSSPropertyListStyleImage:
if (style->listStyleImage())
return style->listStyleImage()->cssValue();
@@ -2144,13 +2066,13 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (marginRight.isFixed() || !renderer || !renderer->isBox())
return zoomAdjustedPixelValueForLength(marginRight, *style);
float value;
- if (marginRight.isPercent() || marginRight.isViewportPercentage()) {
+ if (marginRight.isPercent()) {
// RenderBox gives a marginRight() that is the distance between the right-edge of the child box
// and the right-edge of the containing box, when display == BLOCK. Let's calculate the absolute
// value of the specified margin-right % instead of relying on RenderBox's marginRight() value.
- value = minimumValueForLength(marginRight, toRenderBox(renderer)->containingBlockLogicalWidthForContent(), m_node->document().renderView());
+ value = minimumValueForLength(marginRight, toRenderBox(renderer)->containingBlockLogicalWidthForContent()).toFloat();
} else {
- value = toRenderBox(renderer)->marginRight();
+ value = toRenderBox(renderer)->marginRight().toFloat();
}
return zoomAdjustedPixelValue(value, *style);
}
@@ -2254,15 +2176,17 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
EPageBreak pageBreak = style->pageBreakInside();
ASSERT(pageBreak != PBALWAYS);
if (pageBreak == PBALWAYS)
- return 0;
+ return nullptr;
return cssValuePool().createValue(style->pageBreakInside());
}
case CSSPropertyPosition:
return cssValuePool().createValue(style->position());
case CSSPropertyRight:
- return valueForPositionOffset(*style, CSSPropertyRight, renderer, m_node->document().renderView());
+ return valueForPositionOffset(*style, CSSPropertyRight, renderer);
case CSSPropertyWebkitRubyPosition:
return cssValuePool().createValue(style->rubyPosition());
+ case CSSPropertyScrollBehavior:
+ return cssValuePool().createValue(style->scrollBehavior());
case CSSPropertyTableLayout:
return cssValuePool().createValue(style->tableLayout());
case CSSPropertyTextAlign:
@@ -2270,7 +2194,9 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyTextAlignLast:
return cssValuePool().createValue(style->textAlignLast());
case CSSPropertyTextDecoration:
- return valuesForShorthandProperty(textDecorationShorthand());
+ if (RuntimeEnabledFeatures::css3TextDecorationsEnabled())
+ return valuesForShorthandProperty(textDecorationShorthand());
+ // Fall through.
case CSSPropertyTextDecorationLine:
return renderTextDecorationFlagsToCSSValue(style->textDecoration());
case CSSPropertyTextDecorationStyle:
@@ -2303,18 +2229,25 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case TextEmphasisMarkDoubleCircle:
case TextEmphasisMarkTriangle:
case TextEmphasisMarkSesame: {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
list->append(cssValuePool().createValue(style->textEmphasisFill()));
list->append(cssValuePool().createValue(style->textEmphasisMark()));
return list.release();
}
}
case CSSPropertyTextIndent: {
- RefPtr<CSSValue> textIndent = zoomAdjustedPixelValueForLength(style->textIndent(), *style);
- if (RuntimeEnabledFeatures::css3TextEnabled() && style->textIndentLine() == TextIndentEachLine) {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ // If RuntimeEnabledFeatures::css3TextEnabled() returns false or text-indent has only one value(<length> | <percentage>),
+ // getPropertyCSSValue() returns CSSValue.
+ // If RuntimeEnabledFeatures::css3TextEnabled() returns true and text-indent has each-line or hanging,
+ // getPropertyCSSValue() returns CSSValueList.
+ RefPtrWillBeRawPtr<CSSValue> textIndent = zoomAdjustedPixelValueForLength(style->textIndent(), *style);
+ if (RuntimeEnabledFeatures::css3TextEnabled() && (style->textIndentLine() == TextIndentEachLine || style->textIndentType() == TextIndentHanging)) {
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
list->append(textIndent.release());
- list->append(cssValuePool().createIdentifierValue(CSSValueEachLine));
+ if (style->textIndentLine() == TextIndentEachLine)
+ list->append(cssValuePool().createIdentifierValue(CSSValueEachLine));
+ if (style->textIndentType() == TextIndentHanging)
+ list->append(cssValuePool().createIdentifierValue(CSSValueHanging));
return list.release();
}
return textIndent.release();
@@ -2322,7 +2255,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyTextShadow:
return valueForShadowList(style->textShadow(), *style, false);
case CSSPropertyTextRendering:
- return cssValuePool().createValue(style->fontDescription().textRenderingMode());
+ return cssValuePool().createValue(style->fontDescription().textRendering());
case CSSPropertyTextOverflow:
if (style->textOverflow())
return cssValuePool().createIdentifierValue(CSSValueEllipsis);
@@ -2336,7 +2269,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyTextTransform:
return cssValuePool().createValue(style->textTransform());
case CSSPropertyTop:
- return valueForPositionOffset(*style, CSSPropertyTop, renderer, m_node->document().renderView());
+ return valueForPositionOffset(*style, CSSPropertyTop, renderer);
case CSSPropertyTouchAction:
return touchActionFlagsToCSSValue(style->touchAction());
case CSSPropertyTouchActionDelay:
@@ -2364,10 +2297,10 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case BASELINE_MIDDLE:
return cssValuePool().createIdentifierValue(CSSValueWebkitBaselineMiddle);
case LENGTH:
- return cssValuePool().createValue(style->verticalAlignLength());
+ return zoomAdjustedPixelValueForLength(style->verticalAlignLength(), *style);
}
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
case CSSPropertyVisibility:
return cssValuePool().createValue(style->visibility());
case CSSPropertyWhiteSpace:
@@ -2385,6 +2318,8 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return zoomAdjustedPixelValue(sizingBox(renderer).width(), *style);
}
return zoomAdjustedPixelValueForLength(style->width(), *style);
+ case CSSPropertyWillChange:
+ return valueForWillChange(style->willChangeProperties(), style->willChangeContents(), style->willChangeScrollPosition());
case CSSPropertyWordBreak:
return cssValuePool().createValue(style->wordBreak());
case CSSPropertyWordSpacing:
@@ -2399,21 +2334,24 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return cssValuePool().createValue(style->fontDescription().kerning());
case CSSPropertyWebkitFontSmoothing:
return cssValuePool().createValue(style->fontDescription().fontSmoothing());
- case CSSPropertyWebkitFontVariantLigatures: {
+ case CSSPropertyFontVariantLigatures: {
FontDescription::LigaturesState commonLigaturesState = style->fontDescription().commonLigaturesState();
FontDescription::LigaturesState discretionaryLigaturesState = style->fontDescription().discretionaryLigaturesState();
FontDescription::LigaturesState historicalLigaturesState = style->fontDescription().historicalLigaturesState();
+ FontDescription::LigaturesState contextualLigaturesState = style->fontDescription().contextualLigaturesState();
if (commonLigaturesState == FontDescription::NormalLigaturesState && discretionaryLigaturesState == FontDescription::NormalLigaturesState
- && historicalLigaturesState == FontDescription::NormalLigaturesState)
+ && historicalLigaturesState == FontDescription::NormalLigaturesState && contextualLigaturesState == FontDescription::NormalLigaturesState)
return cssValuePool().createIdentifierValue(CSSValueNormal);
- RefPtr<CSSValueList> valueList = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> valueList = CSSValueList::createSpaceSeparated();
if (commonLigaturesState != FontDescription::NormalLigaturesState)
valueList->append(cssValuePool().createIdentifierValue(commonLigaturesState == FontDescription::DisabledLigaturesState ? CSSValueNoCommonLigatures : CSSValueCommonLigatures));
if (discretionaryLigaturesState != FontDescription::NormalLigaturesState)
valueList->append(cssValuePool().createIdentifierValue(discretionaryLigaturesState == FontDescription::DisabledLigaturesState ? CSSValueNoDiscretionaryLigatures : CSSValueDiscretionaryLigatures));
if (historicalLigaturesState != FontDescription::NormalLigaturesState)
valueList->append(cssValuePool().createIdentifierValue(historicalLigaturesState == FontDescription::DisabledLigaturesState ? CSSValueNoHistoricalLigatures : CSSValueHistoricalLigatures));
+ if (contextualLigaturesState != FontDescription::NormalLigaturesState)
+ valueList->append(cssValuePool().createIdentifierValue(contextualLigaturesState == FontDescription::DisabledLigaturesState ? CSSValueNoContextual : CSSValueContextual));
return valueList;
}
case CSSPropertyZIndex:
@@ -2435,13 +2373,14 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyAnimationDirection:
ASSERT(RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled());
case CSSPropertyWebkitAnimationDirection: {
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- const CSSAnimationDataList* t = style->animations();
- if (t) {
- for (size_t i = 0; i < t->size(); ++i)
- list->append(valueForAnimationDirection(t->animation(i)->direction()));
- } else
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ const CSSAnimationData* animationData = style->animations();
+ if (animationData) {
+ for (size_t i = 0; i < animationData->directionList().size(); ++i)
+ list->append(valueForAnimationDirection(animationData->directionList()[i]));
+ } else {
list->append(cssValuePool().createIdentifierValue(CSSValueNormal));
+ }
return list.release();
}
case CSSPropertyAnimationDuration:
@@ -2451,59 +2390,53 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyAnimationFillMode:
ASSERT(RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled());
case CSSPropertyWebkitAnimationFillMode: {
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- const CSSAnimationDataList* t = style->animations();
- if (t) {
- for (size_t i = 0; i < t->size(); ++i)
- list->append(valueForAnimationFillMode(t->animation(i)->fillMode()));
- } else
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ const CSSAnimationData* animationData = style->animations();
+ if (animationData) {
+ for (size_t i = 0; i < animationData->fillModeList().size(); ++i)
+ list->append(valueForAnimationFillMode(animationData->fillModeList()[i]));
+ } else {
list->append(cssValuePool().createIdentifierValue(CSSValueNone));
+ }
return list.release();
}
case CSSPropertyAnimationIterationCount:
ASSERT(RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled());
case CSSPropertyWebkitAnimationIterationCount: {
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- const CSSAnimationDataList* t = style->animations();
- if (t) {
- for (size_t i = 0; i < t->size(); ++i) {
- double iterationCount = t->animation(i)->iterationCount();
- if (iterationCount == CSSAnimationData::IterationCountInfinite)
- list->append(cssValuePool().createIdentifierValue(CSSValueInfinite));
- else
- list->append(cssValuePool().createValue(iterationCount, CSSPrimitiveValue::CSS_NUMBER));
- }
- } else
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationIterationCount(), CSSPrimitiveValue::CSS_NUMBER));
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ const CSSAnimationData* animationData = style->animations();
+ if (animationData) {
+ for (size_t i = 0; i < animationData->iterationCountList().size(); ++i)
+ list->append(valueForAnimationIterationCount(animationData->iterationCountList()[i]));
+ } else {
+ list->append(cssValuePool().createValue(CSSAnimationData::initialIterationCount(), CSSPrimitiveValue::CSS_NUMBER));
+ }
return list.release();
}
case CSSPropertyAnimationName:
ASSERT(RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled());
case CSSPropertyWebkitAnimationName: {
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- const CSSAnimationDataList* t = style->animations();
- if (t) {
- for (size_t i = 0; i < t->size(); ++i)
- list->append(cssValuePool().createValue(t->animation(i)->name(), CSSPrimitiveValue::CSS_STRING));
- } else
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ const CSSAnimationData* animationData = style->animations();
+ if (animationData) {
+ for (size_t i = 0; i < animationData->nameList().size(); ++i)
+ list->append(cssValuePool().createValue(animationData->nameList()[i], CSSPrimitiveValue::CSS_STRING));
+ } else {
list->append(cssValuePool().createIdentifierValue(CSSValueNone));
+ }
return list.release();
}
case CSSPropertyAnimationPlayState:
ASSERT(RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled());
case CSSPropertyWebkitAnimationPlayState: {
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- const CSSAnimationDataList* t = style->animations();
- if (t) {
- for (size_t i = 0; i < t->size(); ++i) {
- int prop = t->animation(i)->playState();
- if (prop == AnimPlayStatePlaying)
- list->append(cssValuePool().createIdentifierValue(CSSValueRunning));
- else
- list->append(cssValuePool().createIdentifierValue(CSSValuePaused));
- }
- } else
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ const CSSAnimationData* animationData = style->animations();
+ if (animationData) {
+ for (size_t i = 0; i < animationData->playStateList().size(); ++i)
+ list->append(valueForAnimationPlayState(animationData->playStateList()[i]));
+ } else {
list->append(cssValuePool().createIdentifierValue(CSSValueRunning));
+ }
return list.release();
}
case CSSPropertyAnimationTimingFunction:
@@ -2512,40 +2445,33 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return valueForAnimationTimingFunction(style->animations());
case CSSPropertyAnimation:
case CSSPropertyWebkitAnimation: {
- const CSSAnimationDataList* animations = style->animations();
- if (animations) {
- RefPtr<CSSValueList> animationsList = CSSValueList::createCommaSeparated();
- for (size_t i = 0; i < animations->size(); ++i) {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- const CSSAnimationData* animation = animations->animation(i);
- list->append(cssValuePool().createValue(animation->name(), CSSPrimitiveValue::CSS_STRING));
- list->append(cssValuePool().createValue(animation->duration(), CSSPrimitiveValue::CSS_S));
- list->append(createTimingFunctionValue(animation->timingFunction()));
- list->append(cssValuePool().createValue(animation->delay(), CSSPrimitiveValue::CSS_S));
- if (animation->iterationCount() == CSSAnimationData::IterationCountInfinite)
- list->append(cssValuePool().createIdentifierValue(CSSValueInfinite));
- else
- list->append(cssValuePool().createValue(animation->iterationCount(), CSSPrimitiveValue::CSS_NUMBER));
- list->append(valueForAnimationDirection(animation->direction()));
- list->append(valueForAnimationFillMode(animation->fillMode()));
- if (animation->playState() == AnimPlayStatePaused)
- list->append(cssValuePool().createIdentifierValue(CSSValuePaused));
- else
- list->append(cssValuePool().createIdentifierValue(CSSValueRunning));
+ const CSSAnimationData* animationData = style->animations();
+ if (animationData) {
+ RefPtrWillBeRawPtr<CSSValueList> animationsList = CSSValueList::createCommaSeparated();
+ for (size_t i = 0; i < animationData->nameList().size(); ++i) {
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ list->append(cssValuePool().createValue(animationData->nameList()[i], CSSPrimitiveValue::CSS_STRING));
+ list->append(cssValuePool().createValue(CSSTimingData::getRepeated(animationData->durationList(), i), CSSPrimitiveValue::CSS_S));
+ list->append(createTimingFunctionValue(CSSTimingData::getRepeated(animationData->timingFunctionList(), i).get()));
+ list->append(cssValuePool().createValue(CSSTimingData::getRepeated(animationData->delayList(), i), CSSPrimitiveValue::CSS_S));
+ list->append(valueForAnimationIterationCount(CSSTimingData::getRepeated(animationData->iterationCountList(), i)));
+ list->append(valueForAnimationDirection(CSSTimingData::getRepeated(animationData->directionList(), i)));
+ list->append(valueForAnimationFillMode(CSSTimingData::getRepeated(animationData->fillModeList(), i)));
+ list->append(valueForAnimationPlayState(CSSTimingData::getRepeated(animationData->playStateList(), i)));
animationsList->append(list);
}
return animationsList.release();
}
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
// animation-name default value.
list->append(cssValuePool().createIdentifierValue(CSSValueNone));
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationDuration(), CSSPrimitiveValue::CSS_S));
- list->append(createTimingFunctionValue(CSSAnimationData::initialAnimationTimingFunction().get()));
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationDelay(), CSSPrimitiveValue::CSS_S));
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationIterationCount(), CSSPrimitiveValue::CSS_NUMBER));
- list->append(valueForAnimationDirection(CSSAnimationData::initialAnimationDirection()));
- list->append(valueForAnimationFillMode(CSSAnimationData::initialAnimationFillMode()));
+ list->append(cssValuePool().createValue(CSSAnimationData::initialDuration(), CSSPrimitiveValue::CSS_S));
+ list->append(createTimingFunctionValue(CSSAnimationData::initialTimingFunction().get()));
+ list->append(cssValuePool().createValue(CSSAnimationData::initialDelay(), CSSPrimitiveValue::CSS_S));
+ list->append(cssValuePool().createValue(CSSAnimationData::initialIterationCount(), CSSPrimitiveValue::CSS_NUMBER));
+ list->append(valueForAnimationDirection(CSSAnimationData::initialDirection()));
+ list->append(valueForAnimationFillMode(CSSAnimationData::initialFillMode()));
// Initial animation-play-state.
list->append(cssValuePool().createIdentifierValue(CSSValueRunning));
return list.release();
@@ -2556,6 +2482,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!style->hasAspectRatio())
return cssValuePool().createIdentifierValue(CSSValueNone);
return CSSAspectRatioValue::create(style->aspectRatioNumerator(), style->aspectRatioDenominator());
+ case CSSPropertyBackfaceVisibility:
case CSSPropertyWebkitBackfaceVisibility:
return cssValuePool().createIdentifierValue((style->backfaceVisibility() == BackfaceVisibilityHidden) ? CSSValueHidden : CSSValueVisible);
case CSSPropertyWebkitBorderImage:
@@ -2591,20 +2518,21 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyWebkitMarginTopCollapse:
case CSSPropertyWebkitMarginBeforeCollapse:
return cssValuePool().createValue(style->marginBeforeCollapse());
+ case CSSPropertyPerspective:
case CSSPropertyWebkitPerspective:
if (!style->hasPerspective())
return cssValuePool().createIdentifierValue(CSSValueNone);
return zoomAdjustedPixelValue(style->perspective(), *style);
+ case CSSPropertyPerspectiveOrigin:
case CSSPropertyWebkitPerspectiveOrigin: {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (renderer) {
LayoutRect box;
if (renderer->isBox())
box = toRenderBox(renderer)->borderBoxRect();
- RenderView* renderView = m_node->document().renderView();
- list->append(zoomAdjustedPixelValue(minimumValueForLength(style->perspectiveOriginX(), box.width(), renderView), *style));
- list->append(zoomAdjustedPixelValue(minimumValueForLength(style->perspectiveOriginY(), box.height(), renderView), *style));
+ list->append(zoomAdjustedPixelValue(minimumValueForLength(style->perspectiveOriginX(), box.width()), *style));
+ list->append(zoomAdjustedPixelValue(minimumValueForLength(style->perspectiveOriginY(), box.height()), *style));
}
else {
list->append(zoomAdjustedPixelValueForLength(style->perspectiveOriginX(), *style));
@@ -2632,7 +2560,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyClip: {
if (!style->hasClip())
return cssValuePool().createIdentifierValue(CSSValueAuto);
- RefPtr<Rect> rect = Rect::create();
+ RefPtrWillBeRawPtr<Rect> rect = Rect::create();
rect->setTop(zoomAdjustedPixelValue(style->clip().top().value(), *style));
rect->setRight(zoomAdjustedPixelValue(style->clip().right().value(), *style));
rect->setBottom(zoomAdjustedPixelValue(style->clip().bottom().value(), *style));
@@ -2641,18 +2569,19 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
}
case CSSPropertySpeak:
return cssValuePool().createValue(style->speak());
+ case CSSPropertyTransform:
case CSSPropertyWebkitTransform:
return computedTransform(renderer, *style);
+ case CSSPropertyTransformOrigin:
case CSSPropertyWebkitTransformOrigin: {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
if (renderer) {
LayoutRect box;
if (renderer->isBox())
box = toRenderBox(renderer)->borderBoxRect();
- RenderView* renderView = m_node->document().renderView();
- list->append(zoomAdjustedPixelValue(minimumValueForLength(style->transformOriginX(), box.width(), renderView), *style));
- list->append(zoomAdjustedPixelValue(minimumValueForLength(style->transformOriginY(), box.height(), renderView), *style));
+ list->append(zoomAdjustedPixelValue(minimumValueForLength(style->transformOriginX(), box.width()), *style));
+ list->append(zoomAdjustedPixelValue(minimumValueForLength(style->transformOriginY(), box.height()), *style));
if (style->transformOriginZ() != 0)
list->append(zoomAdjustedPixelValue(style->transformOriginZ(), *style));
} else {
@@ -2663,6 +2592,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
}
return list.release();
}
+ case CSSPropertyTransformStyle:
case CSSPropertyWebkitTransformStyle:
return cssValuePool().createIdentifierValue((style->transformStyle3D() == TransformStyle3DPreserve3D) ? CSSValuePreserve3d : CSSValueFlat);
case CSSPropertyTransitionDelay:
@@ -2679,39 +2609,30 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return valueForAnimationTimingFunction(style->transitions());
case CSSPropertyTransition:
case CSSPropertyWebkitTransition: {
- const CSSAnimationDataList* animList = style->transitions();
- if (animList) {
- RefPtr<CSSValueList> transitionsList = CSSValueList::createCommaSeparated();
- for (size_t i = 0; i < animList->size(); ++i) {
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- const CSSAnimationData* animation = animList->animation(i);
- list->append(createTransitionPropertyValue(animation));
- list->append(cssValuePool().createValue(animation->duration(), CSSPrimitiveValue::CSS_S));
- list->append(createTimingFunctionValue(animation->timingFunction()));
- list->append(cssValuePool().createValue(animation->delay(), CSSPrimitiveValue::CSS_S));
+ const CSSTransitionData* transitionData = style->transitions();
+ if (transitionData) {
+ RefPtrWillBeRawPtr<CSSValueList> transitionsList = CSSValueList::createCommaSeparated();
+ for (size_t i = 0; i < transitionData->propertyList().size(); ++i) {
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ list->append(createTransitionPropertyValue(transitionData->propertyList()[i]));
+ list->append(cssValuePool().createValue(CSSTimingData::getRepeated(transitionData->durationList(), i), CSSPrimitiveValue::CSS_S));
+ list->append(createTimingFunctionValue(CSSTimingData::getRepeated(transitionData->timingFunctionList(), i).get()));
+ list->append(cssValuePool().createValue(CSSTimingData::getRepeated(transitionData->delayList(), i), CSSPrimitiveValue::CSS_S));
transitionsList->append(list);
}
return transitionsList.release();
}
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
// transition-property default value.
list->append(cssValuePool().createIdentifierValue(CSSValueAll));
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationDuration(), CSSPrimitiveValue::CSS_S));
- list->append(createTimingFunctionValue(CSSAnimationData::initialAnimationTimingFunction().get()));
- list->append(cssValuePool().createValue(CSSAnimationData::initialAnimationDelay(), CSSPrimitiveValue::CSS_S));
+ list->append(cssValuePool().createValue(CSSTransitionData::initialDuration(), CSSPrimitiveValue::CSS_S));
+ list->append(createTimingFunctionValue(CSSTransitionData::initialTimingFunction().get()));
+ list->append(cssValuePool().createValue(CSSTransitionData::initialDelay(), CSSPrimitiveValue::CSS_S));
return list.release();
}
case CSSPropertyPointerEvents:
return cssValuePool().createValue(style->pointerEvents());
- case CSSPropertyWebkitLineGrid:
- if (style->lineGrid().isNull())
- return cssValuePool().createIdentifierValue(CSSValueNone);
- return cssValuePool().createValue(style->lineGrid(), CSSPrimitiveValue::CSS_STRING);
- case CSSPropertyWebkitLineSnap:
- return CSSPrimitiveValue::create(style->lineSnap());
- case CSSPropertyWebkitLineAlign:
- return CSSPrimitiveValue::create(style->lineAlign());
case CSSPropertyWebkitWritingMode:
return cssValuePool().createValue(style->writingMode());
case CSSPropertyWebkitTextCombine:
@@ -2734,50 +2655,14 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
return CSSPrimitiveValue::create(toReferenceClipPathOperation(operation)->url(), CSSPrimitiveValue::CSS_URI);
}
return cssValuePool().createIdentifierValue(CSSValueNone);
- case CSSPropertyWebkitFlowInto:
- if (style->flowThread().isNull())
- return cssValuePool().createIdentifierValue(CSSValueNone);
- return cssValuePool().createValue(style->flowThread(), CSSPrimitiveValue::CSS_STRING);
- case CSSPropertyWebkitFlowFrom:
- if (!style->hasFlowFrom())
- return cssValuePool().createIdentifierValue(CSSValueNone);
- return cssValuePool().createValue(style->regionThread(), CSSPrimitiveValue::CSS_STRING);
- case CSSPropertyWebkitRegionFragment:
- return cssValuePool().createValue(style->regionFragment());
case CSSPropertyWebkitWrapFlow:
return cssValuePool().createValue(style->wrapFlow());
case CSSPropertyShapeMargin:
- return cssValuePool().createValue(style->shapeMargin());
- case CSSPropertyShapePadding:
- return cssValuePool().createValue(style->shapePadding());
+ return cssValuePool().createValue(style->shapeMargin(), *style);
case CSSPropertyShapeImageThreshold:
return cssValuePool().createValue(style->shapeImageThreshold(), CSSPrimitiveValue::CSS_NUMBER);
- case CSSPropertyShapeInside:
- if (!style->shapeInside())
- return cssValuePool().createIdentifierValue(CSSValueAuto);
- if (style->shapeInside()->type() == ShapeValue::Box)
- return cssValuePool().createValue(style->shapeInside()->layoutBox());
- if (style->shapeInside()->type() == ShapeValue::Outside)
- return cssValuePool().createIdentifierValue(CSSValueOutsideShape);
- if (style->shapeInside()->type() == ShapeValue::Image) {
- if (style->shapeInside()->image())
- return style->shapeInside()->image()->cssValue();
- return cssValuePool().createIdentifierValue(CSSValueNone);
- }
- ASSERT(style->shapeInside()->type() == ShapeValue::Shape);
- return valueForBasicShape(*style, style->shapeInside()->shape());
case CSSPropertyShapeOutside:
- if (!style->shapeOutside())
- return cssValuePool().createIdentifierValue(CSSValueAuto);
- if (style->shapeOutside()->type() == ShapeValue::Box)
- return cssValuePool().createValue(style->shapeOutside()->layoutBox());
- if (style->shapeOutside()->type() == ShapeValue::Image) {
- if (style->shapeOutside()->image())
- return style->shapeOutside()->image()->cssValue();
- return cssValuePool().createIdentifierValue(CSSValueNone);
- }
- ASSERT(style->shapeOutside()->type() == ShapeValue::Shape);
- return valueForBasicShape(*style, style->shapeOutside()->shape());
+ return valueForShape(*style, style->shapeOutside());
case CSSPropertyWebkitWrapThrough:
return cssValuePool().createValue(style->wrapThrough());
case CSSPropertyWebkitFilter:
@@ -2790,7 +2675,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
if (!layers->next())
return cssValuePool().createValue(layers->blendMode());
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
for (const FillLayer* currLayer = layers; currLayer; currLayer = currLayer->next())
list->append(cssValuePool().createValue(currLayer->blendMode()));
@@ -2799,12 +2684,12 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyBackground:
return valuesForBackgroundShorthand();
case CSSPropertyBorder: {
- RefPtr<CSSValue> value = getPropertyCSSValue(CSSPropertyBorderTop, DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(CSSPropertyBorderTop, DoNotUpdateLayout);
const CSSPropertyID properties[3] = { CSSPropertyBorderRight, CSSPropertyBorderBottom,
CSSPropertyBorderLeft };
for (size_t i = 0; i < WTF_ARRAY_LENGTH(properties); ++i) {
if (!compareCSSValuePtr<CSSValue>(value, getPropertyCSSValue(properties[i], DoNotUpdateLayout)))
- return 0;
+ return nullptr;
}
return value.release();
}
@@ -2844,7 +2729,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
break;
case CSSPropertyInternalCallback:
// This property is hidden from the web.
- return 0;
+ return nullptr;
/* Unimplemented CSS 3 properties (including CSS3 shorthand properties) */
case CSSPropertyWebkitTextEmphasis:
@@ -2936,7 +2821,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyInternalMarqueeSpeed:
case CSSPropertyInternalMarqueeStyle:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
case CSSPropertyBufferedRendering:
case CSSPropertyClipPath:
@@ -2951,7 +2836,6 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyStopOpacity:
case CSSPropertyColorInterpolation:
case CSSPropertyColorInterpolationFilters:
- case CSSPropertyColorProfile:
case CSSPropertyColorRendering:
case CSSPropertyFill:
case CSSPropertyFillOpacity:
@@ -2975,21 +2859,23 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(CSSPropert
case CSSPropertyDominantBaseline:
case CSSPropertyGlyphOrientationHorizontal:
case CSSPropertyGlyphOrientationVertical:
- case CSSPropertyKerning:
case CSSPropertyTextAnchor:
case CSSPropertyVectorEffect:
case CSSPropertyPaintOrder:
case CSSPropertyWritingMode:
return getSVGPropertyCSSValue(propertyID, DoNotUpdateLayout);
+
+ case CSSPropertyAll:
+ return nullptr;
}
logUnimplementedPropertyID(propertyID);
- return 0;
+ return nullptr;
}
String CSSComputedStyleDeclaration::getPropertyValue(CSSPropertyID propertyID) const
{
- RefPtr<CSSValue> value = getPropertyCSSValue(propertyID);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(propertyID);
if (value)
return value->cssText();
return "";
@@ -3029,37 +2915,37 @@ bool CSSComputedStyleDeclaration::cssPropertyMatches(CSSPropertyID propertyID, c
return true;
}
}
- RefPtr<CSSValue> value = getPropertyCSSValue(propertyID);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(propertyID);
return value && propertyValue && value->equals(*propertyValue);
}
-PassRefPtr<MutableStylePropertySet> CSSComputedStyleDeclaration::copyProperties() const
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> CSSComputedStyleDeclaration::copyProperties() const
{
return copyPropertiesInSet(computableProperties());
}
-PassRefPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForShorthandProperty(const StylePropertyShorthand& shorthand) const
+PassRefPtrWillBeRawPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForShorthandProperty(const StylePropertyShorthand& shorthand) const
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
for (size_t i = 0; i < shorthand.length(); ++i) {
- RefPtr<CSSValue> value = getPropertyCSSValue(shorthand.properties()[i], DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(shorthand.properties()[i], DoNotUpdateLayout);
list->append(value);
}
return list.release();
}
-PassRefPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForSidesShorthand(const StylePropertyShorthand& shorthand) const
+PassRefPtrWillBeRawPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForSidesShorthand(const StylePropertyShorthand& shorthand) const
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
// Assume the properties are in the usual order top, right, bottom, left.
- RefPtr<CSSValue> topValue = getPropertyCSSValue(shorthand.properties()[0], DoNotUpdateLayout);
- RefPtr<CSSValue> rightValue = getPropertyCSSValue(shorthand.properties()[1], DoNotUpdateLayout);
- RefPtr<CSSValue> bottomValue = getPropertyCSSValue(shorthand.properties()[2], DoNotUpdateLayout);
- RefPtr<CSSValue> leftValue = getPropertyCSSValue(shorthand.properties()[3], DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> topValue = getPropertyCSSValue(shorthand.properties()[0], DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> rightValue = getPropertyCSSValue(shorthand.properties()[1], DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> bottomValue = getPropertyCSSValue(shorthand.properties()[2], DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> leftValue = getPropertyCSSValue(shorthand.properties()[3], DoNotUpdateLayout);
// All 4 properties must be specified.
if (!topValue || !rightValue || !bottomValue || !leftValue)
- return 0;
+ return nullptr;
bool showLeft = !compareCSSValuePtr(rightValue, leftValue);
bool showBottom = !compareCSSValuePtr(topValue, bottomValue) || showLeft;
@@ -3076,22 +2962,22 @@ PassRefPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForSidesShorthand(co
return list.release();
}
-PassRefPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForGridShorthand(const StylePropertyShorthand& shorthand) const
+PassRefPtrWillBeRawPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForGridShorthand(const StylePropertyShorthand& shorthand) const
{
- RefPtr<CSSValueList> list = CSSValueList::createSlashSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSlashSeparated();
for (size_t i = 0; i < shorthand.length(); ++i) {
- RefPtr<CSSValue> value = getPropertyCSSValue(shorthand.properties()[i], DoNotUpdateLayout);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(shorthand.properties()[i], DoNotUpdateLayout);
list->append(value.release());
}
return list.release();
}
-PassRefPtr<MutableStylePropertySet> CSSComputedStyleDeclaration::copyPropertiesInSet(const Vector<CSSPropertyID>& properties) const
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> CSSComputedStyleDeclaration::copyPropertiesInSet(const Vector<CSSPropertyID>& properties) const
{
- Vector<CSSProperty, 256> list;
+ WillBeHeapVector<CSSProperty, 256> list;
list.reserveInitialCapacity(properties.size());
for (unsigned i = 0; i < properties.size(); ++i) {
- RefPtr<CSSValue> value = getPropertyCSSValue(properties[i]);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(properties[i]);
if (value)
list.append(CSSProperty(properties[i], value.release(), false));
}
@@ -3103,13 +2989,13 @@ CSSRule* CSSComputedStyleDeclaration::parentRule() const
return 0;
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(const String& propertyName)
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValue(const String& propertyName)
{
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
- return 0;
- RefPtr<CSSValue> value = getPropertyCSSValue(propertyID);
- return value ? value->cloneForCSSOM() : 0;
+ return nullptr;
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(propertyID);
+ return value ? value->cloneForCSSOM() : nullptr;
}
String CSSComputedStyleDeclaration::getPropertyValue(const String& propertyName)
@@ -3147,7 +3033,7 @@ String CSSComputedStyleDeclaration::removeProperty(const String& name, Exception
return String();
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValueInternal(CSSPropertyID propertyID)
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::getPropertyCSSValueInternal(CSSPropertyID propertyID)
{
return getPropertyCSSValue(propertyID);
}
@@ -3162,89 +3048,7 @@ void CSSComputedStyleDeclaration::setPropertyInternal(CSSPropertyID id, const St
exceptionState.throwDOMException(NoModificationAllowedError, "These styles are computed, and therefore the '" + getPropertyNameString(id) + "' property is read-only.");
}
-const HashMap<AtomicString, String>* CSSComputedStyleDeclaration::variableMap() const
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- Node* styledNode = this->styledNode();
- if (!styledNode)
- return 0;
- RefPtr<RenderStyle> style = styledNode->computedStyle(styledNode->isPseudoElement() ? NOPSEUDO : m_pseudoElementSpecifier);
- if (!style)
- return 0;
- return style->variables();
-}
-
-unsigned CSSComputedStyleDeclaration::variableCount() const
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- const HashMap<AtomicString, String>* variables = variableMap();
- if (!variables)
- return 0;
- return variables->size();
-}
-
-String CSSComputedStyleDeclaration::variableValue(const AtomicString& name) const
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- const HashMap<AtomicString, String>* variables = variableMap();
- if (!variables)
- return emptyString();
- HashMap<AtomicString, String>::const_iterator it = variables->find(name);
- if (it == variables->end())
- return emptyString();
- return it->value;
-}
-
-bool CSSComputedStyleDeclaration::setVariableValue(const AtomicString& name, const String&, ExceptionState& exceptionState)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- exceptionState.throwDOMException(NoModificationAllowedError, "These styles are computed, and therefore the '" + name + "' property is read-only.");
- return false;
-}
-
-bool CSSComputedStyleDeclaration::removeVariable(const AtomicString&)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- return false;
-}
-
-bool CSSComputedStyleDeclaration::clearVariables(ExceptionState& exceptionState)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- exceptionState.throwDOMException(NoModificationAllowedError, "These styles are computed, and therefore variables may not be cleared.");
- return false;
-}
-
-CSSComputedStyleDeclaration::ComputedCSSVariablesIterator::ComputedCSSVariablesIterator(const HashMap<AtomicString, String>* variables)
- : m_active(variables)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- if (m_active) {
- m_it = variables->begin();
- m_end = variables->end();
- }
-}
-
-void CSSComputedStyleDeclaration::ComputedCSSVariablesIterator::advance()
-{
- ASSERT(m_active);
- ++m_it;
- m_active = !atEnd();
-}
-
-AtomicString CSSComputedStyleDeclaration::ComputedCSSVariablesIterator::name() const
-{
- ASSERT(m_active);
- return m_it->key;
-}
-
-String CSSComputedStyleDeclaration::ComputedCSSVariablesIterator::value() const
-{
- ASSERT(m_active);
- return m_it->value;
-}
-
-PassRefPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForBackgroundShorthand() const
+PassRefPtrWillBeRawPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForBackgroundShorthand() const
{
static const CSSPropertyID propertiesBeforeSlashSeperator[5] = { CSSPropertyBackgroundColor, CSSPropertyBackgroundImage,
CSSPropertyBackgroundRepeat, CSSPropertyBackgroundAttachment,
@@ -3252,10 +3056,16 @@ PassRefPtr<CSSValueList> CSSComputedStyleDeclaration::valuesForBackgroundShortha
static const CSSPropertyID propertiesAfterSlashSeperator[3] = { CSSPropertyBackgroundSize, CSSPropertyBackgroundOrigin,
CSSPropertyBackgroundClip };
- RefPtr<CSSValueList> list = CSSValueList::createSlashSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSlashSeparated();
list->append(valuesForShorthandProperty(StylePropertyShorthand(CSSPropertyBackground, propertiesBeforeSlashSeperator, WTF_ARRAY_LENGTH(propertiesBeforeSlashSeperator))));
list->append(valuesForShorthandProperty(StylePropertyShorthand(CSSPropertyBackground, propertiesAfterSlashSeperator, WTF_ARRAY_LENGTH(propertiesAfterSlashSeperator))));
return list.release();
}
+void CSSComputedStyleDeclaration::trace(Visitor* visitor)
+{
+ visitor->trace(m_node);
+ CSSStyleDeclaration::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.h b/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.h
index a3ff8770319..d60072ab91a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSComputedStyleDeclaration.h
@@ -33,9 +33,6 @@ namespace WebCore {
class CSSPrimitiveValue;
class CSSValueList;
-class Color;
-class CustomFilterNumberParameter;
-class CustomFilterParameter;
class ExceptionState;
class MutableStylePropertySet;
class Node;
@@ -44,54 +41,41 @@ class RenderStyle;
class SVGPaint;
class ShadowData;
class ShadowList;
+class StyleColor;
class StylePropertySet;
class StylePropertyShorthand;
enum EUpdateLayout { DoNotUpdateLayout = false, UpdateLayout = true };
-class CSSComputedStyleDeclaration : public CSSStyleDeclaration {
-private:
- class ComputedCSSVariablesIterator : public CSSVariablesIterator {
- public:
- virtual ~ComputedCSSVariablesIterator() { }
- static PassRefPtr<ComputedCSSVariablesIterator> create(const HashMap<AtomicString, String>* variableMap) { return adoptRef(new ComputedCSSVariablesIterator(variableMap)); }
- private:
- explicit ComputedCSSVariablesIterator(const HashMap<AtomicString, String>* variableMap);
- virtual void advance() OVERRIDE;
- virtual bool atEnd() const OVERRIDE { return m_it == m_end; }
- virtual AtomicString name() const OVERRIDE;
- virtual String value() const OVERRIDE;
- bool m_active;
- typedef HashMap<AtomicString, String>::const_iterator VariablesMapIterator;
- VariablesMapIterator m_it;
- VariablesMapIterator m_end;
- };
-
+class CSSComputedStyleDeclaration FINAL : public CSSStyleDeclaration {
public:
- static PassRefPtr<CSSComputedStyleDeclaration> create(PassRefPtr<Node> node, bool allowVisitedStyle = false, const String& pseudoElementName = String())
+ static PassRefPtrWillBeRawPtr<CSSComputedStyleDeclaration> create(PassRefPtrWillBeRawPtr<Node> node, bool allowVisitedStyle = false, const String& pseudoElementName = String())
{
- return adoptRef(new CSSComputedStyleDeclaration(node, allowVisitedStyle, pseudoElementName));
+ return adoptRefWillBeNoop(new CSSComputedStyleDeclaration(node, allowVisitedStyle, pseudoElementName));
}
virtual ~CSSComputedStyleDeclaration();
+#if !ENABLE(OILPAN)
virtual void ref() OVERRIDE;
virtual void deref() OVERRIDE;
+#endif
- PassRefPtr<CSSValue> getPropertyCSSValue(CSSPropertyID) const;
String getPropertyValue(CSSPropertyID) const;
bool getPropertyPriority(CSSPropertyID) const;
- virtual PassRefPtr<MutableStylePropertySet> copyProperties() const OVERRIDE;
+ virtual PassRefPtrWillBeRawPtr<MutableStylePropertySet> copyProperties() const OVERRIDE;
- PassRefPtr<CSSValue> getPropertyCSSValue(CSSPropertyID, EUpdateLayout) const;
- PassRefPtr<CSSValue> getFontSizeCSSValuePreferringKeyword() const;
+ PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValue(CSSPropertyID, EUpdateLayout = UpdateLayout) const;
+ PassRefPtrWillBeRawPtr<CSSValue> getFontSizeCSSValuePreferringKeyword() const;
bool useFixedFontDefaultSize() const;
- PassRefPtr<CSSValue> getSVGPropertyCSSValue(CSSPropertyID, EUpdateLayout) const;
+ PassRefPtrWillBeRawPtr<CSSValue> getSVGPropertyCSSValue(CSSPropertyID, EUpdateLayout) const;
+
+ PassRefPtrWillBeRawPtr<MutableStylePropertySet> copyPropertiesInSet(const Vector<CSSPropertyID>&) const;
- PassRefPtr<MutableStylePropertySet> copyPropertiesInSet(const Vector<CSSPropertyID>&) const;
+ virtual void trace(Visitor*) OVERRIDE;
private:
- CSSComputedStyleDeclaration(PassRefPtr<Node>, bool allowVisitedStyle, const String&);
+ CSSComputedStyleDeclaration(PassRefPtrWillBeRawPtr<Node>, bool allowVisitedStyle, const String&);
// The styled node is either the node passed into getComputedStyle, or the
// PseudoElement for :before and :after if they exist.
@@ -101,49 +85,43 @@ private:
Node* styledNode() const;
// CSSOM functions. Don't make these public.
- virtual CSSRule* parentRule() const;
- virtual unsigned length() const;
- virtual String item(unsigned index) const;
+ virtual CSSRule* parentRule() const OVERRIDE;
+ virtual unsigned length() const OVERRIDE;
+ virtual String item(unsigned index) const OVERRIDE;
PassRefPtr<RenderStyle> computeRenderStyle(CSSPropertyID) const;
- virtual PassRefPtr<CSSValue> getPropertyCSSValue(const String& propertyName);
- virtual String getPropertyValue(const String& propertyName);
- virtual String getPropertyPriority(const String& propertyName);
- virtual String getPropertyShorthand(const String& propertyName);
- virtual bool isPropertyImplicit(const String& propertyName);
- virtual void setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState&);
- virtual String removeProperty(const String& propertyName, ExceptionState&);
- virtual String cssText() const;
- virtual void setCSSText(const String&, ExceptionState&);
- virtual PassRefPtr<CSSValue> getPropertyCSSValueInternal(CSSPropertyID);
- virtual String getPropertyValueInternal(CSSPropertyID);
- virtual void setPropertyInternal(CSSPropertyID, const String& value, bool important, ExceptionState&);
-
- const HashMap<AtomicString, String>* variableMap() const;
- virtual unsigned variableCount() const OVERRIDE;
- virtual String variableValue(const AtomicString& name) const OVERRIDE;
- virtual bool setVariableValue(const AtomicString& name, const String& value, ExceptionState&) OVERRIDE;
- virtual bool removeVariable(const AtomicString& name) OVERRIDE;
- virtual bool clearVariables(ExceptionState&) OVERRIDE;
- virtual PassRefPtr<CSSVariablesIterator> variablesIterator() const OVERRIDE { return ComputedCSSVariablesIterator::create(variableMap()); }
+ virtual PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValue(const String& propertyName) OVERRIDE;
+ virtual String getPropertyValue(const String& propertyName) OVERRIDE;
+ virtual String getPropertyPriority(const String& propertyName) OVERRIDE;
+ virtual String getPropertyShorthand(const String& propertyName) OVERRIDE;
+ virtual bool isPropertyImplicit(const String& propertyName) OVERRIDE;
+ virtual void setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState&) OVERRIDE;
+ virtual String removeProperty(const String& propertyName, ExceptionState&) OVERRIDE;
+ virtual String cssText() const OVERRIDE;
+ virtual void setCSSText(const String&, ExceptionState&) OVERRIDE;
+ virtual PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValueInternal(CSSPropertyID) OVERRIDE;
+ virtual String getPropertyValueInternal(CSSPropertyID) OVERRIDE;
+ virtual void setPropertyInternal(CSSPropertyID, const String& value, bool important, ExceptionState&) OVERRIDE;
virtual bool cssPropertyMatches(CSSPropertyID, const CSSValue*) const OVERRIDE;
- PassRefPtr<CSSValue> valueForShadowData(const ShadowData&, const RenderStyle&, bool useSpread) const;
- PassRefPtr<CSSValue> valueForShadowList(const ShadowList*, const RenderStyle&, bool useSpread) const;
- PassRefPtr<CSSPrimitiveValue> currentColorOrValidColor(const RenderStyle&, const Color&) const;
- PassRefPtr<SVGPaint> adjustSVGPaintForCurrentColor(PassRefPtr<SVGPaint>, RenderStyle&) const;
+ PassRefPtrWillBeRawPtr<CSSValue> valueForShadowData(const ShadowData&, const RenderStyle&, bool useSpread) const;
+ PassRefPtrWillBeRawPtr<CSSValue> valueForShadowList(const ShadowList*, const RenderStyle&, bool useSpread) const;
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> currentColorOrValidColor(const RenderStyle&, const StyleColor&) const;
+ PassRefPtrWillBeRawPtr<SVGPaint> adjustSVGPaintForCurrentColor(PassRefPtrWillBeRawPtr<SVGPaint>, RenderStyle&) const;
- PassRefPtr<CSSValue> valueForFilter(const RenderObject*, const RenderStyle&) const;
+ PassRefPtrWillBeRawPtr<CSSValue> valueForFilter(const RenderObject*, const RenderStyle&) const;
- PassRefPtr<CSSValueList> valuesForShorthandProperty(const StylePropertyShorthand&) const;
- PassRefPtr<CSSValueList> valuesForSidesShorthand(const StylePropertyShorthand&) const;
- PassRefPtr<CSSValueList> valuesForBackgroundShorthand() const;
- PassRefPtr<CSSValueList> valuesForGridShorthand(const StylePropertyShorthand&) const;
+ PassRefPtrWillBeRawPtr<CSSValueList> valuesForShorthandProperty(const StylePropertyShorthand&) const;
+ PassRefPtrWillBeRawPtr<CSSValueList> valuesForSidesShorthand(const StylePropertyShorthand&) const;
+ PassRefPtrWillBeRawPtr<CSSValueList> valuesForBackgroundShorthand() const;
+ PassRefPtrWillBeRawPtr<CSSValueList> valuesForGridShorthand(const StylePropertyShorthand&) const;
- RefPtr<Node> m_node;
+ RefPtrWillBeMember<Node> m_node;
PseudoId m_pseudoElementSpecifier;
bool m_allowVisitedStyle;
+#if !ENABLE(OILPAN)
unsigned m_refCount;
+#endif
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.cpp
index 801cbb66f99..daa45df9d05 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.cpp
@@ -167,7 +167,7 @@ void CSSCrossfadeValue::loadSubimages(ResourceFetcher* fetcher)
PassRefPtr<Image> CSSCrossfadeValue::image(RenderObject* renderer, const IntSize& size)
{
if (size.isEmpty())
- return 0;
+ return nullptr;
ResourceFetcher* fetcher = renderer->document().fetcher();
ImageResource* cachedFromImage = cachedImageForCSSValue(m_fromValue.get(), fetcher);
@@ -218,4 +218,12 @@ bool CSSCrossfadeValue::equals(const CSSCrossfadeValue& other) const
&& compareCSSValuePtr(m_percentageValue, other.m_percentageValue);
}
+void CSSCrossfadeValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_fromValue);
+ visitor->trace(m_toValue);
+ visitor->trace(m_percentageValue);
+ CSSImageGeneratorValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.h b/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.h
index ffb46aed9f1..617a5d25ff1 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCrossfadeValue.h
@@ -43,9 +43,9 @@ class Document;
class CSSCrossfadeValue : public CSSImageGeneratorValue {
friend class CrossfadeSubimageObserverProxy;
public:
- static PassRefPtr<CSSCrossfadeValue> create(PassRefPtr<CSSValue> fromValue, PassRefPtr<CSSValue> toValue)
+ static PassRefPtrWillBeRawPtr<CSSCrossfadeValue> create(PassRefPtrWillBeRawPtr<CSSValue> fromValue, PassRefPtrWillBeRawPtr<CSSValue> toValue)
{
- return adoptRef(new CSSCrossfadeValue(fromValue, toValue));
+ return adoptRefWillBeNoop(new CSSCrossfadeValue(fromValue, toValue));
}
~CSSCrossfadeValue();
@@ -61,14 +61,16 @@ public:
void loadSubimages(ResourceFetcher*);
- void setPercentage(PassRefPtr<CSSPrimitiveValue> percentageValue) { m_percentageValue = percentageValue; }
+ void setPercentage(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> percentageValue) { m_percentageValue = percentageValue; }
bool hasFailedOrCanceledSubresources() const;
bool equals(const CSSCrossfadeValue&) const;
+ void traceAfterDispatch(Visitor*);
+
private:
- CSSCrossfadeValue(PassRefPtr<CSSValue> fromValue, PassRefPtr<CSSValue> toValue)
+ CSSCrossfadeValue(PassRefPtrWillBeRawPtr<CSSValue> fromValue, PassRefPtrWillBeRawPtr<CSSValue> toValue)
: CSSImageGeneratorValue(CrossfadeClass)
, m_fromValue(fromValue)
, m_toValue(toValue)
@@ -76,7 +78,7 @@ private:
, m_cachedToImage(0)
, m_crossfadeSubimageObserver(this) { }
- class CrossfadeSubimageObserverProxy : public ImageResourceClient {
+ class CrossfadeSubimageObserverProxy FINAL : public ImageResourceClient {
public:
CrossfadeSubimageObserverProxy(CSSCrossfadeValue* ownerValue)
: m_ownerValue(ownerValue)
@@ -92,9 +94,9 @@ private:
void crossfadeChanged(const IntRect&);
- RefPtr<CSSValue> m_fromValue;
- RefPtr<CSSValue> m_toValue;
- RefPtr<CSSPrimitiveValue> m_percentageValue;
+ RefPtrWillBeMember<CSSValue> m_fromValue;
+ RefPtrWillBeMember<CSSValue> m_toValue;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_percentageValue;
ResourcePtr<ImageResource> m_cachedFromImage;
ResourcePtr<ImageResource> m_cachedToImage;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.cpp
index 878fd8910de..296375b29b9 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.cpp
@@ -22,7 +22,7 @@
#include "config.h"
#include "core/css/CSSCursorImageValue.h"
-#include "SVGNames.h"
+#include "core/SVGNames.h"
#include "core/css/CSSImageSetValue.h"
#include "core/fetch/ImageResource.h"
#include "core/fetch/ResourceFetcher.h"
@@ -34,20 +34,18 @@
#include "core/svg/SVGLengthContext.h"
#include "core/svg/SVGURIReference.h"
#include "wtf/MathExtras.h"
+#include "wtf/text/StringBuilder.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
-static inline SVGCursorElement* resourceReferencedByCursorElement(const String& url, Document& document)
+static inline SVGCursorElement* resourceReferencedByCursorElement(const String& url, TreeScope& treeScope)
{
- Element* element = SVGURIReference::targetElementFromIRIString(url, document);
- if (element && element->hasTagName(SVGNames::cursorTag))
- return static_cast<SVGCursorElement*>(element);
-
- return 0;
+ Element* element = SVGURIReference::targetElementFromIRIString(url, treeScope);
+ return isSVGCursorElement(element) ? toSVGCursorElement(element) : 0;
}
-CSSCursorImageValue::CSSCursorImageValue(PassRefPtr<CSSValue> imageValue, bool hasHotSpot, const IntPoint& hotSpot)
+CSSCursorImageValue::CSSCursorImageValue(PassRefPtrWillBeRawPtr<CSSValue> imageValue, bool hasHotSpot, const IntPoint& hotSpot)
: CSSValue(CursorImageClass)
, m_imageValue(imageValue)
, m_hasHotSpot(hasHotSpot)
@@ -58,6 +56,8 @@ CSSCursorImageValue::CSSCursorImageValue(PassRefPtr<CSSValue> imageValue, bool h
CSSCursorImageValue::~CSSCursorImageValue()
{
+ // The below teardown is all handled by weak pointer processing in oilpan.
+#if !ENABLE(OILPAN)
if (!isSVGCursor())
return;
@@ -68,9 +68,10 @@ CSSCursorImageValue::~CSSCursorImageValue()
for (; it != end; ++it) {
SVGElement* referencedElement = *it;
referencedElement->cursorImageValueRemoved();
- if (SVGCursorElement* cursorElement = resourceReferencedByCursorElement(url, referencedElement->document()))
+ if (SVGCursorElement* cursorElement = resourceReferencedByCursorElement(url, referencedElement->treeScope()))
cursorElement->removeClient(referencedElement);
}
+#endif
}
String CSSCursorImageValue::customCSSText() const
@@ -95,21 +96,23 @@ bool CSSCursorImageValue::updateIfSVGCursorIsUsed(Element* element)
return false;
String url = toCSSImageValue(m_imageValue.get())->url();
- if (SVGCursorElement* cursorElement = resourceReferencedByCursorElement(url, element->document())) {
+ if (SVGCursorElement* cursorElement = resourceReferencedByCursorElement(url, element->treeScope())) {
// FIXME: This will override hot spot specified in CSS, which is probably incorrect.
SVGLengthContext lengthContext(0);
m_hasHotSpot = true;
- float x = roundf(cursorElement->xCurrentValue().value(lengthContext));
+ float x = roundf(cursorElement->x()->currentValue()->value(lengthContext));
m_hotSpot.setX(static_cast<int>(x));
- float y = roundf(cursorElement->yCurrentValue().value(lengthContext));
+ float y = roundf(cursorElement->y()->currentValue()->value(lengthContext));
m_hotSpot.setY(static_cast<int>(y));
- if (cachedImageURL() != element->document().completeURL(cursorElement->hrefCurrentValue()))
+ if (cachedImageURL() != element->document().completeURL(cursorElement->href()->currentValue()->value()))
clearImageResource();
SVGElement* svgElement = toSVGElement(element);
+#if !ENABLE(OILPAN)
m_referencedElements.add(svgElement);
+#endif
svgElement->setCursorImageValue(this);
cursorElement->addClient(svgElement);
return true;
@@ -130,10 +133,11 @@ StyleImage* CSSCursorImageValue::cachedImage(ResourceFetcher* loader, float devi
// to change the URL of the CSSImageValue (which would then change behavior like cssText),
// we create an alternate CSSImageValue to use.
if (isSVGCursor() && loader && loader->document()) {
- RefPtr<CSSImageValue> imageValue = toCSSImageValue(m_imageValue.get());
+ RefPtrWillBeRawPtr<CSSImageValue> imageValue = toCSSImageValue(m_imageValue.get());
// FIXME: This will fail if the <cursor> element is in a shadow DOM (bug 59827)
if (SVGCursorElement* cursorElement = resourceReferencedByCursorElement(imageValue->url(), *loader->document())) {
- RefPtr<CSSImageValue> svgImageValue = CSSImageValue::create(cursorElement->hrefCurrentValue());
+ RefPtrWillBeRawPtr<CSSImageValue> svgImageValue = CSSImageValue::create(loader->document()->completeURL(cursorElement->href()->currentValue()->value()));
+ svgImageValue->setReferrer(imageValue->referrer());
StyleFetchedImage* cachedImage = svgImageValue->cachedImage(loader);
m_image = cachedImage;
return cachedImage;
@@ -164,7 +168,7 @@ StyleImage* CSSCursorImageValue::cachedOrPendingImage(float deviceScaleFactor)
bool CSSCursorImageValue::isSVGCursor() const
{
if (m_imageValue->isImageValue()) {
- RefPtr<CSSImageValue> imageValue = toCSSImageValue(m_imageValue.get());
+ RefPtrWillBeRawPtr<CSSImageValue> imageValue = toCSSImageValue(m_imageValue.get());
KURL kurl(ParsedURLString, imageValue->url());
return kurl.hasFragmentIdentifier();
}
@@ -180,14 +184,16 @@ String CSSCursorImageValue::cachedImageURL()
void CSSCursorImageValue::clearImageResource()
{
- m_image = 0;
+ m_image = nullptr;
m_accessedImage = false;
}
+#if !ENABLE(OILPAN)
void CSSCursorImageValue::removeReferencedElement(SVGElement* element)
{
m_referencedElements.remove(element);
}
+#endif
bool CSSCursorImageValue::equals(const CSSCursorImageValue& other) const
{
@@ -195,4 +201,10 @@ bool CSSCursorImageValue::equals(const CSSCursorImageValue& other) const
&& compareCSSValuePtr(m_imageValue, other.m_imageValue);
}
+void CSSCursorImageValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_imageValue);
+ CSSValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.h b/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.h
index 17bba3188a1..abc54f73a3f 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCursorImageValue.h
@@ -32,9 +32,9 @@ class SVGElement;
class CSSCursorImageValue : public CSSValue {
public:
- static PassRefPtr<CSSCursorImageValue> create(PassRefPtr<CSSValue> imageValue, bool hasHotSpot, const IntPoint& hotSpot)
+ static PassRefPtrWillBeRawPtr<CSSCursorImageValue> create(PassRefPtrWillBeRawPtr<CSSValue> imageValue, bool hasHotSpot, const IntPoint& hotSpot)
{
- return adoptRef(new CSSCursorImageValue(imageValue, hasHotSpot, hotSpot));
+ return adoptRefWillBeNoop(new CSSCursorImageValue(imageValue, hasHotSpot, hotSpot));
}
~CSSCursorImageValue();
@@ -54,25 +54,31 @@ public:
StyleImage* cachedImage(ResourceFetcher*, float deviceScaleFactor);
StyleImage* cachedOrPendingImage(float deviceScaleFactor);
+#if !ENABLE(OILPAN)
void removeReferencedElement(SVGElement*);
+#endif
bool equals(const CSSCursorImageValue&) const;
+ void traceAfterDispatch(Visitor*);
+
private:
- CSSCursorImageValue(PassRefPtr<CSSValue> imageValue, bool hasHotSpot, const IntPoint& hotSpot);
+ CSSCursorImageValue(PassRefPtrWillBeRawPtr<CSSValue> imageValue, bool hasHotSpot, const IntPoint& hotSpot);
bool isSVGCursor() const;
String cachedImageURL();
void clearImageResource();
- RefPtr<CSSValue> m_imageValue;
+ RefPtrWillBeMember<CSSValue> m_imageValue;
bool m_hasHotSpot;
IntPoint m_hotSpot;
RefPtr<StyleImage> m_image;
bool m_accessedImage;
+#if !ENABLE(OILPAN)
HashSet<SVGElement*> m_referencedElements;
+#endif
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSCursorImageValue, isCursorImageValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSCustomFontData.h b/chromium/third_party/WebKit/Source/core/css/CSSCustomFontData.h
index 9436927cabb..ec2bb6dc885 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSCustomFontData.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSCustomFontData.h
@@ -28,32 +28,45 @@ namespace WebCore {
class CSSCustomFontData FINAL : public CustomFontData {
public:
- static PassRefPtr<CSSCustomFontData> create(bool isLoadingFallback = false)
+ enum FallbackVisibility { InvisibleFallback, VisibleFallback };
+
+ static PassRefPtr<CSSCustomFontData> create(RemoteFontFaceSource* source, FallbackVisibility visibility)
{
- return adoptRef(new CSSCustomFontData(isLoadingFallback));
+ return adoptRef(new CSSCustomFontData(source, visibility));
}
virtual ~CSSCustomFontData() { }
+ virtual bool shouldSkipDrawing() const OVERRIDE
+ {
+ if (m_fontFaceSource)
+ m_fontFaceSource->paintRequested();
+ return m_fallbackVisibility == InvisibleFallback && m_isUsed;
+ }
+
virtual void beginLoadIfNeeded() const OVERRIDE
{
- if (!m_isUsed && m_isLoadingFallback && m_fontFaceSource) {
+ if (!m_isUsed && m_fontFaceSource) {
m_isUsed = true;
m_fontFaceSource->beginLoadIfNeeded();
}
}
- virtual void setCSSFontFaceSource(CSSFontFaceSource* source) OVERRIDE { m_fontFaceSource = source; }
- virtual void clearCSSFontFaceSource() OVERRIDE { m_fontFaceSource = 0; }
+ virtual bool isLoading() const OVERRIDE { return m_isUsed; }
+ virtual bool isLoadingFallback() const OVERRIDE { return true; }
+ virtual void clearFontFaceSource() OVERRIDE { m_fontFaceSource = 0; }
private:
- CSSCustomFontData(bool isLoadingFallback)
- : CustomFontData(isLoadingFallback)
- , m_fontFaceSource(0)
+ CSSCustomFontData(RemoteFontFaceSource* source, FallbackVisibility visibility)
+ : m_fontFaceSource(source)
+ , m_fallbackVisibility(visibility)
+ , m_isUsed(false)
{
}
- CSSFontFaceSource* m_fontFaceSource;
+ RemoteFontFaceSource* m_fontFaceSource;
+ FallbackVisibility m_fallbackVisibility;
+ mutable bool m_isUsed;
};
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.cpp b/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.cpp
index cdd794828a7..1137f9b7ad9 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.cpp
@@ -29,33 +29,31 @@
#include "config.h"
#include "core/css/CSSDefaultStyleSheets.h"
-#include "UserAgentStyleSheets.h"
+#include "core/MathMLNames.h"
+#include "core/UserAgentStyleSheets.h"
#include "core/css/MediaQueryEvaluator.h"
#include "core/css/RuleSet.h"
#include "core/css/StyleSheetContents.h"
#include "core/dom/FullscreenElementStack.h"
#include "core/html/HTMLAnchorElement.h"
#include "core/html/HTMLHtmlElement.h"
-#include "core/html/HTMLVideoElement.h"
#include "core/rendering/RenderTheme.h"
+#include "wtf/LeakAnnotations.h"
namespace WebCore {
using namespace HTMLNames;
-RuleSet* CSSDefaultStyleSheets::defaultStyle;
-RuleSet* CSSDefaultStyleSheets::defaultViewportStyle;
-RuleSet* CSSDefaultStyleSheets::defaultQuirksStyle;
-RuleSet* CSSDefaultStyleSheets::defaultPrintStyle;
-RuleSet* CSSDefaultStyleSheets::defaultViewSourceStyle;
-RuleSet* CSSDefaultStyleSheets::defaultXHTMLMobileProfileStyle;
-
-StyleSheetContents* CSSDefaultStyleSheets::defaultStyleSheet;
-StyleSheetContents* CSSDefaultStyleSheets::viewportStyleSheet;
-StyleSheetContents* CSSDefaultStyleSheets::quirksStyleSheet;
-StyleSheetContents* CSSDefaultStyleSheets::svgStyleSheet;
-StyleSheetContents* CSSDefaultStyleSheets::mediaControlsStyleSheet;
-StyleSheetContents* CSSDefaultStyleSheets::fullscreenStyleSheet;
+CSSDefaultStyleSheets& CSSDefaultStyleSheets::instance()
+{
+#if ENABLE(OILPAN)
+ DEFINE_STATIC_LOCAL(Persistent<CSSDefaultStyleSheets>, cssDefaultStyleSheets, (new CSSDefaultStyleSheets()));
+ return *cssDefaultStyleSheets;
+#else
+ DEFINE_STATIC_LOCAL(CSSDefaultStyleSheets, cssDefaultStyleSheets, ());
+ return cssDefaultStyleSheets;
+#endif
+}
static const MediaQueryEvaluator& screenEval()
{
@@ -69,100 +67,153 @@ static const MediaQueryEvaluator& printEval()
return staticPrintEval;
}
-static StyleSheetContents* parseUASheet(const String& str)
+static PassRefPtrWillBeRawPtr<StyleSheetContents> parseUASheet(const String& str)
{
- StyleSheetContents* sheet = StyleSheetContents::create(CSSParserContext(UASheetMode)).leakRef(); // leak the sheet on purpose
+ RefPtrWillBeRawPtr<StyleSheetContents> sheet = StyleSheetContents::create(CSSParserContext(UASheetMode, 0));
sheet->parseString(str);
- return sheet;
+ // User Agent stylesheets are parsed once for the lifetime of the renderer
+ // and are intentionally leaked.
+ WTF_ANNOTATE_LEAKING_OBJECT_PTR(sheet.get());
+ return sheet.release();
}
-static StyleSheetContents* parseUASheet(const char* characters, unsigned size)
+static PassRefPtrWillBeRawPtr<StyleSheetContents> parseUASheet(const char* characters, unsigned size)
{
return parseUASheet(String(characters, size));
}
-void CSSDefaultStyleSheets::loadDefaultStylesheetIfNecessary()
+CSSDefaultStyleSheets::CSSDefaultStyleSheets()
+ : m_defaultStyle(nullptr)
+ , m_defaultViewportStyle(nullptr)
+ , m_defaultQuirksStyle(nullptr)
+ , m_defaultPrintStyle(nullptr)
+ , m_defaultViewSourceStyle(nullptr)
+ , m_defaultXHTMLMobileProfileStyle(nullptr)
+ , m_defaultTransitionStyle(nullptr)
+ , m_defaultStyleSheet(nullptr)
+ , m_viewportStyleSheet(nullptr)
+ , m_quirksStyleSheet(nullptr)
+ , m_svgStyleSheet(nullptr)
+ , m_mathmlStyleSheet(nullptr)
+ , m_mediaControlsStyleSheet(nullptr)
+ , m_fullscreenStyleSheet(nullptr)
{
- if (!defaultStyle)
- loadDefaultStyle();
-}
-
-void CSSDefaultStyleSheets::loadDefaultStyle()
-{
- ASSERT(!defaultStyle);
- defaultStyle = RuleSet::create().leakPtr();
- defaultViewportStyle = RuleSet::create().leakPtr();
- defaultPrintStyle = RuleSet::create().leakPtr();
- defaultQuirksStyle = RuleSet::create().leakPtr();
+ m_defaultStyle = RuleSet::create();
+ m_defaultViewportStyle = RuleSet::create();
+ m_defaultPrintStyle = RuleSet::create();
+ m_defaultQuirksStyle = RuleSet::create();
// Strict-mode rules.
String defaultRules = String(htmlUserAgentStyleSheet, sizeof(htmlUserAgentStyleSheet)) + RenderTheme::theme().extraDefaultStyleSheet();
- defaultStyleSheet = parseUASheet(defaultRules);
- defaultStyle->addRulesFromSheet(defaultStyleSheet, screenEval());
+ m_defaultStyleSheet = parseUASheet(defaultRules);
+ m_defaultStyle->addRulesFromSheet(defaultStyleSheet(), screenEval());
#if OS(ANDROID)
String viewportRules(viewportAndroidUserAgentStyleSheet, sizeof(viewportAndroidUserAgentStyleSheet));
#else
String viewportRules;
#endif
- viewportStyleSheet = parseUASheet(viewportRules);
- defaultViewportStyle->addRulesFromSheet(viewportStyleSheet, screenEval());
- defaultPrintStyle->addRulesFromSheet(defaultStyleSheet, printEval());
+ m_viewportStyleSheet = parseUASheet(viewportRules);
+ m_defaultViewportStyle->addRulesFromSheet(viewportStyleSheet(), screenEval());
+ m_defaultPrintStyle->addRulesFromSheet(defaultStyleSheet(), printEval());
// Quirks-mode rules.
String quirksRules = String(quirksUserAgentStyleSheet, sizeof(quirksUserAgentStyleSheet)) + RenderTheme::theme().extraQuirksStyleSheet();
- quirksStyleSheet = parseUASheet(quirksRules);
- defaultQuirksStyle->addRulesFromSheet(quirksStyleSheet, screenEval());
+ m_quirksStyleSheet = parseUASheet(quirksRules);
+ m_defaultQuirksStyle->addRulesFromSheet(quirksStyleSheet(), screenEval());
+}
+
+RuleSet* CSSDefaultStyleSheets::defaultViewSourceStyle()
+{
+ if (!m_defaultViewSourceStyle) {
+ m_defaultViewSourceStyle = RuleSet::create();
+ // Loaded stylesheet is leaked on purpose.
+ RefPtrWillBeRawPtr<StyleSheetContents> stylesheet = parseUASheet(sourceUserAgentStyleSheet, sizeof(sourceUserAgentStyleSheet));
+ m_defaultViewSourceStyle->addRulesFromSheet(stylesheet.release().leakRef(), screenEval());
+ }
+ return m_defaultViewSourceStyle.get();
}
-RuleSet* CSSDefaultStyleSheets::viewSourceStyle()
+RuleSet* CSSDefaultStyleSheets::defaultTransitionStyle()
{
- if (!defaultViewSourceStyle) {
- defaultViewSourceStyle = RuleSet::create().leakPtr();
- defaultViewSourceStyle->addRulesFromSheet(parseUASheet(sourceUserAgentStyleSheet, sizeof(sourceUserAgentStyleSheet)), screenEval());
+ if (!m_defaultTransitionStyle) {
+ m_defaultTransitionStyle = RuleSet::create();
+ // Loaded stylesheet is leaked on purpose.
+ RefPtrWillBeRawPtr<StyleSheetContents> stylesheet = parseUASheet(navigationTransitionsUserAgentStyleSheet, sizeof(navigationTransitionsUserAgentStyleSheet));
+ m_defaultTransitionStyle->addRulesFromSheet(stylesheet.release().leakRef(), screenEval());
}
- return defaultViewSourceStyle;
+ return m_defaultTransitionStyle.get();
}
-RuleSet* CSSDefaultStyleSheets::xhtmlMobileProfileStyle()
+RuleSet* CSSDefaultStyleSheets::defaultXHTMLMobileProfileStyle()
{
- if (!defaultXHTMLMobileProfileStyle) {
- defaultXHTMLMobileProfileStyle = RuleSet::create().leakPtr();
- defaultXHTMLMobileProfileStyle->addRulesFromSheet(parseUASheet(xhtmlmpUserAgentStyleSheet, sizeof(xhtmlmpUserAgentStyleSheet)), screenEval());
+ if (!m_defaultXHTMLMobileProfileStyle) {
+ m_defaultXHTMLMobileProfileStyle = RuleSet::create();
+ // Loaded stylesheet is leaked on purpose.
+ RefPtrWillBeRawPtr<StyleSheetContents> stylesheet = parseUASheet(xhtmlmpUserAgentStyleSheet, sizeof(xhtmlmpUserAgentStyleSheet));
+ m_defaultXHTMLMobileProfileStyle->addRulesFromSheet(stylesheet.release().leakRef(), screenEval());
}
- return defaultXHTMLMobileProfileStyle;
+ return m_defaultXHTMLMobileProfileStyle.get();
}
void CSSDefaultStyleSheets::ensureDefaultStyleSheetsForElement(Element* element, bool& changedDefaultStyle)
{
// FIXME: We should assert that the sheet only styles SVG elements.
- if (element->isSVGElement() && !svgStyleSheet) {
- svgStyleSheet = parseUASheet(svgUserAgentStyleSheet, sizeof(svgUserAgentStyleSheet));
- defaultStyle->addRulesFromSheet(svgStyleSheet, screenEval());
- defaultPrintStyle->addRulesFromSheet(svgStyleSheet, printEval());
+ if (element->isSVGElement() && !m_svgStyleSheet) {
+ m_svgStyleSheet = parseUASheet(svgUserAgentStyleSheet, sizeof(svgUserAgentStyleSheet));
+ m_defaultStyle->addRulesFromSheet(svgStyleSheet(), screenEval());
+ m_defaultPrintStyle->addRulesFromSheet(svgStyleSheet(), printEval());
+ changedDefaultStyle = true;
+ }
+
+ // FIXME: We should assert that the sheet only styles MathML elements.
+ if (element->namespaceURI() == MathMLNames::mathmlNamespaceURI
+ && !m_mathmlStyleSheet) {
+ m_mathmlStyleSheet = parseUASheet(mathmlUserAgentStyleSheet,
+ sizeof(mathmlUserAgentStyleSheet));
+ m_defaultStyle->addRulesFromSheet(mathmlStyleSheet(), screenEval());
+ m_defaultPrintStyle->addRulesFromSheet(mathmlStyleSheet(), printEval());
changedDefaultStyle = true;
}
// FIXME: We should assert that this sheet only contains rules for <video> and <audio>.
- if (!mediaControlsStyleSheet && (isHTMLVideoElement(element) || element->hasTagName(audioTag))) {
+ if (!m_mediaControlsStyleSheet && (isHTMLVideoElement(*element) || isHTMLAudioElement(*element))) {
String mediaRules = String(mediaControlsUserAgentStyleSheet, sizeof(mediaControlsUserAgentStyleSheet)) + RenderTheme::theme().extraMediaControlsStyleSheet();
- mediaControlsStyleSheet = parseUASheet(mediaRules);
- defaultStyle->addRulesFromSheet(mediaControlsStyleSheet, screenEval());
- defaultPrintStyle->addRulesFromSheet(mediaControlsStyleSheet, printEval());
+ m_mediaControlsStyleSheet = parseUASheet(mediaRules);
+ m_defaultStyle->addRulesFromSheet(mediaControlsStyleSheet(), screenEval());
+ m_defaultPrintStyle->addRulesFromSheet(mediaControlsStyleSheet(), printEval());
changedDefaultStyle = true;
}
// FIXME: This only works because we Force recalc the entire document so the new sheet
// is loaded for <html> and the correct styles apply to everyone.
- if (!fullscreenStyleSheet && FullscreenElementStack::isFullScreen(&element->document())) {
+ if (!m_fullscreenStyleSheet && FullscreenElementStack::isFullScreen(element->document())) {
String fullscreenRules = String(fullscreenUserAgentStyleSheet, sizeof(fullscreenUserAgentStyleSheet)) + RenderTheme::theme().extraFullScreenStyleSheet();
- fullscreenStyleSheet = parseUASheet(fullscreenRules);
- defaultStyle->addRulesFromSheet(fullscreenStyleSheet, screenEval());
- defaultQuirksStyle->addRulesFromSheet(fullscreenStyleSheet, screenEval());
+ m_fullscreenStyleSheet = parseUASheet(fullscreenRules);
+ m_defaultStyle->addRulesFromSheet(fullscreenStyleSheet(), screenEval());
+ m_defaultQuirksStyle->addRulesFromSheet(fullscreenStyleSheet(), screenEval());
changedDefaultStyle = true;
}
- ASSERT(defaultStyle->features().idsInRules.isEmpty());
- ASSERT(defaultStyle->features().siblingRules.isEmpty());
+ ASSERT(!m_defaultStyle->features().hasIdsInSelectors());
+ ASSERT(m_defaultStyle->features().siblingRules.isEmpty());
+}
+
+void CSSDefaultStyleSheets::trace(Visitor* visitor)
+{
+ visitor->trace(m_defaultStyle);
+ visitor->trace(m_defaultViewportStyle);
+ visitor->trace(m_defaultQuirksStyle);
+ visitor->trace(m_defaultPrintStyle);
+ visitor->trace(m_defaultViewSourceStyle);
+ visitor->trace(m_defaultXHTMLMobileProfileStyle);
+ visitor->trace(m_defaultTransitionStyle);
+ visitor->trace(m_defaultStyleSheet);
+ visitor->trace(m_viewportStyleSheet);
+ visitor->trace(m_quirksStyleSheet);
+ visitor->trace(m_svgStyleSheet);
+ visitor->trace(m_mathmlStyleSheet);
+ visitor->trace(m_mediaControlsStyleSheet);
+ visitor->trace(m_fullscreenStyleSheet);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.h b/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.h
index c85fd226340..0efccd191ec 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSDefaultStyleSheets.h
@@ -23,39 +23,58 @@
#ifndef CSSDefaultStyleSheets_h
#define CSSDefaultStyleSheets_h
+#include "platform/heap/Handle.h"
+
namespace WebCore {
class Element;
class RuleSet;
class StyleSheetContents;
-class CSSDefaultStyleSheets {
+class CSSDefaultStyleSheets : public NoBaseWillBeGarbageCollected<CSSDefaultStyleSheets> {
public:
- static RuleSet* defaultStyle;
- static RuleSet* defaultViewportStyle;
- static RuleSet* defaultQuirksStyle;
- static RuleSet* defaultPrintStyle;
- static RuleSet* defaultViewSourceStyle;
- static RuleSet* defaultXHTMLMobileProfileStyle;
-
- static StyleSheetContents* defaultStyleSheet;
- static StyleSheetContents* viewportStyleSheet;
- static StyleSheetContents* quirksStyleSheet;
- static StyleSheetContents* svgStyleSheet;
- static StyleSheetContents* mediaControlsStyleSheet;
- static StyleSheetContents* fullscreenStyleSheet;
-
- static void ensureDefaultStyleSheetsForElement(Element*, bool& changedDefaultStyle);
- // FIXME: defaultStyleSheet should have an accessor which incorporates this branch:
- static void loadDefaultStylesheetIfNecessary();
-
- static RuleSet* viewSourceStyle();
+ static CSSDefaultStyleSheets& instance();
+
+ void ensureDefaultStyleSheetsForElement(Element*, bool& changedDefaultStyle);
+
+ RuleSet* defaultStyle() { return m_defaultStyle.get(); }
+ RuleSet* defaultViewportStyle() { return m_defaultViewportStyle.get(); }
+ RuleSet* defaultQuirksStyle() { return m_defaultQuirksStyle.get(); }
+ RuleSet* defaultPrintStyle() { return m_defaultPrintStyle.get(); }
+ RuleSet* defaultViewSourceStyle();
+ RuleSet* defaultTransitionStyle();
// FIXME: Remove WAP support.
- static RuleSet* xhtmlMobileProfileStyle();
+ RuleSet* defaultXHTMLMobileProfileStyle();
+
+ StyleSheetContents* defaultStyleSheet() { return m_defaultStyleSheet.get(); }
+ StyleSheetContents* viewportStyleSheet() { return m_viewportStyleSheet.get(); }
+ StyleSheetContents* quirksStyleSheet() { return m_quirksStyleSheet.get(); }
+ StyleSheetContents* svgStyleSheet() { return m_svgStyleSheet.get(); }
+ StyleSheetContents* mathmlStyleSheet() { return m_mathmlStyleSheet.get(); }
+ StyleSheetContents* mediaControlsStyleSheet() { return m_mediaControlsStyleSheet.get(); }
+ StyleSheetContents* fullscreenStyleSheet() { return m_fullscreenStyleSheet.get(); }
+
+ void trace(Visitor*);
private:
- static void loadDefaultStyle();
+ CSSDefaultStyleSheets();
+
+ OwnPtrWillBeMember<RuleSet> m_defaultStyle;
+ OwnPtrWillBeMember<RuleSet> m_defaultViewportStyle;
+ OwnPtrWillBeMember<RuleSet> m_defaultQuirksStyle;
+ OwnPtrWillBeMember<RuleSet> m_defaultPrintStyle;
+ OwnPtrWillBeMember<RuleSet> m_defaultViewSourceStyle;
+ OwnPtrWillBeMember<RuleSet> m_defaultXHTMLMobileProfileStyle;
+ OwnPtrWillBeMember<RuleSet> m_defaultTransitionStyle;
+
+ RefPtrWillBeMember<StyleSheetContents> m_defaultStyleSheet;
+ RefPtrWillBeMember<StyleSheetContents> m_viewportStyleSheet;
+ RefPtrWillBeMember<StyleSheetContents> m_quirksStyleSheet;
+ RefPtrWillBeMember<StyleSheetContents> m_svgStyleSheet;
+ RefPtrWillBeMember<StyleSheetContents> m_mathmlStyleSheet;
+ RefPtrWillBeMember<StyleSheetContents> m_mediaControlsStyleSheet;
+ RefPtrWillBeMember<StyleSheetContents> m_fullscreenStyleSheet;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.cpp
index dc44874be19..90b3390fcad 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.cpp
@@ -45,8 +45,10 @@ CSSFilterRule::CSSFilterRule(StyleRuleFilter* filterRule, CSSStyleSheet* parent)
CSSFilterRule::~CSSFilterRule()
{
+#if !ENABLE(OILPAN)
if (m_propertiesCSSOMWrapper)
m_propertiesCSSOMWrapper->clearParentRule();
+#endif
}
CSSStyleDeclaration* CSSFilterRule::style() const
@@ -65,7 +67,7 @@ String CSSFilterRule::cssText() const
result.append(filterName);
result.appendLiteral(" { ");
- String descs = m_filterRule->properties()->asText();
+ String descs = m_filterRule->properties().asText();
result.append(descs);
if (!descs.isEmpty())
result.append(' ');
@@ -82,5 +84,12 @@ void CSSFilterRule::reattach(StyleRuleBase* rule)
m_propertiesCSSOMWrapper->reattach(m_filterRule->mutableProperties());
}
+void CSSFilterRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_filterRule);
+ visitor->trace(m_propertiesCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.h b/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.h
index 9bb1b192c2a..bd3be8dfe3b 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFilterRule.h
@@ -31,6 +31,7 @@
#define CSSFilterRule_h
#include "core/css/CSSRule.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -38,9 +39,12 @@ class CSSStyleDeclaration;
class StyleRuleFilter;
class StyleRuleCSSStyleDeclaration;
-class CSSFilterRule : public CSSRule {
+class CSSFilterRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSFilterRule> create(StyleRuleFilter* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSFilterRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSFilterRule> create(StyleRuleFilter* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSFilterRule(rule, sheet));
+ }
virtual ~CSSFilterRule();
@@ -50,11 +54,13 @@ public:
CSSStyleDeclaration* style() const;
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSFilterRule(StyleRuleFilter*, CSSStyleSheet* parent);
- RefPtr<StyleRuleFilter> m_filterRule;
- mutable RefPtr<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
+ RefPtrWillBeMember<StyleRuleFilter> m_filterRule;
+ mutable RefPtrWillBeMember<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSFilterRule, WEBKIT_FILTER_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.cpp
index 75567a7eeb8..3f71adecdcb 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.cpp
@@ -26,66 +26,60 @@
#include "config.h"
#include "core/css/CSSFilterValue.h"
-#include "wtf/text/WTFString.h"
+#include "wtf/text/StringBuilder.h"
namespace WebCore {
CSSFilterValue::CSSFilterValue(FilterOperationType operationType)
- : CSSValueList(CSSFilterClass, typeUsesSpaceSeparator(operationType) ? SpaceSeparator : CommaSeparator)
+ : CSSValueList(CSSFilterClass, CommaSeparator)
, m_type(operationType)
{
}
-bool CSSFilterValue::typeUsesSpaceSeparator(FilterOperationType operationType)
-{
- return operationType != CustomFilterOperation;
-}
-
String CSSFilterValue::customCSSText() const
{
- String result;
+ StringBuilder result;
switch (m_type) {
case ReferenceFilterOperation:
- result = "url(";
+ result.append("url(");
break;
case GrayscaleFilterOperation:
- result = "grayscale(";
+ result.append("grayscale(");
break;
case SepiaFilterOperation:
- result = "sepia(";
+ result.append("sepia(");
break;
case SaturateFilterOperation:
- result = "saturate(";
+ result.append("saturate(");
break;
case HueRotateFilterOperation:
- result = "hue-rotate(";
+ result.append("hue-rotate(");
break;
case InvertFilterOperation:
- result = "invert(";
+ result.append("invert(");
break;
case OpacityFilterOperation:
- result = "opacity(";
+ result.append("opacity(");
break;
case BrightnessFilterOperation:
- result = "brightness(";
+ result.append("brightness(");
break;
case ContrastFilterOperation:
- result = "contrast(";
+ result.append("contrast(");
break;
case BlurFilterOperation:
- result = "blur(";
+ result.append("blur(");
break;
case DropShadowFilterOperation:
- result = "drop-shadow(";
- break;
- case CustomFilterOperation:
- result = "custom(";
+ result.append("drop-shadow(");
break;
default:
break;
}
- return result + CSSValueList::customCSSText() + ")";
+ result.append(CSSValueList::customCSSText());
+ result.append(')');
+ return result.toString();
}
CSSFilterValue::CSSFilterValue(const CSSFilterValue& cloneFrom)
@@ -94,9 +88,9 @@ CSSFilterValue::CSSFilterValue(const CSSFilterValue& cloneFrom)
{
}
-PassRefPtr<CSSFilterValue> CSSFilterValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSFilterValue> CSSFilterValue::cloneForCSSOM() const
{
- return adoptRef(new CSSFilterValue(*this));
+ return adoptRefWillBeNoop(new CSSFilterValue(*this));
}
bool CSSFilterValue::equals(const CSSFilterValue& other) const
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.h b/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.h
index 7a2f80c1a4c..4304e144cd4 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFilterValue.h
@@ -47,24 +47,25 @@ public:
ContrastFilterOperation,
BlurFilterOperation,
DropShadowFilterOperation,
- CustomFilterOperation
};
static bool typeUsesSpaceSeparator(FilterOperationType);
- static PassRefPtr<CSSFilterValue> create(FilterOperationType type)
+ static PassRefPtrWillBeRawPtr<CSSFilterValue> create(FilterOperationType type)
{
- return adoptRef(new CSSFilterValue(type));
+ return adoptRefWillBeNoop(new CSSFilterValue(type));
}
String customCSSText() const;
FilterOperationType operationType() const { return m_type; }
- PassRefPtr<CSSFilterValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSFilterValue> cloneForCSSOM() const;
bool equals(const CSSFilterValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValueList::traceAfterDispatch(visitor); }
+
private:
explicit CSSFilterValue(FilterOperationType);
explicit CSSFilterValue(const CSSFilterValue& cloneFrom);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFace.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontFace.cpp
index c21c9125afb..9dddf489a46 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFace.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFace.cpp
@@ -26,60 +26,19 @@
#include "config.h"
#include "core/css/CSSFontFace.h"
+#include "core/css/CSSFontFaceSource.h"
#include "core/css/CSSFontSelector.h"
#include "core/css/CSSSegmentedFontFace.h"
#include "core/css/FontFaceSet.h"
+#include "core/css/RemoteFontFaceSource.h"
#include "core/dom/Document.h"
#include "core/frame/UseCounter.h"
+#include "platform/fonts/FontDescription.h"
#include "platform/fonts/SimpleFontData.h"
namespace WebCore {
-CSSFontFace::~CSSFontFace()
-{
- m_fontFace->cssFontFaceDestroyed();
-}
-
-PassRefPtr<CSSFontFace> CSSFontFace::createFromStyleRule(Document* document, const StyleRuleFontFace* fontFaceRule)
-{
- RefPtr<FontFace> fontFace = FontFace::create(fontFaceRule);
- if (!fontFace || fontFace->family().isEmpty())
- return 0;
-
- unsigned traitsMask = fontFace->traitsMask();
- if (!traitsMask)
- return 0;
-
- // FIXME: Plumbing back into createCSSFontFace seems odd.
- // Maybe move FontFace::createCSSFontFace logic here?
- RefPtr<CSSFontFace> cssFontFace = fontFace->createCSSFontFace(document);
- if (!cssFontFace || !cssFontFace->isValid())
- return 0;
-
- return cssFontFace;
-}
-
-bool CSSFontFace::isLoaded() const
-{
- size_t size = m_sources.size();
- for (size_t i = 0; i < size; i++) {
- if (!m_sources[i]->isLoaded())
- return false;
- }
- return true;
-}
-
-bool CSSFontFace::isValid() const
-{
- size_t size = m_sources.size();
- for (size_t i = 0; i < size; i++) {
- if (m_sources[i]->isValid())
- return true;
- }
- return false;
-}
-
-void CSSFontFace::addSource(PassOwnPtr<CSSFontFaceSource> source)
+void CSSFontFace::addSource(PassOwnPtrWillBeRawPtr<CSSFontFaceSource> source)
{
source->setFontFace(this);
m_sources.append(source);
@@ -91,99 +50,112 @@ void CSSFontFace::setSegmentedFontFace(CSSSegmentedFontFace* segmentedFontFace)
m_segmentedFontFace = segmentedFontFace;
}
-void CSSFontFace::beginLoadIfNeeded(CSSFontFaceSource* source)
+void CSSFontFace::didBeginLoad()
{
- if (!m_segmentedFontFace)
- return;
-
- if (source->resource() && source->resource()->stillNeedsLoad()) {
- CSSFontSelector* fontSelector = m_segmentedFontFace->fontSelector();
- fontSelector->beginLoadingFontSoon(source->resource());
- }
-
if (loadStatus() == FontFace::Unloaded)
setLoadStatus(FontFace::Loading);
}
-void CSSFontFace::fontLoaded(CSSFontFaceSource* source)
+void CSSFontFace::fontLoaded(RemoteFontFaceSource* source)
{
- if (source != m_activeSource)
+ if (!isValid() || source != m_sources.first())
return;
- m_activeSource = 0;
- // FIXME: Can we assert that m_segmentedFontFace is non-null? That may
- // require stopping in-progress font loading when the last
- // CSSSegmentedFontFace is removed.
- if (!m_segmentedFontFace)
- return;
-
- CSSFontSelector* fontSelector = m_segmentedFontFace->fontSelector();
- fontSelector->fontLoaded();
-
- if (fontSelector->document() && loadStatus() == FontFace::Loading) {
+ if (loadStatus() == FontFace::Loading) {
if (source->ensureFontData()) {
setLoadStatus(FontFace::Loaded);
- if (source->isSVGFontFaceSource())
- UseCounter::count(*fontSelector->document(), UseCounter::SVGFontInCSS);
+#if ENABLE(SVG_FONTS)
+ Document* document = m_segmentedFontFace ? m_segmentedFontFace->fontSelector()->document() : 0;
+ if (document && source->isSVGFontFaceSource())
+ UseCounter::count(*document, UseCounter::SVGFontInCSS);
+#endif
+ } else {
+ m_sources.removeFirst();
+ load();
}
- else if (!isValid())
- setLoadStatus(FontFace::Error);
}
- m_segmentedFontFace->fontLoaded(this);
+ if (m_segmentedFontFace)
+ m_segmentedFontFace->fontLoaded(this);
+}
+
+void CSSFontFace::fontLoadWaitLimitExceeded(RemoteFontFaceSource* source)
+{
+ if (!isValid() || source != m_sources.first())
+ return;
+ if (m_segmentedFontFace)
+ m_segmentedFontFace->fontLoadWaitLimitExceeded(this);
}
PassRefPtr<SimpleFontData> CSSFontFace::getFontData(const FontDescription& fontDescription)
{
- m_activeSource = 0;
if (!isValid())
- return 0;
+ return nullptr;
- size_t size = m_sources.size();
- for (size_t i = 0; i < size; ++i) {
- if (RefPtr<SimpleFontData> result = m_sources[i]->getFontData(fontDescription)) {
- m_activeSource = m_sources[i].get();
- if (loadStatus() == FontFace::Unloaded && (m_sources[i]->isLoading() || m_sources[i]->isLoaded()))
+ while (!m_sources.isEmpty()) {
+ OwnPtrWillBeMember<CSSFontFaceSource>& source = m_sources.first();
+ if (RefPtr<SimpleFontData> result = source->getFontData(fontDescription)) {
+ if (loadStatus() == FontFace::Unloaded && (source->isLoading() || source->isLoaded()))
setLoadStatus(FontFace::Loading);
- if (loadStatus() == FontFace::Loading && m_sources[i]->isLoaded())
+ if (loadStatus() == FontFace::Loading && source->isLoaded())
setLoadStatus(FontFace::Loaded);
return result.release();
}
+ m_sources.removeFirst();
}
if (loadStatus() == FontFace::Unloaded)
setLoadStatus(FontFace::Loading);
if (loadStatus() == FontFace::Loading)
setLoadStatus(FontFace::Error);
- return 0;
+ return nullptr;
}
-void CSSFontFace::willUseFontData(const FontDescription& fontDescription)
+bool CSSFontFace::maybeScheduleFontLoad(const FontDescription& fontDescription, UChar32 character)
{
- if (loadStatus() != FontFace::Unloaded || m_activeSource)
- return;
-
- // Kicks off font load here only if the @font-face has no unicode-range.
- // @font-faces with unicode-range will be loaded when a GlyphPage for the
- // font is created.
- // FIXME: Pass around the text to render from RenderText, and kick download
- // if m_ranges intersects with the text. Make sure this does not cause
- // performance regression.
- if (!m_ranges.isEntireRange())
- return;
+ if (m_ranges.contains(character)) {
+ if (loadStatus() == FontFace::Unloaded)
+ load(fontDescription);
+ return true;
+ }
+ return false;
+}
- ASSERT(m_segmentedFontFace);
+void CSSFontFace::load()
+{
+ FontDescription fontDescription;
+ FontFamily fontFamily;
+ fontFamily.setFamily(m_fontFace->family());
+ fontDescription.setFamily(fontFamily);
+ fontDescription.setTraits(m_fontFace->traits());
+ load(fontDescription);
+}
- size_t size = m_sources.size();
- for (size_t i = 0; i < size; ++i) {
- if (!m_sources[i]->isValid() || (m_sources[i]->isLocal() && !m_sources[i]->isLocalFontAvailable(fontDescription)))
- continue;
- if (!m_sources[i]->isLocal() && !m_sources[i]->isLoaded()) {
- m_activeSource = m_sources[i].get();
- beginLoadIfNeeded(m_activeSource);
+void CSSFontFace::load(const FontDescription& fontDescription)
+{
+ if (loadStatus() == FontFace::Unloaded)
+ setLoadStatus(FontFace::Loading);
+ ASSERT(loadStatus() == FontFace::Loading);
+
+ while (!m_sources.isEmpty()) {
+ OwnPtrWillBeMember<CSSFontFaceSource>& source = m_sources.first();
+ if (source->isValid()) {
+ if (source->isLocal()) {
+ if (source->isLocalFontAvailable(fontDescription)) {
+ setLoadStatus(FontFace::Loaded);
+ return;
+ }
+ } else {
+ if (!source->isLoaded())
+ source->beginLoadIfNeeded();
+ else
+ setLoadStatus(FontFace::Loaded);
+ return;
+ }
}
- break;
+ m_sources.removeFirst();
}
+ setLoadStatus(FontFace::Error);
}
void CSSFontFace::setLoadStatus(FontFace::LoadStatus newStatus)
@@ -199,38 +171,76 @@ void CSSFontFace::setLoadStatus(FontFace::LoadStatus newStatus)
switch (newStatus) {
case FontFace::Loading:
- FontFaceSet::from(document)->beginFontLoading(m_fontFace.get());
+ FontFaceSet::from(*document)->beginFontLoading(m_fontFace);
break;
case FontFace::Loaded:
- FontFaceSet::from(document)->fontLoaded(m_fontFace.get());
+ FontFaceSet::from(*document)->fontLoaded(m_fontFace);
break;
case FontFace::Error:
- FontFaceSet::from(document)->loadError(m_fontFace.get());
+ FontFaceSet::from(*document)->loadError(m_fontFace);
break;
default:
break;
}
}
+CSSFontFace::UnicodeRangeSet::UnicodeRangeSet(const Vector<UnicodeRange>& ranges)
+ : m_ranges(ranges)
+{
+ if (m_ranges.isEmpty())
+ return;
+
+ std::sort(m_ranges.begin(), m_ranges.end());
+
+ // Unify overlapping ranges.
+ UChar32 from = m_ranges[0].from();
+ UChar32 to = m_ranges[0].to();
+ size_t targetIndex = 0;
+ for (size_t i = 1; i < m_ranges.size(); i++) {
+ if (to + 1 >= m_ranges[i].from()) {
+ to = std::max(to, m_ranges[i].to());
+ } else {
+ m_ranges[targetIndex++] = UnicodeRange(from, to);
+ from = m_ranges[i].from();
+ to = m_ranges[i].to();
+ }
+ }
+ m_ranges[targetIndex++] = UnicodeRange(from, to);
+ m_ranges.shrink(targetIndex);
+}
+
+bool CSSFontFace::UnicodeRangeSet::contains(UChar32 c) const
+{
+ if (isEntireRange())
+ return true;
+ Vector<UnicodeRange>::const_iterator it = std::lower_bound(m_ranges.begin(), m_ranges.end(), c);
+ return it != m_ranges.end() && it->contains(c);
+}
+
bool CSSFontFace::UnicodeRangeSet::intersectsWith(const String& text) const
{
if (text.isEmpty())
return false;
if (isEntireRange())
return true;
+ if (text.is8Bit() && m_ranges[0].from() >= 0x100)
+ return false;
- // FIXME: This takes O(text.length() * m_ranges.size()) time. It would be
- // better to make m_ranges sorted and use binary search.
unsigned index = 0;
while (index < text.length()) {
UChar32 c = text.characterStartingAt(index);
index += U16_LENGTH(c);
- for (unsigned i = 0; i < m_ranges.size(); i++) {
- if (m_ranges[i].contains(c))
- return true;
- }
+ if (contains(c))
+ return true;
}
return false;
}
+void CSSFontFace::trace(Visitor* visitor)
+{
+ visitor->trace(m_segmentedFontFace);
+ visitor->trace(m_sources);
+ visitor->trace(m_fontFace);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFace.h b/chromium/third_party/WebKit/Source/core/css/CSSFontFace.h
index e4ad5f048a1..96ddbf52601 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFace.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFace.h
@@ -27,44 +27,49 @@
#define CSSFontFace_h
#include "core/css/CSSFontFaceSource.h"
+#include "core/css/CSSSegmentedFontFace.h"
#include "core/css/FontFace.h"
+#include "wtf/Deque.h"
#include "wtf/Forward.h"
#include "wtf/PassRefPtr.h"
-#include "wtf/RefCounted.h"
#include "wtf/Vector.h"
namespace WebCore {
-class CSSSegmentedFontFace;
+class CSSFontSelector;
class Document;
class FontDescription;
+class RemoteFontFaceSource;
class SimpleFontData;
class StyleRuleFontFace;
-// FIXME: Can this be a subclass of FontFace?
-class CSSFontFace : public RefCounted<CSSFontFace> {
+class CSSFontFace FINAL : public NoBaseWillBeGarbageCollectedFinalized<CSSFontFace> {
public:
- static PassRefPtr<CSSFontFace> create(PassRefPtr<FontFace> fontFace) { return adoptRef(new CSSFontFace(fontFace)); }
- static PassRefPtr<CSSFontFace> createFromStyleRule(Document*, const StyleRuleFontFace*);
-
+ struct UnicodeRange;
class UnicodeRangeSet;
- ~CSSFontFace();
+ CSSFontFace(FontFace* fontFace, Vector<UnicodeRange>& ranges)
+ : m_ranges(ranges)
+ , m_segmentedFontFace(nullptr)
+ , m_fontFace(fontFace)
+ {
+ ASSERT(m_fontFace);
+ }
- FontFace* fontFace() const { return m_fontFace.get(); }
+ FontFace* fontFace() const { return m_fontFace; }
UnicodeRangeSet& ranges() { return m_ranges; }
void setSegmentedFontFace(CSSSegmentedFontFace*);
- void clearSegmentedFontFace() { m_segmentedFontFace = 0; }
+ void clearSegmentedFontFace() { m_segmentedFontFace = nullptr; }
- bool isLoaded() const;
- bool isValid() const;
+ bool isValid() const { return !m_sources.isEmpty(); }
- void addSource(PassOwnPtr<CSSFontFaceSource>);
+ void addSource(PassOwnPtrWillBeRawPtr<CSSFontFaceSource>);
- void beginLoadIfNeeded(CSSFontFaceSource*);
- void fontLoaded(CSSFontFaceSource*);
+ void didBeginLoad();
+ void fontLoaded(RemoteFontFaceSource*);
+ void fontLoadWaitLimitExceeded(RemoteFontFaceSource*);
PassRefPtr<SimpleFontData> getFontData(const FontDescription&);
@@ -78,6 +83,8 @@ public:
UChar32 from() const { return m_from; }
UChar32 to() const { return m_to; }
bool contains(UChar32 c) const { return m_from <= c && c <= m_to; }
+ bool operator<(const UnicodeRange& other) const { return m_from < other.m_from; }
+ bool operator<(UChar32 c) const { return m_to < c; }
private:
UChar32 m_from;
@@ -86,7 +93,8 @@ public:
class UnicodeRangeSet {
public:
- void add(UChar32 from, UChar32 to) { m_ranges.append(UnicodeRange(from, to)); }
+ explicit UnicodeRangeSet(const Vector<UnicodeRange>&);
+ bool contains(UChar32) const;
bool intersectsWith(const String&) const;
bool isEntireRange() const { return m_ranges.isEmpty(); }
size_t size() const { return m_ranges.size(); }
@@ -96,23 +104,21 @@ public:
};
FontFace::LoadStatus loadStatus() const { return m_fontFace->loadStatus(); }
- void willUseFontData(const FontDescription&);
+ bool maybeScheduleFontLoad(const FontDescription&, UChar32);
+ void load();
+ void load(const FontDescription&);
+
+ bool hadBlankText() { return isValid() && m_sources.first()->hadBlankText(); }
+
+ void trace(Visitor*);
private:
- CSSFontFace(PassRefPtr<FontFace> fontFace)
- : m_segmentedFontFace(0)
- , m_activeSource(0)
- , m_fontFace(fontFace)
- {
- ASSERT(m_fontFace);
- }
void setLoadStatus(FontFace::LoadStatus);
UnicodeRangeSet m_ranges;
- CSSSegmentedFontFace* m_segmentedFontFace;
- Vector<OwnPtr<CSSFontFaceSource> > m_sources;
- CSSFontFaceSource* m_activeSource;
- RefPtr<FontFace> m_fontFace;
+ RawPtrWillBeMember<CSSSegmentedFontFace> m_segmentedFontFace;
+ WillBeHeapDeque<OwnPtrWillBeMember<CSSFontFaceSource> > m_sources;
+ RawPtrWillBeMember<FontFace> m_fontFace;
};
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.cpp
index 95aa3b27328..5d0d06b1d96 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.cpp
@@ -61,4 +61,10 @@ const AtomicString& CSSFontFaceLoadEvent::interfaceName() const
return EventNames::CSSFontFaceLoadEvent;
}
+void CSSFontFaceLoadEvent::trace(Visitor* visitor)
+{
+ visitor->trace(m_fontfaces);
+ Event::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.h b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.h
index e77ca32e86b..8597efc2b24 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceLoadEvent.h
@@ -34,7 +34,6 @@
#include "core/css/FontFace.h"
#include "core/dom/DOMError.h"
#include "core/events/Event.h"
-#include "core/events/ThreadLocalEventNames.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefPtr.h"
@@ -44,28 +43,30 @@ struct CSSFontFaceLoadEventInit : public EventInit {
FontFaceArray fontfaces;
};
-class CSSFontFaceLoadEvent : public Event {
+class CSSFontFaceLoadEvent FINAL : public Event {
public:
- static PassRefPtr<CSSFontFaceLoadEvent> create()
+ static PassRefPtrWillBeRawPtr<CSSFontFaceLoadEvent> create()
{
- return adoptRef<CSSFontFaceLoadEvent>(new CSSFontFaceLoadEvent());
+ return adoptRefWillBeNoop(new CSSFontFaceLoadEvent());
}
- static PassRefPtr<CSSFontFaceLoadEvent> create(const AtomicString& type, const CSSFontFaceLoadEventInit& initializer)
+ static PassRefPtrWillBeRawPtr<CSSFontFaceLoadEvent> create(const AtomicString& type, const CSSFontFaceLoadEventInit& initializer)
{
- return adoptRef<CSSFontFaceLoadEvent>(new CSSFontFaceLoadEvent(type, initializer));
+ return adoptRefWillBeNoop(new CSSFontFaceLoadEvent(type, initializer));
}
- static PassRefPtr<CSSFontFaceLoadEvent> createForFontFaces(const AtomicString& type, const FontFaceArray& fontfaces = FontFaceArray())
+ static PassRefPtrWillBeRawPtr<CSSFontFaceLoadEvent> createForFontFaces(const AtomicString& type, const FontFaceArray& fontfaces = FontFaceArray())
{
- return adoptRef<CSSFontFaceLoadEvent>(new CSSFontFaceLoadEvent(type, fontfaces));
+ return adoptRefWillBeNoop(new CSSFontFaceLoadEvent(type, fontfaces));
}
virtual ~CSSFontFaceLoadEvent();
FontFaceArray fontfaces() const { return m_fontfaces; }
- virtual const AtomicString& interfaceName() const;
+ virtual const AtomicString& interfaceName() const OVERRIDE;
+
+ virtual void trace(Visitor*) OVERRIDE;
private:
CSSFontFaceLoadEvent();
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.cpp
index d6357bd3250..276ffbfc578 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.cpp
@@ -37,8 +37,10 @@ CSSFontFaceRule::CSSFontFaceRule(StyleRuleFontFace* fontFaceRule, CSSStyleSheet*
CSSFontFaceRule::~CSSFontFaceRule()
{
+#if !ENABLE(OILPAN)
if (m_propertiesCSSOMWrapper)
m_propertiesCSSOMWrapper->clearParentRule();
+#endif
}
CSSStyleDeclaration* CSSFontFaceRule::style() const
@@ -52,7 +54,7 @@ String CSSFontFaceRule::cssText() const
{
StringBuilder result;
result.appendLiteral("@font-face { ");
- String descs = m_fontFaceRule->properties()->asText();
+ String descs = m_fontFaceRule->properties().asText();
result.append(descs);
if (!descs.isEmpty())
result.append(' ');
@@ -68,4 +70,11 @@ void CSSFontFaceRule::reattach(StyleRuleBase* rule)
m_propertiesCSSOMWrapper->reattach(m_fontFaceRule->mutableProperties());
}
+void CSSFontFaceRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_fontFaceRule);
+ visitor->trace(m_propertiesCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.h b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.h
index 0b88f9b2eee..866389828bd 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceRule.h
@@ -23,6 +23,7 @@
#define CSSFontFaceRule_h
#include "core/css/CSSRule.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -30,9 +31,12 @@ class CSSStyleDeclaration;
class StyleRuleFontFace;
class StyleRuleCSSStyleDeclaration;
-class CSSFontFaceRule : public CSSRule {
+class CSSFontFaceRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSFontFaceRule> create(StyleRuleFontFace* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSFontFaceRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSFontFaceRule> create(StyleRuleFontFace* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSFontFaceRule(rule, sheet));
+ }
virtual ~CSSFontFaceRule();
@@ -44,11 +48,13 @@ public:
StyleRuleFontFace* styleRule() const { return m_fontFaceRule.get(); }
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSFontFaceRule(StyleRuleFontFace*, CSSStyleSheet* parent);
- RefPtr<StyleRuleFontFace> m_fontFaceRule;
- mutable RefPtr<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
+ RefPtrWillBeMember<StyleRuleFontFace> m_fontFaceRule;
+ mutable RefPtrWillBeMember<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSFontFaceRule, FONT_FACE_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.cpp
index d235aea7edf..39dfcd7c291 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.cpp
@@ -26,292 +26,46 @@
#include "config.h"
#include "core/css/CSSFontFaceSource.h"
-#include "RuntimeEnabledFeatures.h"
-#include "core/css/CSSCustomFontData.h"
#include "core/css/CSSFontFace.h"
-#include "platform/fonts/FontCache.h"
+#include "platform/fonts/FontCacheKey.h"
#include "platform/fonts/FontDescription.h"
#include "platform/fonts/SimpleFontData.h"
-#include "public/platform/Platform.h"
-#include "wtf/CurrentTime.h"
-
-#if ENABLE(SVG_FONTS)
-#include "SVGNames.h"
-#include "core/svg/SVGFontData.h"
-#include "core/svg/SVGFontElement.h"
-#include "core/svg/SVGFontFaceElement.h"
-#endif
namespace WebCore {
-CSSFontFaceSource::CSSFontFaceSource(const String& str, FontResource* font)
- : m_string(str)
- , m_font(font)
- , m_face(0)
-#if ENABLE(SVG_FONTS)
- , m_hasExternalSVGFont(false)
-#endif
+CSSFontFaceSource::CSSFontFaceSource()
+ : m_face(nullptr)
{
- if (m_font)
- m_font->addClient(this);
}
CSSFontFaceSource::~CSSFontFaceSource()
{
- if (m_font)
- m_font->removeClient(this);
- pruneTable();
-}
-
-void CSSFontFaceSource::pruneTable()
-{
- if (m_fontDataTable.isEmpty())
- return;
-
- for (FontDataTable::iterator it = m_fontDataTable.begin(); it != m_fontDataTable.end(); ++it) {
- SimpleFontData* fontData = it->value.get();
- if (fontData && fontData->customFontData())
- fontData->customFontData()->clearCSSFontFaceSource();
- }
- m_fontDataTable.clear();
-}
-
-bool CSSFontFaceSource::isLocal() const
-{
- if (m_font)
- return false;
-#if ENABLE(SVG_FONTS)
- if (m_svgFontFaceElement)
- return false;
-#endif
- return true;
-}
-
-bool CSSFontFaceSource::isLoading() const
-{
- if (m_font)
- return !m_font->stillNeedsLoad() && !m_font->isLoaded();
- return false;
-}
-
-bool CSSFontFaceSource::isLoaded() const
-{
- if (m_font)
- return m_font->isLoaded();
- return true;
-}
-
-bool CSSFontFaceSource::isValid() const
-{
- if (m_font)
- return !m_font->errorOccurred();
- return true;
-}
-
-void CSSFontFaceSource::didStartFontLoad(FontResource*)
-{
- // Avoid duplicated reports when multiple CSSFontFaceSource are registered
- // at this FontResource.
- if (!m_fontDataTable.isEmpty())
- m_histograms.loadStarted();
-}
-
-void CSSFontFaceSource::fontLoaded(FontResource*)
-{
- if (!m_fontDataTable.isEmpty())
- m_histograms.recordRemoteFont(m_font.get());
-
- pruneTable();
- if (m_face)
- m_face->fontLoaded(this);
}
PassRefPtr<SimpleFontData> CSSFontFaceSource::getFontData(const FontDescription& fontDescription)
{
// If the font hasn't loaded or an error occurred, then we've got nothing.
if (!isValid())
- return 0;
+ return nullptr;
if (isLocal()) {
// We're local. Just return a SimpleFontData from the normal cache.
- // We don't want to check alternate font family names here, so pass true as the checkingAlternateName parameter.
- RefPtr<SimpleFontData> fontData = FontCache::fontCache()->getFontData(fontDescription, m_string, true);
- m_histograms.recordLocalFont(fontData);
- return fontData;
+ return createFontData(fontDescription);
}
// See if we have a mapping in our FontData cache.
AtomicString emptyFontFamily = "";
FontCacheKey key = fontDescription.cacheKey(emptyFontFamily);
- RefPtr<SimpleFontData>& fontData = m_fontDataTable.add(key.hash(), 0).iterator->value;
- if (fontData)
- return fontData; // No release, because fontData is a reference to a RefPtr that is held in the m_fontDataTable.
-
- // If we are still loading, then we let the system pick a font.
- if (isLoaded()) {
- if (m_font) {
-#if ENABLE(SVG_FONTS)
- if (m_hasExternalSVGFont) {
- // For SVG fonts parse the external SVG document, and extract the <font> element.
- if (!m_font->ensureSVGFontData())
- return 0;
-
- if (!m_externalSVGFontElement) {
- String fragmentIdentifier;
- size_t start = m_string.find('#');
- if (start != kNotFound)
- fragmentIdentifier = m_string.string().substring(start + 1);
- m_externalSVGFontElement = m_font->getSVGFontById(fragmentIdentifier);
- }
-
- if (!m_externalSVGFontElement)
- return 0;
-
- SVGFontFaceElement* fontFaceElement = 0;
-
- // Select first <font-face> child
- for (Node* fontChild = m_externalSVGFontElement->firstChild(); fontChild; fontChild = fontChild->nextSibling()) {
- if (fontChild->hasTagName(SVGNames::font_faceTag)) {
- fontFaceElement = toSVGFontFaceElement(fontChild);
- break;
- }
- }
-
- if (fontFaceElement) {
- if (!m_svgFontFaceElement) {
- // We're created using a CSS @font-face rule, that means we're not associated with a SVGFontFaceElement.
- // Use the imported <font-face> tag as referencing font-face element for these cases.
- m_svgFontFaceElement = fontFaceElement;
- }
-
- fontData = SimpleFontData::create(
- SVGFontData::create(fontFaceElement),
- fontDescription.effectiveFontSize(),
- fontDescription.isSyntheticBold(),
- fontDescription.isSyntheticItalic());
- }
- } else
-#endif
- {
- // Create new FontPlatformData from our CGFontRef, point size and ATSFontRef.
- if (!m_font->ensureCustomFontData())
- return 0;
-
- fontData = SimpleFontData::create(
- m_font->platformDataFromCustomData(fontDescription.effectiveFontSize(),
- fontDescription.isSyntheticBold(), fontDescription.isSyntheticItalic(),
- fontDescription.orientation(), fontDescription.widthVariant()), CustomFontData::create(false));
- }
- } else {
-#if ENABLE(SVG_FONTS)
- // In-Document SVG Fonts
- if (m_svgFontFaceElement) {
- fontData = SimpleFontData::create(
- SVGFontData::create(m_svgFontFaceElement.get()),
- fontDescription.effectiveFontSize(),
- fontDescription.isSyntheticBold(),
- fontDescription.isSyntheticItalic());
- }
-#endif
- }
- } else {
- // This temporary font is not retained and should not be returned.
- FontCachePurgePreventer fontCachePurgePreventer;
- SimpleFontData* temporaryFont = FontCache::fontCache()->getNonRetainedLastResortFallbackFont(fontDescription);
- RefPtr<CSSCustomFontData> cssFontData = CSSCustomFontData::create(true);
- cssFontData->setCSSFontFaceSource(this);
- fontData = SimpleFontData::create(temporaryFont->platformData(), cssFontData);
- }
-
+ RefPtr<SimpleFontData>& fontData = m_fontDataTable.add(key.hash(), nullptr).storedValue->value;
+ if (!fontData)
+ fontData = createFontData(fontDescription);
return fontData; // No release, because fontData is a reference to a RefPtr that is held in the m_fontDataTable.
}
-#if ENABLE(SVG_FONTS)
-SVGFontFaceElement* CSSFontFaceSource::svgFontFaceElement() const
-{
- return m_svgFontFaceElement.get();
-}
-
-void CSSFontFaceSource::setSVGFontFaceElement(PassRefPtr<SVGFontFaceElement> element)
-{
- m_svgFontFaceElement = element;
-}
-
-bool CSSFontFaceSource::isSVGFontFaceSource() const
-{
- return m_svgFontFaceElement || m_hasExternalSVGFont;
-}
-#endif
-
-bool CSSFontFaceSource::ensureFontData()
-{
- if (!m_font)
- return false;
-#if ENABLE(SVG_FONTS)
- if (m_hasExternalSVGFont)
- return m_font->ensureSVGFontData();
-#endif
- return m_font->ensureCustomFontData();
-}
-
-bool CSSFontFaceSource::isLocalFontAvailable(const FontDescription& fontDescription)
-{
- if (!isLocal())
- return false;
- return FontCache::fontCache()->isPlatformFontAvailable(fontDescription, m_string);
-}
-
-void CSSFontFaceSource::beginLoadIfNeeded()
+void CSSFontFaceSource::trace(Visitor* visitor)
{
- if (m_face && m_font)
- m_face->beginLoadIfNeeded(this);
-}
-
-void CSSFontFaceSource::FontLoadHistograms::loadStarted()
-{
- if (!m_loadStartTime)
- m_loadStartTime = currentTimeMS();
-}
-
-void CSSFontFaceSource::FontLoadHistograms::recordLocalFont(bool loadSuccess)
-{
- if (!m_loadStartTime) {
- blink::Platform::current()->histogramEnumeration("WebFont.LocalFontUsed", loadSuccess ? 1 : 0, 2);
- m_loadStartTime = -1; // Do not count this font again.
- }
-}
-
-void CSSFontFaceSource::FontLoadHistograms::recordRemoteFont(const FontResource* font)
-{
- if (m_loadStartTime > 0 && font && !font->isLoading()) {
- int duration = static_cast<int>(currentTimeMS() - m_loadStartTime);
- blink::Platform::current()->histogramCustomCounts(histogramName(font), duration, 0, 10000, 50);
- m_loadStartTime = -1;
-
- enum { Miss, Hit, DataUrl, CacheHitEnumMax };
- int histogramValue = font->url().protocolIsData() ? DataUrl
- : font->response().wasCached() ? Hit
- : Miss;
- blink::Platform::current()->histogramEnumeration("WebFont.CacheHit", histogramValue, CacheHitEnumMax);
- }
-}
-
-const char* CSSFontFaceSource::FontLoadHistograms::histogramName(const FontResource* font)
-{
- if (font->errorOccurred())
- return "WebFont.DownloadTime.LoadError";
-
- unsigned size = font->encodedSize();
- if (size < 10 * 1024)
- return "WebFont.DownloadTime.0.Under10KB";
- if (size < 50 * 1024)
- return "WebFont.DownloadTime.1.10KBTo50KB";
- if (size < 100 * 1024)
- return "WebFont.DownloadTime.2.50KBTo100KB";
- if (size < 1024 * 1024)
- return "WebFont.DownloadTime.3.100KBTo1MB";
- return "WebFont.DownloadTime.4.Over1MB";
+ visitor->trace(m_face);
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.h b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.h
index 8ba3f027534..47da18a1ae2 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSource.h
@@ -26,11 +26,8 @@
#ifndef CSSFontFaceSource_h
#define CSSFontFaceSource_h
-#include "core/fetch/FontResource.h"
-#include "core/fetch/ResourcePtr.h"
-#include "platform/Timer.h"
+#include "platform/heap/Handle.h"
#include "wtf/HashMap.h"
-#include "wtf/text/AtomicString.h"
namespace WebCore {
@@ -38,69 +35,37 @@ class FontResource;
class CSSFontFace;
class FontDescription;
class SimpleFontData;
-#if ENABLE(SVG_FONTS)
-class SVGFontElement;
-class SVGFontFaceElement;
-#endif
-
-class CSSFontFaceSource : public FontResourceClient {
+class CSSFontFaceSource : public NoBaseWillBeGarbageCollectedFinalized<CSSFontFaceSource> {
public:
- CSSFontFaceSource(const String&, FontResource* = 0);
virtual ~CSSFontFaceSource();
- bool isLocal() const;
- bool isLoading() const;
- bool isLoaded() const;
- bool isValid() const;
+ virtual bool isLocal() const { return false; }
+ virtual bool isLoading() const { return false; }
+ virtual bool isLoaded() const { return true; }
+ virtual bool isValid() const { return true; }
- FontResource* resource() { return m_font.get(); }
+ virtual FontResource* resource() { return 0; }
void setFontFace(CSSFontFace* face) { m_face = face; }
- virtual void didStartFontLoad(FontResource*) OVERRIDE;
- virtual void fontLoaded(FontResource*);
-
PassRefPtr<SimpleFontData> getFontData(const FontDescription&);
-#if ENABLE(SVG_FONTS)
- SVGFontFaceElement* svgFontFaceElement() const;
- void setSVGFontFaceElement(PassRefPtr<SVGFontFaceElement>);
- bool isSVGFontFaceSource() const;
- void setHasExternalSVGFont(bool value) { m_hasExternalSVGFont = value; }
-#endif
+ virtual bool isLocalFontAvailable(const FontDescription&) { return false; }
+ virtual void beginLoadIfNeeded() { }
- bool ensureFontData();
- bool isLocalFontAvailable(const FontDescription&);
- void beginLoadIfNeeded();
+ // For UMA reporting
+ virtual bool hadBlankText() { return false; }
+
+ virtual void trace(Visitor*);
+
+protected:
+ CSSFontFaceSource();
+ virtual PassRefPtr<SimpleFontData> createFontData(const FontDescription&) = 0;
-private:
typedef HashMap<unsigned, RefPtr<SimpleFontData> > FontDataTable; // The hash key is composed of size synthetic styles.
- class FontLoadHistograms {
- public:
- FontLoadHistograms() : m_loadStartTime(0) { }
- void loadStarted();
- void recordLocalFont(bool loadSuccess);
- void recordRemoteFont(const FontResource*);
- private:
- const char* histogramName(const FontResource*);
- double m_loadStartTime;
- };
-
- void pruneTable();
- void startLoadingTimerFired(Timer<CSSFontFaceSource>*);
-
- AtomicString m_string; // URI for remote, built-in font name for local.
- ResourcePtr<FontResource> m_font; // For remote fonts, a pointer to our cached resource.
- CSSFontFace* m_face; // Our owning font face.
+ RawPtrWillBeMember<CSSFontFace> m_face; // Our owning font face.
FontDataTable m_fontDataTable;
- FontLoadHistograms m_histograms;
-
-#if ENABLE(SVG_FONTS)
- RefPtr<SVGFontFaceElement> m_svgFontFaceElement;
- RefPtr<SVGFontElement> m_externalSVGFontElement;
- bool m_hasExternalSVGFont;
-#endif
};
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.cpp
index 9e7f212554a..f0cde2c59ab 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.cpp
@@ -26,7 +26,7 @@
#include "config.h"
#include "core/css/CSSFontFaceSrcValue.h"
-#include "FetchInitiatorTypeNames.h"
+#include "core/FetchInitiatorTypeNames.h"
#include "core/css/StyleSheetContents.h"
#include "core/dom/Document.h"
#include "core/dom/Node.h"
@@ -81,12 +81,6 @@ String CSSFontFaceSrcValue::customCSSText() const
return result.toString();
}
-void CSSFontFaceSrcValue::addSubresourceStyleURLs(ListHashSet<KURL>& urls, const StyleSheetContents* styleSheet) const
-{
- if (!isLocal())
- addSubresourceURL(urls, styleSheet->completeURL(m_resource));
-}
-
bool CSSFontFaceSrcValue::hasFailedOrCanceledSubresources() const
{
if (!m_fetched)
@@ -94,15 +88,44 @@ bool CSSFontFaceSrcValue::hasFailedOrCanceledSubresources() const
return m_fetched->loadFailedOrCanceled();
}
+bool CSSFontFaceSrcValue::shouldSetCrossOriginAccessControl(const KURL& resource, SecurityOrigin* securityOrigin)
+{
+ if (resource.isLocalFile() || resource.protocolIsData())
+ return false;
+ return !securityOrigin->canRequest(resource);
+}
+
FontResource* CSSFontFaceSrcValue::fetch(Document* document)
{
if (!m_fetched) {
FetchRequest request(ResourceRequest(document->completeURL(m_resource)), FetchInitiatorTypeNames::css);
+ SecurityOrigin* securityOrigin = document->securityOrigin();
+ if (shouldSetCrossOriginAccessControl(request.url(), securityOrigin)) {
+ request.setCrossOriginAccessControl(securityOrigin, DoNotAllowStoredCredentials);
+ }
+ request.mutableResourceRequest().setHTTPReferrer(m_referrer);
m_fetched = document->fetcher()->fetchFont(request);
+ } else {
+ // FIXME: CSSFontFaceSrcValue::fetch is invoked when @font-face rule
+ // is processed by StyleResolver / StyleEngine.
+ restoreCachedResourceIfNeeded(document);
}
return m_fetched.get();
}
+void CSSFontFaceSrcValue::restoreCachedResourceIfNeeded(Document* document)
+{
+ ASSERT(m_fetched);
+ ASSERT(document && document->fetcher());
+
+ const String resourceURL = document->completeURL(m_resource);
+ if (document->fetcher()->cachedResource(KURL(ParsedURLString, resourceURL)))
+ return;
+
+ FetchRequest request(ResourceRequest(resourceURL), FetchInitiatorTypeNames::css);
+ document->fetcher()->requestLoadStarted(m_fetched.get(), request, ResourceFetcher::ResourceLoadingFromCache);
+}
+
bool CSSFontFaceSrcValue::equals(const CSSFontFaceSrcValue& other) const
{
return m_isLocal == other.m_isLocal && m_format == other.m_format && m_resource == other.m_resource;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.h b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.h
index 1be94d687ff..83f26f7ee64 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceSrcValue.h
@@ -28,6 +28,7 @@
#include "core/css/CSSValue.h"
#include "core/fetch/ResourcePtr.h"
+#include "platform/weborigin/Referrer.h"
#include "wtf/PassRefPtr.h"
#include "wtf/text/WTFString.h"
@@ -39,13 +40,13 @@ class SVGFontFaceElement;
class CSSFontFaceSrcValue : public CSSValue {
public:
- static PassRefPtr<CSSFontFaceSrcValue> create(const String& resource)
+ static PassRefPtrWillBeRawPtr<CSSFontFaceSrcValue> create(const String& resource)
{
- return adoptRef(new CSSFontFaceSrcValue(resource, false));
+ return adoptRefWillBeNoop(new CSSFontFaceSrcValue(resource, false));
}
- static PassRefPtr<CSSFontFaceSrcValue> createLocal(const String& resource)
+ static PassRefPtrWillBeRawPtr<CSSFontFaceSrcValue> createLocal(const String& resource)
{
- return adoptRef(new CSSFontFaceSrcValue(resource, true));
+ return adoptRefWillBeNoop(new CSSFontFaceSrcValue(resource, true));
}
const String& resource() const { return m_resource; }
@@ -53,6 +54,7 @@ public:
bool isLocal() const { return m_isLocal; }
void setFormat(const String& format) { m_format = format; }
+ void setReferrer(const Referrer& referrer) { m_referrer = referrer; }
bool isSupportedFormat() const;
@@ -65,14 +67,14 @@ public:
String customCSSText() const;
- void addSubresourceStyleURLs(ListHashSet<KURL>&, const StyleSheetContents*) const;
-
bool hasFailedOrCanceledSubresources() const;
FontResource* fetch(Document*);
bool equals(const CSSFontFaceSrcValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSFontFaceSrcValue(const String& resource, bool local)
: CSSValue(FontFaceSrcClass)
@@ -84,8 +86,12 @@ private:
{
}
+ void restoreCachedResourceIfNeeded(Document*);
+ bool shouldSetCrossOriginAccessControl(const KURL& resource, SecurityOrigin*);
+
String m_resource;
String m_format;
+ Referrer m_referrer;
bool m_isLocal;
ResourcePtr<FontResource> m_fetched;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFaceTest.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceTest.cpp
new file mode 100644
index 00000000000..87b0bab86fd
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFaceTest.cpp
@@ -0,0 +1,90 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/CSSFontFace.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+static const UChar hiraganaA[2] = { 0x3042, 0 };
+
+TEST(CSSFontFace, UnicodeRangeSetEmpty)
+{
+ Vector<CSSFontFace::UnicodeRange> ranges;
+ CSSFontFace::UnicodeRangeSet set(ranges);
+ EXPECT_TRUE(set.isEntireRange());
+ EXPECT_EQ(0u, set.size());
+ EXPECT_FALSE(set.intersectsWith(String()));
+ EXPECT_TRUE(set.intersectsWith(String("a")));
+ EXPECT_TRUE(set.intersectsWith(String(hiraganaA)));
+}
+
+TEST(CSSFontFace, UnicodeRangeSetSingleCharacter)
+{
+ Vector<CSSFontFace::UnicodeRange> ranges;
+ ranges.append(CSSFontFace::UnicodeRange('b', 'b'));
+ CSSFontFace::UnicodeRangeSet set(ranges);
+ EXPECT_FALSE(set.isEntireRange());
+ EXPECT_FALSE(set.intersectsWith(String()));
+ EXPECT_FALSE(set.intersectsWith(String("a")));
+ EXPECT_TRUE(set.intersectsWith(String("b")));
+ EXPECT_FALSE(set.intersectsWith(String("c")));
+ EXPECT_TRUE(set.intersectsWith(String("abc")));
+ EXPECT_FALSE(set.intersectsWith(String(hiraganaA)));
+ ASSERT_EQ(1u, set.size());
+ EXPECT_EQ('b', set.rangeAt(0).from());
+ EXPECT_EQ('b', set.rangeAt(0).to());
+}
+
+TEST(CSSFontFace, UnicodeRangeSetTwoRanges)
+{
+ Vector<CSSFontFace::UnicodeRange> ranges;
+ ranges.append(CSSFontFace::UnicodeRange('6', '7'));
+ ranges.append(CSSFontFace::UnicodeRange('2', '4'));
+ CSSFontFace::UnicodeRangeSet set(ranges);
+ EXPECT_FALSE(set.isEntireRange());
+ EXPECT_FALSE(set.intersectsWith(String()));
+ EXPECT_FALSE(set.intersectsWith(String("1")));
+ EXPECT_TRUE(set.intersectsWith(String("2")));
+ EXPECT_TRUE(set.intersectsWith(String("3")));
+ EXPECT_TRUE(set.intersectsWith(String("4")));
+ EXPECT_FALSE(set.intersectsWith(String("5")));
+ EXPECT_TRUE(set.intersectsWith(String("6")));
+ EXPECT_TRUE(set.intersectsWith(String("7")));
+ EXPECT_FALSE(set.intersectsWith(String("8")));
+ ASSERT_EQ(2u, set.size());
+ EXPECT_EQ('2', set.rangeAt(0).from());
+ EXPECT_EQ('4', set.rangeAt(0).to());
+ EXPECT_EQ('6', set.rangeAt(1).from());
+ EXPECT_EQ('7', set.rangeAt(1).to());
+}
+
+TEST(CSSFontFace, UnicodeRangeSetOverlap)
+{
+ Vector<CSSFontFace::UnicodeRange> ranges;
+ ranges.append(CSSFontFace::UnicodeRange('0', '2'));
+ ranges.append(CSSFontFace::UnicodeRange('1', '1'));
+ ranges.append(CSSFontFace::UnicodeRange('3', '5'));
+ ranges.append(CSSFontFace::UnicodeRange('4', '6'));
+ CSSFontFace::UnicodeRangeSet set(ranges);
+ ASSERT_EQ(1u, set.size());
+ EXPECT_EQ('0', set.rangeAt(0).from());
+ EXPECT_EQ('6', set.rangeAt(0).to());
+}
+
+TEST(CSSFontFace, UnicodeRangeSetNon8Bit)
+{
+ Vector<CSSFontFace::UnicodeRange> ranges;
+ ranges.append(CSSFontFace::UnicodeRange(0x3042, 0x3042));
+ CSSFontFace::UnicodeRangeSet set(ranges);
+ ASSERT_EQ(1u, set.size());
+ EXPECT_EQ(0x3042, set.rangeAt(0).from());
+ EXPECT_EQ(0x3042, set.rangeAt(0).to());
+ EXPECT_FALSE(set.intersectsWith(String("a")));
+ EXPECT_TRUE(set.intersectsWith(String(hiraganaA)));
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontFeatureValue.h b/chromium/third_party/WebKit/Source/core/css/CSSFontFeatureValue.h
index 8a0367fabe3..fc841792619 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontFeatureValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontFeatureValue.h
@@ -33,9 +33,9 @@ namespace WebCore {
class CSSFontFeatureValue : public CSSValue {
public:
- static PassRefPtr<CSSFontFeatureValue> create(const AtomicString& tag, int value)
+ static PassRefPtrWillBeRawPtr<CSSFontFeatureValue> create(const AtomicString& tag, int value)
{
- return adoptRef(new CSSFontFeatureValue(tag, value));
+ return adoptRefWillBeNoop(new CSSFontFeatureValue(tag, value));
}
const AtomicString& tag() const { return m_tag; }
@@ -44,6 +44,8 @@ public:
bool equals(const CSSFontFeatureValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSFontFeatureValue(const AtomicString& tag, int value);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.cpp
index 9b83e9e2182..2f1019c3312 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.cpp
@@ -27,87 +27,25 @@
#include "config.h"
#include "core/css/CSSFontSelector.h"
-#include "RuntimeEnabledFeatures.h"
-#include "core/css/CSSFontFace.h"
-#include "core/css/CSSFontFaceRule.h"
-#include "core/css/CSSFontFaceSource.h"
+#include "core/css/CSSFontSelectorClient.h"
#include "core/css/CSSSegmentedFontFace.h"
#include "core/css/CSSValueList.h"
+#include "core/css/FontFaceSet.h"
#include "core/css/resolver/StyleResolver.h"
#include "core/dom/Document.h"
-#include "core/fetch/FontResource.h"
-#include "core/fetch/ResourceFetcher.h"
-#include "core/loader/FrameLoader.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
+#include "core/loader/FrameLoader.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/fonts/FontCache.h"
#include "platform/fonts/SimpleFontData.h"
#include "wtf/text/AtomicString.h"
-using namespace std;
-
namespace WebCore {
-FontLoader::FontLoader(ResourceFetcher* resourceFetcher)
- : m_beginLoadingTimer(this, &FontLoader::beginLoadTimerFired)
- , m_resourceFetcher(resourceFetcher)
-{
-}
-
-void FontLoader::addFontToBeginLoading(FontResource* fontResource)
-{
- if (!m_resourceFetcher || !fontResource->stillNeedsLoad())
- return;
-
- m_fontsToBeginLoading.append(fontResource);
- // FIXME: Use RequestCountTracker??!!
- // Increment the request count now, in order to prevent didFinishLoad from being dispatched
- // after this font has been requested but before it began loading. Balanced by
- // decrementRequestCount() in beginLoadTimerFired() and in clearDocument().
- m_resourceFetcher->incrementRequestCount(fontResource);
- m_beginLoadingTimer.startOneShot(0);
-}
-
-void FontLoader::beginLoadTimerFired(Timer<WebCore::FontLoader>*)
-{
- loadPendingFonts();
-}
-
-void FontLoader::loadPendingFonts()
-{
- ASSERT(m_resourceFetcher);
-
- Vector<ResourcePtr<FontResource> > fontsToBeginLoading;
- fontsToBeginLoading.swap(m_fontsToBeginLoading);
-
- for (size_t i = 0; i < fontsToBeginLoading.size(); ++i) {
- fontsToBeginLoading[i]->beginLoadIfNeeded(m_resourceFetcher);
- // Balances incrementRequestCount() in beginLoadingFontSoon().
- m_resourceFetcher->decrementRequestCount(fontsToBeginLoading[i].get());
- }
-}
-
-void FontLoader::clearResourceFetcher()
-{
- if (!m_resourceFetcher) {
- ASSERT(m_fontsToBeginLoading.isEmpty());
- return;
- }
-
- m_beginLoadingTimer.stop();
-
- for (size_t i = 0; i < m_fontsToBeginLoading.size(); ++i) {
- // Balances incrementRequestCount() in beginLoadingFontSoon().
- m_resourceFetcher->decrementRequestCount(m_fontsToBeginLoading[i].get());
- }
-
- m_fontsToBeginLoading.clear();
- m_resourceFetcher = 0;
-}
-
CSSFontSelector::CSSFontSelector(Document* document)
: m_document(document)
- , m_fontLoader(document->fetcher())
+ , m_fontLoader(FontLoader::create(this, document->fetcher()))
, m_genericFontFamilySettings(document->frame()->settings()->genericFontFamilySettings())
{
// FIXME: An old comment used to say there was no need to hold a reference to m_document
@@ -117,33 +55,38 @@ CSSFontSelector::CSSFontSelector(Document* document)
ASSERT(m_document);
ASSERT(m_document->frame());
FontCache::fontCache()->addClient(this);
+ FontFaceSet::from(*document)->addFontFacesToFontFaceCache(&m_fontFaceCache, this);
}
CSSFontSelector::~CSSFontSelector()
{
+#if !ENABLE(OILPAN)
clearDocument();
FontCache::fontCache()->removeClient(this);
+#endif
}
-void CSSFontSelector::registerForInvalidationCallbacks(FontSelectorClient* client)
+void CSSFontSelector::registerForInvalidationCallbacks(CSSFontSelectorClient* client)
{
m_clients.add(client);
}
-void CSSFontSelector::unregisterForInvalidationCallbacks(FontSelectorClient* client)
+#if !ENABLE(OILPAN)
+void CSSFontSelector::unregisterForInvalidationCallbacks(CSSFontSelectorClient* client)
{
m_clients.remove(client);
}
+#endif
void CSSFontSelector::dispatchInvalidationCallbacks()
{
- Vector<FontSelectorClient*> clients;
+ WillBeHeapVector<RawPtrWillBeMember<CSSFontSelectorClient> > clients;
copyToVector(m_clients, clients);
for (size_t i = 0; i < clients.size(); ++i)
clients[i]->fontsNeedUpdate(this);
}
-void CSSFontSelector::fontLoaded()
+void CSSFontSelector::fontFaceInvalidated()
{
dispatchInvalidationCallbacks();
}
@@ -153,28 +96,18 @@ void CSSFontSelector::fontCacheInvalidated()
dispatchInvalidationCallbacks();
}
-void CSSFontSelector::addFontFaceRule(const StyleRuleFontFace* fontFaceRule, PassRefPtr<CSSFontFace> cssFontFace)
-{
- m_cssSegmentedFontFaceCache.add(this, fontFaceRule, cssFontFace);
-}
-
-void CSSFontSelector::removeFontFaceRule(const StyleRuleFontFace* fontFaceRule)
-{
- m_cssSegmentedFontFaceCache.remove(fontFaceRule);
-}
-
static AtomicString familyNameFromSettings(const GenericFontFamilySettings& settings, const FontDescription& fontDescription, const AtomicString& genericFamilyName)
{
UScriptCode script = fontDescription.script();
#if OS(ANDROID)
- if (fontDescription.genericFamily() == FontDescription::StandardFamily && !fontDescription.isSpecifiedFont())
+ if (fontDescription.genericFamily() == FontDescription::StandardFamily)
return FontCache::getGenericFamilyNameForScript(FontFamilyNames::webkit_standard, script);
if (genericFamilyName.startsWith("-webkit-"))
return FontCache::getGenericFamilyNameForScript(genericFamilyName, script);
#else
- if (fontDescription.genericFamily() == FontDescription::StandardFamily && !fontDescription.isSpecifiedFont())
+ if (fontDescription.genericFamily() == FontDescription::StandardFamily)
return settings.standard(script);
if (genericFamilyName == FontFamilyNames::webkit_serif)
return settings.serif(script);
@@ -196,43 +129,56 @@ static AtomicString familyNameFromSettings(const GenericFontFamilySettings& sett
PassRefPtr<FontData> CSSFontSelector::getFontData(const FontDescription& fontDescription, const AtomicString& familyName)
{
- if (CSSSegmentedFontFace* face = m_cssSegmentedFontFaceCache.get(fontDescription, familyName))
+ if (CSSSegmentedFontFace* face = m_fontFaceCache.get(fontDescription, familyName))
return face->getFontData(fontDescription);
// Try to return the correct font based off our settings, in case we were handed the generic font family name.
AtomicString settingsFamilyName = familyNameFromSettings(m_genericFontFamilySettings, fontDescription, familyName);
if (settingsFamilyName.isEmpty())
- return 0;
+ return nullptr;
return FontCache::fontCache()->getFontData(fontDescription, settingsFamilyName);
}
-CSSSegmentedFontFace* CSSFontSelector::getFontFace(const FontDescription& fontDescription, const AtomicString& familyName)
+void CSSFontSelector::willUseFontData(const FontDescription& fontDescription, const AtomicString& family, UChar32 character)
{
- return m_cssSegmentedFontFaceCache.get(fontDescription, familyName);
+ CSSSegmentedFontFace* face = m_fontFaceCache.get(fontDescription, family);
+ if (face)
+ face->willUseFontData(fontDescription, character);
}
-void CSSFontSelector::willUseFontData(const FontDescription& fontDescription, const AtomicString& family)
+bool CSSFontSelector::isPlatformFontAvailable(const FontDescription& fontDescription, const AtomicString& passedFamily)
{
- CSSSegmentedFontFace* face = getFontFace(fontDescription, family);
- if (face)
- face->willUseFontData(fontDescription);
+ AtomicString family = familyNameFromSettings(m_genericFontFamilySettings, fontDescription, passedFamily);
+ if (family.isEmpty())
+ family = passedFamily;
+ return FontCache::fontCache()->isPlatformFontAvailable(fontDescription, family);
}
+#if !ENABLE(OILPAN)
void CSSFontSelector::clearDocument()
{
- m_fontLoader.clearResourceFetcher();
- m_document = 0;
+ m_fontLoader->clearResourceFetcherAndFontSelector();
+ m_document = nullptr;
}
+#endif
-void CSSFontSelector::beginLoadingFontSoon(FontResource* font)
+void CSSFontSelector::updateGenericFontFamilySettings(Document& document)
{
- m_fontLoader.addFontToBeginLoading(font);
+ if (!document.settings())
+ return;
+ m_genericFontFamilySettings = document.settings()->genericFontFamilySettings();
+ // Need to increment FontFaceCache version to update RenderStyles.
+ m_fontFaceCache.incrementVersion();
}
-void CSSFontSelector::loadPendingFonts()
+void CSSFontSelector::trace(Visitor* visitor)
{
- m_fontLoader.loadPendingFonts();
+ visitor->trace(m_document);
+ visitor->trace(m_fontFaceCache);
+ visitor->trace(m_clients);
+ visitor->trace(m_fontLoader);
+ FontSelector::trace(visitor);
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.h b/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.h
index 34d33a8809d..94e2578ca1d 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontSelector.h
@@ -26,11 +26,11 @@
#ifndef CSSFontSelector_h
#define CSSFontSelector_h
-#include "core/css/CSSSegmentedFontFaceCache.h"
-#include "core/fetch/ResourcePtr.h"
-#include "platform/Timer.h"
+#include "core/css/FontFaceCache.h"
+#include "core/css/FontLoader.h"
#include "platform/fonts/FontSelector.h"
#include "platform/fonts/GenericFontFamilySettings.h"
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/HashMap.h"
#include "wtf/HashSet.h"
@@ -39,72 +39,63 @@ namespace WebCore {
class CSSFontFace;
class CSSFontFaceRule;
+class CSSFontSelectorClient;
class CSSSegmentedFontFace;
-class FontResource;
class Document;
class FontDescription;
class StyleRuleFontFace;
-class FontLoader {
+class CSSFontSelector FINAL : public FontSelector {
public:
- explicit FontLoader(ResourceFetcher*);
-
- void addFontToBeginLoading(FontResource*);
- void loadPendingFonts();
-
- void clearResourceFetcher();
-
-private:
- void beginLoadTimerFired(Timer<FontLoader>*);
-
- Timer<FontLoader> m_beginLoadingTimer;
- Vector<ResourcePtr<FontResource> > m_fontsToBeginLoading;
- ResourceFetcher* m_resourceFetcher;
-};
-
-class CSSFontSelector : public FontSelector {
-public:
- static PassRefPtr<CSSFontSelector> create(Document* document)
+ static PassRefPtrWillBeRawPtr<CSSFontSelector> create(Document* document)
{
- return adoptRef(new CSSFontSelector(document));
+ return adoptRefWillBeNoop(new CSSFontSelector(document));
}
virtual ~CSSFontSelector();
- virtual unsigned version() const OVERRIDE { return m_cssSegmentedFontFaceCache.version(); }
+ virtual unsigned version() const OVERRIDE { return m_fontFaceCache.version(); }
- virtual PassRefPtr<FontData> getFontData(const FontDescription&, const AtomicString&);
- CSSSegmentedFontFace* getFontFace(const FontDescription&, const AtomicString& family);
- virtual void willUseFontData(const FontDescription&, const AtomicString& family) OVERRIDE;
+ virtual PassRefPtr<FontData> getFontData(const FontDescription&, const AtomicString&) OVERRIDE;
+ virtual void willUseFontData(const FontDescription&, const AtomicString& family, UChar32) OVERRIDE;
+ bool isPlatformFontAvailable(const FontDescription&, const AtomicString& family);
+#if !ENABLE(OILPAN)
void clearDocument();
+#endif
- void addFontFaceRule(const StyleRuleFontFace*, PassRefPtr<CSSFontFace>);
- void removeFontFaceRule(const StyleRuleFontFace*);
+ void fontFaceInvalidated();
- void fontLoaded();
- virtual void fontCacheInvalidated();
+ // FontCacheClient implementation
+ virtual void fontCacheInvalidated() OVERRIDE;
- virtual void registerForInvalidationCallbacks(FontSelectorClient*);
- virtual void unregisterForInvalidationCallbacks(FontSelectorClient*);
+ void registerForInvalidationCallbacks(CSSFontSelectorClient*);
+#if !ENABLE(OILPAN)
+ void unregisterForInvalidationCallbacks(CSSFontSelectorClient*);
+#endif
Document* document() const { return m_document; }
+ FontFaceCache* fontFaceCache() { return &m_fontFaceCache; }
+ FontLoader* fontLoader() { return m_fontLoader.get(); }
const GenericFontFamilySettings& genericFontFamilySettings() const { return m_genericFontFamilySettings; }
+ void updateGenericFontFamilySettings(Document&);
- void beginLoadingFontSoon(FontResource*);
- void loadPendingFonts();
+ virtual void trace(Visitor*);
private:
explicit CSSFontSelector(Document*);
void dispatchInvalidationCallbacks();
- Document* m_document;
+ // FIXME: Oilpan: Ideally this should just be a traced Member but that will
+ // currently leak because RenderStyle and its data are not on the heap.
+ // See crbug.com/383860 for details.
+ RawPtrWillBeWeakMember<Document> m_document;
// FIXME: Move to Document or StyleEngine.
- CSSSegmentedFontFaceCache m_cssSegmentedFontFaceCache;
- HashSet<FontSelectorClient*> m_clients;
+ FontFaceCache m_fontFaceCache;
+ WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSFontSelectorClient> > m_clients;
- FontLoader m_fontLoader;
+ RefPtrWillBeMember<FontLoader> m_fontLoader;
GenericFontFamilySettings m_genericFontFamilySettings;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMapForEachCallback.h b/chromium/third_party/WebKit/Source/core/css/CSSFontSelectorClient.h
index 001ccbdcf74..5a8c1c0892a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMapForEachCallback.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontSelectorClient.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
+ * Copyright (C) 2014 Google Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -11,6 +11,9 @@
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@@ -25,24 +28,25 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef CSSVariablesMapForEachCallback_h
-#define CSSVariablesMapForEachCallback_h
+#ifndef CSSFontSelectorClient_h
+#define CSSFontSelectorClient_h
-#include "bindings/v8/ScriptValue.h"
-#include "wtf/RefCounted.h"
-#include "wtf/text/WTFString.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
-class CSSVariablesMap;
+class CSSFontSelector;
+class Visitor;
-class CSSVariablesMapForEachCallback {
+class CSSFontSelectorClient : public NoBaseWillBeGarbageCollectedFinalized<CSSFontSelectorClient> {
public:
- virtual ~CSSVariablesMapForEachCallback() { }
- virtual void handleItem(ScriptValue thisValue, const String& value, const String& name, CSSVariablesMap*) = 0;
- virtual void handleItem(const String& value, const String& name, CSSVariablesMap*) = 0;
+ virtual ~CSSFontSelectorClient() { }
+
+ virtual void fontsNeedUpdate(CSSFontSelector*) = 0;
+
+ virtual void trace(Visitor*) { }
};
} // namespace WebCore
-#endif // CSSVariablesMapForEachCallback_h
+#endif // CSSFontSelectorClient_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFontValue.cpp
index aee5a9726d6..522c7f81a53 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontValue.cpp
@@ -74,4 +74,16 @@ bool CSSFontValue::equals(const CSSFontValue& other) const
&& compareCSSValuePtr(family, other.family);
}
+void CSSFontValue::traceAfterDispatch(Visitor* visitor)
+{
+
+ visitor->trace(style);
+ visitor->trace(variant);
+ visitor->trace(weight);
+ visitor->trace(size);
+ visitor->trace(lineHeight);
+ visitor->trace(family);
+ CSSValue::traceAfterDispatch(visitor);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFontValue.h b/chromium/third_party/WebKit/Source/core/css/CSSFontValue.h
index f0c99d55326..892d4e24b82 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFontValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFontValue.h
@@ -32,21 +32,23 @@ class CSSValueList;
class CSSFontValue : public CSSValue {
public:
- static PassRefPtr<CSSFontValue> create()
+ static PassRefPtrWillBeRawPtr<CSSFontValue> create()
{
- return adoptRef(new CSSFontValue);
+ return adoptRefWillBeNoop(new CSSFontValue);
}
String customCSSText() const;
bool equals(const CSSFontValue&) const;
- RefPtr<CSSPrimitiveValue> style;
- RefPtr<CSSPrimitiveValue> variant;
- RefPtr<CSSPrimitiveValue> weight;
- RefPtr<CSSPrimitiveValue> size;
- RefPtr<CSSPrimitiveValue> lineHeight;
- RefPtr<CSSValueList> family;
+ void traceAfterDispatch(Visitor*);
+
+ RefPtrWillBeMember<CSSPrimitiveValue> style;
+ RefPtrWillBeMember<CSSPrimitiveValue> variant;
+ RefPtrWillBeMember<CSSPrimitiveValue> weight;
+ RefPtrWillBeMember<CSSPrimitiveValue> size;
+ RefPtrWillBeMember<CSSPrimitiveValue> lineHeight;
+ RefPtrWillBeMember<CSSValueList> family;
private:
CSSFontValue()
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.cpp
index 7cbbf86d06f..9fb04dc43e2 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.cpp
@@ -40,7 +40,7 @@ CSSFunctionValue::CSSFunctionValue(CSSParserFunction* function)
m_args = CSSValueList::createFromParserValueList(function->args.get());
}
-CSSFunctionValue::CSSFunctionValue(String name, PassRefPtr<CSSValueList> args)
+CSSFunctionValue::CSSFunctionValue(String name, PassRefPtrWillBeRawPtr<CSSValueList> args)
: CSSValue(FunctionClass)
, m_name(name)
, m_args(args)
@@ -62,4 +62,10 @@ bool CSSFunctionValue::equals(const CSSFunctionValue& other) const
return m_name == other.m_name && compareCSSValuePtr(m_args, other.m_args);
}
+void CSSFunctionValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_args);
+ CSSValue::traceAfterDispatch(visitor);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.h b/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.h
index 87fa8afacfb..aa678635978 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSFunctionValue.h
@@ -35,14 +35,14 @@ struct CSSParserFunction;
class CSSFunctionValue : public CSSValue {
public:
- static PassRefPtr<CSSFunctionValue> create(CSSParserFunction* function)
+ static PassRefPtrWillBeRawPtr<CSSFunctionValue> create(CSSParserFunction* function)
{
- return adoptRef(new CSSFunctionValue(function));
+ return adoptRefWillBeNoop(new CSSFunctionValue(function));
}
- static PassRefPtr<CSSFunctionValue> create(String name, PassRefPtr<CSSValueList> args)
+ static PassRefPtrWillBeRawPtr<CSSFunctionValue> create(String name, PassRefPtrWillBeRawPtr<CSSValueList> args)
{
- return adoptRef(new CSSFunctionValue(name, args));
+ return adoptRefWillBeNoop(new CSSFunctionValue(name, args));
}
String customCSSText() const;
@@ -51,12 +51,14 @@ public:
CSSValueList* arguments() const { return m_args.get(); }
+ void traceAfterDispatch(Visitor*);
+
private:
explicit CSSFunctionValue(CSSParserFunction*);
- CSSFunctionValue(String, PassRefPtr<CSSValueList>);
+ CSSFunctionValue(String, PassRefPtrWillBeRawPtr<CSSValueList>);
String m_name;
- RefPtr<CSSValueList> m_args;
+ RefPtrWillBeMember<CSSValueList> m_args;
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSFunctionValue, isFunctionValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.cpp
index 68269972045..277162fd89b 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.cpp
@@ -26,7 +26,7 @@
#include "config.h"
#include "core/css/CSSGradientValue.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
#include "core/css/CSSCalculationValue.h"
#include "core/css/CSSToLengthConversionData.h"
#include "core/dom/NodeRenderStyle.h"
@@ -39,19 +39,23 @@
#include "wtf/text/StringBuilder.h"
#include "wtf/text/WTFString.h"
-using namespace std;
-
namespace WebCore {
+void CSSGradientColorStop::trace(Visitor* visitor)
+{
+ visitor->trace(m_position);
+ visitor->trace(m_color);
+}
+
PassRefPtr<Image> CSSGradientValue::image(RenderObject* renderer, const IntSize& size)
{
if (size.isEmpty())
- return 0;
+ return nullptr;
bool cacheable = isCacheable();
if (cacheable) {
if (!clients().contains(renderer))
- return 0;
+ return nullptr;
// Need to look up our size. Create a string of width*height to use as a hash key.
Image* result = getImage(renderer, size);
@@ -63,7 +67,7 @@ PassRefPtr<Image> CSSGradientValue::image(RenderObject* renderer, const IntSize&
RefPtr<Gradient> gradient;
RenderStyle* rootStyle = renderer->document().documentElement()->renderStyle();
- CSSToLengthConversionData conversionData(renderer->style(), rootStyle);
+ CSSToLengthConversionData conversionData(renderer->style(), rootStyle, renderer->view());
if (isLinearGradientValue())
gradient = toCSSLinearGradientValue(this)->createGradient(conversionData, size);
else
@@ -106,7 +110,7 @@ struct GradientStop {
{ }
};
-PassRefPtr<CSSGradientValue> CSSGradientValue::gradientWithStylesResolved(const TextLinkColors& textLinkColors, Color currentColor)
+PassRefPtrWillBeRawPtr<CSSGradientValue> CSSGradientValue::gradientWithStylesResolved(const TextLinkColors& textLinkColors, Color currentColor)
{
bool derived = false;
for (unsigned i = 0; i < m_stops.size(); i++)
@@ -116,7 +120,7 @@ PassRefPtr<CSSGradientValue> CSSGradientValue::gradientWithStylesResolved(const
break;
}
- RefPtr<CSSGradientValue> result;
+ RefPtrWillBeRawPtr<CSSGradientValue> result = nullptr;
if (!derived)
result = this;
else if (isLinearGradientValue())
@@ -125,7 +129,7 @@ PassRefPtr<CSSGradientValue> CSSGradientValue::gradientWithStylesResolved(const
result = toCSSRadialGradientValue(this)->clone();
else {
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
for (unsigned i = 0; i < result->m_stops.size(); i++)
@@ -151,8 +155,6 @@ void CSSGradientValue::addStops(Gradient* gradient, const CSSToLengthConversionD
gradient->addColorStop(offset, stop.m_resolvedColor);
}
- // The back end already sorted the stops.
- gradient->setStopsSorted(true);
return;
}
@@ -262,7 +264,6 @@ void CSSGradientValue::addStops(Gradient* gradient, const CSSToLengthConversionD
stops.first().offset = 0;
stops.first().color = stops.last().color;
stops.shrink(1);
- numStops = 1;
} else {
float maxExtent = 1;
@@ -384,8 +385,6 @@ void CSSGradientValue::addStops(Gradient* gradient, const CSSToLengthConversionD
for (unsigned i = 0; i < numStops; i++)
gradient->addColorStop(stops[i].offset, stops[i].color);
-
- gradient->setStopsSorted(true);
}
static float positionFromValue(CSSPrimitiveValue* value, const CSSToLengthConversionData& conversionData, const IntSize& size, bool isHorizontal)
@@ -460,6 +459,16 @@ bool CSSGradientValue::knownToBeOpaque(const RenderObject*) const
return true;
}
+void CSSGradientValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_firstX);
+ visitor->trace(m_firstY);
+ visitor->trace(m_secondX);
+ visitor->trace(m_secondY);
+ visitor->trace(m_stops);
+ CSSImageGeneratorValue::traceAfterDispatch(visitor);
+}
+
String CSSLinearGradientValue::customCSSText() const
{
StringBuilder result;
@@ -733,6 +742,12 @@ bool CSSLinearGradientValue::equals(const CSSLinearGradientValue& other) const
return equalXandY && m_stops == other.m_stops;
}
+void CSSLinearGradientValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_angle);
+ CSSGradientValue::traceAfterDispatch(visitor);
+}
+
String CSSRadialGradientValue::customCSSText() const
{
StringBuilder result;
@@ -1039,10 +1054,10 @@ PassRefPtr<Gradient> CSSRadialGradientValue::createGradient(const CSSToLengthCon
// Horizontal
switch (fill) {
case ClosestSide: {
- float xDist = min(secondPoint.x(), size.width() - secondPoint.x());
- float yDist = min(secondPoint.y(), size.height() - secondPoint.y());
+ float xDist = std::min(secondPoint.x(), size.width() - secondPoint.x());
+ float yDist = std::min(secondPoint.y(), size.height() - secondPoint.y());
if (shape == Circle) {
- float smaller = min(xDist, yDist);
+ float smaller = std::min(xDist, yDist);
xDist = smaller;
yDist = smaller;
}
@@ -1051,10 +1066,10 @@ PassRefPtr<Gradient> CSSRadialGradientValue::createGradient(const CSSToLengthCon
break;
}
case FarthestSide: {
- float xDist = max(secondPoint.x(), size.width() - secondPoint.x());
- float yDist = max(secondPoint.y(), size.height() - secondPoint.y());
+ float xDist = std::max(secondPoint.x(), size.width() - secondPoint.x());
+ float yDist = std::max(secondPoint.y(), size.height() - secondPoint.y());
if (shape == Circle) {
- float larger = max(xDist, yDist);
+ float larger = std::max(xDist, yDist);
xDist = larger;
yDist = larger;
}
@@ -1070,8 +1085,8 @@ PassRefPtr<Gradient> CSSRadialGradientValue::createGradient(const CSSToLengthCon
else {
// If <shape> is ellipse, the gradient-shape has the same ratio of width to height
// that it would if closest-side or farthest-side were specified, as appropriate.
- float xDist = min(secondPoint.x(), size.width() - secondPoint.x());
- float yDist = min(secondPoint.y(), size.height() - secondPoint.y());
+ float xDist = std::min(secondPoint.x(), size.width() - secondPoint.x());
+ float yDist = std::min(secondPoint.y(), size.height() - secondPoint.y());
secondRadius = horizontalEllipseRadius(corner - secondPoint, xDist / yDist);
aspectRatio = xDist / yDist;
@@ -1087,8 +1102,8 @@ PassRefPtr<Gradient> CSSRadialGradientValue::createGradient(const CSSToLengthCon
else {
// If <shape> is ellipse, the gradient-shape has the same ratio of width to height
// that it would if closest-side or farthest-side were specified, as appropriate.
- float xDist = max(secondPoint.x(), size.width() - secondPoint.x());
- float yDist = max(secondPoint.y(), size.height() - secondPoint.y());
+ float xDist = std::max(secondPoint.x(), size.width() - secondPoint.x());
+ float yDist = std::max(secondPoint.y(), size.height() - secondPoint.y());
secondRadius = horizontalEllipseRadius(corner - secondPoint, xDist / yDist);
aspectRatio = xDist / yDist;
@@ -1161,4 +1176,15 @@ bool CSSRadialGradientValue::equals(const CSSRadialGradientValue& other) const
return equalShape && equalSizingBehavior && equalHorizontalAndVerticalSize && m_stops == other.m_stops;
}
+void CSSRadialGradientValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_firstRadius);
+ visitor->trace(m_secondRadius);
+ visitor->trace(m_shape);
+ visitor->trace(m_sizingBehavior);
+ visitor->trace(m_endHorizontalSize);
+ visitor->trace(m_endVerticalSize);
+ CSSGradientValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.h b/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.h
index 7179b6fff80..4e3af429fc7 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGradientValue.h
@@ -47,10 +47,17 @@ enum CSSGradientType {
};
enum CSSGradientRepeat { NonRepeating, Repeating };
+// This struct is stack allocated and allocated as part of vectors.
+// When allocated on the stack its members are found by conservative
+// stack scanning. When allocated as part of Vectors in heap-allocated
+// objects its members are visited via the containing object's
+// (CSSGradientValue) traceAfterDispatch method.
struct CSSGradientColorStop {
+ ALLOW_ONLY_INLINE_ALLOCATION();
+public:
CSSGradientColorStop() : m_colorIsDerivedFromElement(false) { };
- RefPtr<CSSPrimitiveValue> m_position; // percentage or length
- RefPtr<CSSPrimitiveValue> m_color;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_position; // percentage or length
+ RefPtrWillBeMember<CSSPrimitiveValue> m_color;
Color m_resolvedColor;
bool m_colorIsDerivedFromElement;
bool operator==(const CSSGradientColorStop& other) const
@@ -58,16 +65,27 @@ struct CSSGradientColorStop {
return compareCSSValuePtr(m_color, other.m_color)
&& compareCSSValuePtr(m_position, other.m_position);
}
+
+ void trace(Visitor*);
};
+} // namespace WebCore
+
+
+// We have to declare the VectorTraits specialization before CSSGradientValue
+// declares its inline capacity vector below.
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::CSSGradientColorStop);
+
+namespace WebCore {
+
class CSSGradientValue : public CSSImageGeneratorValue {
public:
PassRefPtr<Image> image(RenderObject*, const IntSize&);
- void setFirstX(PassRefPtr<CSSPrimitiveValue> val) { m_firstX = val; }
- void setFirstY(PassRefPtr<CSSPrimitiveValue> val) { m_firstY = val; }
- void setSecondX(PassRefPtr<CSSPrimitiveValue> val) { m_secondX = val; }
- void setSecondY(PassRefPtr<CSSPrimitiveValue> val) { m_secondY = val; }
+ void setFirstX(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_firstX = val; }
+ void setFirstY(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_firstY = val; }
+ void setSecondX(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_secondX = val; }
+ void setSecondY(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_secondY = val; }
void addStop(const CSSGradientColorStop& stop) { m_stops.append(stop); }
@@ -86,7 +104,9 @@ public:
bool knownToBeOpaque(const RenderObject*) const;
void loadSubimages(ResourceFetcher*) { }
- PassRefPtr<CSSGradientValue> gradientWithStylesResolved(const TextLinkColors&, Color currentColor);
+ PassRefPtrWillBeRawPtr<CSSGradientValue> gradientWithStylesResolved(const TextLinkColors&, Color currentColor);
+
+ void traceAfterDispatch(Visitor*);
protected:
CSSGradientValue(ClassType classType, CSSGradientRepeat repeat, CSSGradientType gradientType)
@@ -118,14 +138,14 @@ protected:
bool isCacheable() const;
// Points. Some of these may be null.
- RefPtr<CSSPrimitiveValue> m_firstX;
- RefPtr<CSSPrimitiveValue> m_firstY;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_firstX;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_firstY;
- RefPtr<CSSPrimitiveValue> m_secondX;
- RefPtr<CSSPrimitiveValue> m_secondY;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_secondX;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_secondY;
// Stops
- Vector<CSSGradientColorStop, 2> m_stops;
+ WillBeHeapVector<CSSGradientColorStop, 2> m_stops;
bool m_stopsSorted;
CSSGradientType m_gradientType;
bool m_repeating;
@@ -136,25 +156,27 @@ DEFINE_CSS_VALUE_TYPE_CASTS(CSSGradientValue, isGradientValue());
class CSSLinearGradientValue : public CSSGradientValue {
public:
- static PassRefPtr<CSSLinearGradientValue> create(CSSGradientRepeat repeat, CSSGradientType gradientType = CSSLinearGradient)
+ static PassRefPtrWillBeRawPtr<CSSLinearGradientValue> create(CSSGradientRepeat repeat, CSSGradientType gradientType = CSSLinearGradient)
{
- return adoptRef(new CSSLinearGradientValue(repeat, gradientType));
+ return adoptRefWillBeNoop(new CSSLinearGradientValue(repeat, gradientType));
}
- void setAngle(PassRefPtr<CSSPrimitiveValue> val) { m_angle = val; }
+ void setAngle(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_angle = val; }
String customCSSText() const;
// Create the gradient for a given size.
PassRefPtr<Gradient> createGradient(const CSSToLengthConversionData&, const IntSize&);
- PassRefPtr<CSSLinearGradientValue> clone() const
+ PassRefPtrWillBeRawPtr<CSSLinearGradientValue> clone() const
{
- return adoptRef(new CSSLinearGradientValue(*this));
+ return adoptRefWillBeNoop(new CSSLinearGradientValue(*this));
}
bool equals(const CSSLinearGradientValue&) const;
+ void traceAfterDispatch(Visitor*);
+
private:
CSSLinearGradientValue(CSSGradientRepeat repeat, CSSGradientType gradientType = CSSLinearGradient)
: CSSGradientValue(LinearGradientClass, repeat, gradientType)
@@ -167,39 +189,41 @@ private:
{
}
- RefPtr<CSSPrimitiveValue> m_angle; // may be null.
+ RefPtrWillBeMember<CSSPrimitiveValue> m_angle; // may be null.
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSLinearGradientValue, isLinearGradientValue());
class CSSRadialGradientValue : public CSSGradientValue {
public:
- static PassRefPtr<CSSRadialGradientValue> create(CSSGradientRepeat repeat, CSSGradientType gradientType = CSSRadialGradient)
+ static PassRefPtrWillBeRawPtr<CSSRadialGradientValue> create(CSSGradientRepeat repeat, CSSGradientType gradientType = CSSRadialGradient)
{
- return adoptRef(new CSSRadialGradientValue(repeat, gradientType));
+ return adoptRefWillBeNoop(new CSSRadialGradientValue(repeat, gradientType));
}
- PassRefPtr<CSSRadialGradientValue> clone() const
+ PassRefPtrWillBeRawPtr<CSSRadialGradientValue> clone() const
{
- return adoptRef(new CSSRadialGradientValue(*this));
+ return adoptRefWillBeNoop(new CSSRadialGradientValue(*this));
}
String customCSSText() const;
- void setFirstRadius(PassRefPtr<CSSPrimitiveValue> val) { m_firstRadius = val; }
- void setSecondRadius(PassRefPtr<CSSPrimitiveValue> val) { m_secondRadius = val; }
+ void setFirstRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_firstRadius = val; }
+ void setSecondRadius(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_secondRadius = val; }
- void setShape(PassRefPtr<CSSPrimitiveValue> val) { m_shape = val; }
- void setSizingBehavior(PassRefPtr<CSSPrimitiveValue> val) { m_sizingBehavior = val; }
+ void setShape(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_shape = val; }
+ void setSizingBehavior(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_sizingBehavior = val; }
- void setEndHorizontalSize(PassRefPtr<CSSPrimitiveValue> val) { m_endHorizontalSize = val; }
- void setEndVerticalSize(PassRefPtr<CSSPrimitiveValue> val) { m_endVerticalSize = val; }
+ void setEndHorizontalSize(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_endHorizontalSize = val; }
+ void setEndVerticalSize(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_endVerticalSize = val; }
// Create the gradient for a given size.
PassRefPtr<Gradient> createGradient(const CSSToLengthConversionData&, const IntSize&);
bool equals(const CSSRadialGradientValue&) const;
+ void traceAfterDispatch(Visitor*);
+
private:
CSSRadialGradientValue(CSSGradientRepeat repeat, CSSGradientType gradientType = CSSRadialGradient)
: CSSGradientValue(RadialGradientClass, repeat, gradientType)
@@ -222,15 +246,15 @@ private:
float resolveRadius(CSSPrimitiveValue*, const CSSToLengthConversionData&, float* widthOrHeight = 0);
// These may be null for non-deprecated gradients.
- RefPtr<CSSPrimitiveValue> m_firstRadius;
- RefPtr<CSSPrimitiveValue> m_secondRadius;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_firstRadius;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_secondRadius;
// The below are only used for non-deprecated gradients. Any of them may be null.
- RefPtr<CSSPrimitiveValue> m_shape;
- RefPtr<CSSPrimitiveValue> m_sizingBehavior;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_shape;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_sizingBehavior;
- RefPtr<CSSPrimitiveValue> m_endHorizontalSize;
- RefPtr<CSSPrimitiveValue> m_endVerticalSize;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_endHorizontalSize;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_endVerticalSize;
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSRadialGradientValue, isRadialGradientValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGrammar.y b/chromium/third_party/WebKit/Source/core/css/CSSGrammar.y
index 2c2c3753094..e006812e9a4 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGrammar.y
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGrammar.y
@@ -29,7 +29,7 @@
#include "HTMLNames.h"
#include "core/css/CSSKeyframeRule.h"
#include "core/css/CSSKeyframesRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSParserMode.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSSelector.h"
@@ -60,10 +60,10 @@ using namespace HTMLNames;
%}
-%pure_parser
+%pure-parser
-%parse-param { CSSParser* parser }
-%lex-param { CSSParser* parser }
+%parse-param { BisonCSSParser* parser }
+%lex-param { BisonCSSParser* parser }
%union {
bool boolean;
@@ -73,7 +73,12 @@ using namespace HTMLNames;
CSSParserString string;
StyleRuleBase* rule;
- Vector<RefPtr<StyleRuleBase> >* ruleList;
+ // The content of the three below HeapVectors are guaranteed to be kept alive by
+ // the corresponding m_parsedRules, m_floatingMediaQueryExpList, and m_parsedKeyFrames
+ // lists in BisonCSSParser.h.
+ WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >* ruleList;
+ WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> >* mediaQueryExpList;
+ WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >* keyframeRuleList;
CSSParserSelector* selector;
Vector<OwnPtr<CSSParserSelector> >* selectorList;
CSSSelector::MarginBoxType marginBox;
@@ -84,9 +89,7 @@ using namespace HTMLNames;
MediaQueryExp* mediaQueryExp;
CSSParserValue value;
CSSParserValueList* valueList;
- Vector<OwnPtr<MediaQueryExp> >* mediaQueryExpList;
StyleKeyframe* keyframe;
- Vector<RefPtr<StyleKeyframe> >* keyframeRuleList;
float val;
CSSPropertyID id;
CSSParserLocation location;
@@ -114,12 +117,9 @@ static inline bool isCSSTokenAString(int yytype)
case FUNCTION:
case ANYFUNCTION:
case HOSTFUNCTION:
+ case HOSTCONTEXTFUNCTION:
case NOTFUNCTION:
case CALCFUNCTION:
- case MINFUNCTION:
- case MAXFUNCTION:
- case VARFUNCTION:
- case VAR_DEFINITION:
case UNICODERANGE:
return true;
default:
@@ -132,6 +132,7 @@ inline static CSSParserValue makeOperatorValue(int value)
{
CSSParserValue v;
v.id = CSSValueInvalid;
+ v.isInt = false;
v.unit = CSSParserValue::Operator;
v.iValue = value;
return v;
@@ -141,6 +142,7 @@ inline static CSSParserValue makeIdentValue(CSSParserString string)
{
CSSParserValue v;
v.id = cssValueKeywordID(string);
+ v.isInt = false;
v.unit = CSSPrimitiveValue::CSS_IDENT;
v.string = string;
return v;
@@ -194,8 +196,6 @@ inline static CSSParserValue makeIdentValue(CSSParserString string)
%token INTERNAL_SUPPORTS_CONDITION_SYM
%token KEYFRAMES_SYM
%token WEBKIT_KEYFRAMES_SYM
-%token WEBKIT_REGION_RULE_SYM
-%token WEBKIT_FILTER_RULE_SYM
%token <marginBox> TOPLEFTCORNER_SYM
%token <marginBox> TOPLEFT_SYM
%token <marginBox> TOPCENTER_SYM
@@ -265,11 +265,8 @@ inline static CSSParserValue makeIdentValue(CSSParserString string)
%token <string> NOTFUNCTION
%token <string> DISTRIBUTEDFUNCTION
%token <string> CALCFUNCTION
-%token <string> MINFUNCTION
-%token <string> MAXFUNCTION
-%token <string> VARFUNCTION
-%token <string> VAR_DEFINITION
%token <string> HOSTFUNCTION
+%token <string> HOSTCONTEXTFUNCTION
%token <string> UNICODERANGE
@@ -287,16 +284,10 @@ inline static CSSParserValue makeIdentValue(CSSParserString string)
%type <rule> valid_rule
%type <ruleList> block_rule_body
%type <ruleList> block_rule_list
-%type <ruleList> region_block_rule_body
-%type <ruleList> region_block_rule_list
%type <rule> block_rule
%type <rule> block_valid_rule
-%type <rule> region_block_rule
-%type <rule> region_block_valid_rule
-%type <rule> region
%type <rule> supports
%type <rule> viewport
-%type <rule> filter
%type <boolean> keyframes_rule_start
%type <string> maybe_ns_prefix
@@ -339,10 +330,8 @@ inline static CSSParserValue makeIdentValue(CSSParserString string)
%type <selector> specifier_list
%type <selector> simple_selector
%type <selector> selector
-%type <selector> relative_selector
%type <selectorList> selector_list
%type <selectorList> simple_selector_list
-%type <selectorList> region_selector
%type <selector> class
%type <selector> attrib
%type <selector> pseudo
@@ -368,11 +357,8 @@ inline static CSSParserValue makeIdentValue(CSSParserString string)
%type <value> calc_func_term
%type <character> calc_func_operator
%type <valueList> calc_func_expr
-%type <valueList> calc_func_expr_list
%type <valueList> calc_func_paren_expr
%type <value> calc_function
-%type <string> min_or_max
-%type <value> min_or_max_function
%type <string> element_name
%type <string> attr_name
@@ -511,10 +497,8 @@ valid_rule:
| keyframes
| namespace
| import
- | region
| supports
| viewport
- | filter
;
before_rule:
@@ -547,46 +531,12 @@ block_rule_list:
}
;
-region_block_rule_body:
- region_block_rule_list
- | region_block_rule_list block_rule_recovery
- ;
-
-region_block_rule_list:
- /* empty */ { $$ = 0; }
- | region_block_rule_list region_block_rule maybe_sgml {
- $$ = parser->appendRule($1, $2);
- }
- ;
-
-region_block_rule:
- before_rule region_block_valid_rule {
- $$ = $2;
- parser->endRule(!!$$);
- }
- | before_rule invalid_rule {
- $$ = 0;
- parser->endRule(false);
- }
- ;
-
block_rule_recovery:
before_rule invalid_rule_header {
parser->endRule(false);
}
;
-region_block_valid_rule:
- ruleset
- | page
- | font_face
- | media
- | keyframes
- | supports
- | viewport
- | filter
- ;
-
block_valid_rule:
ruleset
| page
@@ -595,9 +545,7 @@ block_valid_rule:
| keyframes
| supports
| viewport
- | filter
| namespace
- | region
;
block_rule:
@@ -716,11 +664,11 @@ valid_media_query:
media_query:
valid_media_query
| valid_media_query error error_location rule_error_recovery {
- parser->reportError(parser->lastLocationLabel(), CSSParser::InvalidMediaQueryError);
+ parser->reportError(parser->lastLocationLabel(), InvalidMediaQueryCSSError);
$$ = parser->createFloatingNotAllQuery();
}
| error error_location rule_error_recovery {
- parser->reportError(parser->lastLocationLabel(), CSSParser::InvalidMediaQueryError);
+ parser->reportError(parser->lastLocationLabel(), InvalidMediaQueryCSSError);
$$ = parser->createFloatingNotAllQuery();
}
;
@@ -846,7 +794,7 @@ supports_condition_in_parens:
}
| supports_declaration_condition
| '(' error error_location error_recovery closing_parenthesis maybe_space {
- parser->reportError($3, CSSParser::InvalidSupportsConditionError);
+ parser->reportError($3, InvalidSupportsConditionCSSError);
$$ = false;
}
;
@@ -868,7 +816,7 @@ supports_declaration_condition:
}
| '(' maybe_space IDENT maybe_space ':' maybe_space error error_recovery closing_parenthesis maybe_space {
$$ = false;
- parser->endProperty(false, false, CSSParser::GeneralError);
+ parser->endProperty(false, false, GeneralCSSError);
}
;
@@ -953,7 +901,7 @@ key:
keyframes_error_recovery:
error rule_error_recovery {
- parser->reportError(parser->lastLocationLabel(), CSSParser::InvalidKeyframeSelectorError);
+ parser->reportError(parser->lastLocationLabel(), InvalidKeyframeSelectorCSSError);
}
;
@@ -1089,53 +1037,15 @@ viewport:
}
;
-region_selector:
- selector_list {
- parser->setReusableRegionSelectorVector($1);
- $$ = parser->reusableRegionSelectorVector();
- }
-;
-
-before_region_rule:
- /* empty */ {
- parser->startRuleHeader(CSSRuleSourceData::REGION_RULE);
- }
- ;
-
-region:
- before_region_rule WEBKIT_REGION_RULE_SYM maybe_space region_selector at_rule_header_end '{' at_rule_body_start maybe_space region_block_rule_body closing_brace {
- $$ = parser->createRegionRule($4, $9);
- }
-;
-
-before_filter_rule:
- /* empty */ {
- parser->startRuleHeader(CSSRuleSourceData::FILTER_RULE);
- parser->m_inFilterRule = true;
- }
- ;
-
-filter:
- before_filter_rule WEBKIT_FILTER_RULE_SYM maybe_space IDENT at_rule_header_end_maybe_space
- '{' at_rule_body_start maybe_space_before_declaration declaration_list closing_brace {
- parser->m_inFilterRule = false;
- $$ = parser->createFilterRule($4);
- }
- ;
-
combinator:
'+' maybe_space { $$ = CSSSelector::DirectAdjacent; }
| '~' maybe_space { $$ = CSSSelector::IndirectAdjacent; }
| '>' maybe_space { $$ = CSSSelector::Child; }
- | '^' maybe_space {
- if (!RuntimeEnabledFeatures::shadowDOMEnabled())
+ | '/' IDENT '/' maybe_space {
+ if ($2.equalIgnoringCase("deep"))
+ $$ = CSSSelector::ShadowDeep;
+ else
YYERROR;
- $$ = CSSSelector::ChildTree;
- }
- | '^' '^' maybe_space {
- if (!RuntimeEnabledFeatures::shadowDOMEnabled())
- YYERROR;
- $$ = CSSSelector::DescendantTree;
}
;
@@ -1197,17 +1107,6 @@ selector_list:
}
;
-relative_selector:
- combinator selector {
- $$ = $2;
- CSSParserSelector* end = $$;
- while (end->tagHistory())
- end = end->tagHistory();
- end->setRelation($1);
- }
- | selector
- ;
-
selector:
simple_selector
| selector WHITESPACE
@@ -1420,7 +1319,7 @@ pseudo:
$$->setValue($3);
CSSSelector::PseudoType type = $$->pseudoType();
if (type == CSSSelector::PseudoUnknown) {
- parser->reportError($2, CSSParser::InvalidSelectorPseudoError);
+ parser->reportError($2, InvalidSelectorPseudoCSSError);
YYERROR;
}
}
@@ -1434,7 +1333,7 @@ pseudo:
// FIXME: This call is needed to force selector to compute the pseudoType early enough.
CSSSelector::PseudoType type = $$->pseudoType();
if (type == CSSSelector::PseudoUnknown) {
- parser->reportError($3, CSSParser::InvalidSelectorPseudoError);
+ parser->reportError($3, InvalidSelectorPseudoCSSError);
YYERROR;
}
}
@@ -1451,16 +1350,6 @@ pseudo:
| ':' ':' CUEFUNCTION selector_recovery closing_parenthesis {
YYERROR;
}
- | ':' ':' DISTRIBUTEDFUNCTION maybe_space relative_selector closing_parenthesis {
- $$ = parser->createFloatingSelector();
- $$->setMatch(CSSSelector::PseudoElement);
- $$->setFunctionArgumentSelector($5);
- parser->tokenToLowerCase($3);
- $$->setValue($3);
- }
- | ':' ':' DISTRIBUTEDFUNCTION selector_recovery closing_parenthesis {
- YYERROR;
- }
// use by :-webkit-any.
// FIXME: should we support generic selectors here or just simple_selectors?
// Use simple_selector_list for now to match -moz-any.
@@ -1549,17 +1438,21 @@ pseudo:
if (type != CSSSelector::PseudoHost)
YYERROR;
}
- // used by :host()
- | ':' HOSTFUNCTION maybe_space closing_parenthesis {
+ | ':' HOSTFUNCTION selector_recovery closing_parenthesis {
+ YYERROR;
+ }
+ // used by :host-context()
+ | ':' HOSTCONTEXTFUNCTION maybe_space simple_selector_list maybe_space closing_parenthesis {
$$ = parser->createFloatingSelector();
$$->setMatch(CSSSelector::PseudoClass);
+ $$->adoptSelectorVector(*parser->sinkFloatingSelectorVector($4));
parser->tokenToLowerCase($2);
- $$->setValue($2.atomicSubstring(0, $2.length() - 1));
+ $$->setValue($2);
CSSSelector::PseudoType type = $$->pseudoType();
- if (type != CSSSelector::PseudoHost)
+ if (type != CSSSelector::PseudoHostContext)
YYERROR;
}
- | ':' HOSTFUNCTION selector_recovery closing_parenthesis {
+ | ':' HOSTCONTEXTFUNCTION selector_recovery closing_parenthesis {
YYERROR;
}
;
@@ -1588,12 +1481,6 @@ decl_list:
;
declaration:
- VAR_DEFINITION maybe_space ':' maybe_space expr prio {
- parser->storeVariableDeclaration($1, parser->sinkFloatingValueList($5), $6);
- $$ = true;
- parser->endProperty($6, true);
- }
- |
property ':' maybe_space error_location expr prio {
$$ = false;
bool isPropertyParsed = false;
@@ -1603,7 +1490,7 @@ declaration:
$$ = parser->parseValue($1, $6);
if (!$$) {
parser->rollbackLastProperties(parser->m_parsedProperties.size() - oldParsedProperties);
- parser->reportError($4, CSSParser::InvalidPropertyValueError);
+ parser->reportError($4, InvalidPropertyValueCSSError);
} else
isPropertyParsed = true;
parser->m_valueList = nullptr;
@@ -1613,25 +1500,25 @@ declaration:
|
property ':' maybe_space error_location expr prio error error_recovery {
/* When we encounter something like p {color: red !important fail;} we should drop the declaration */
- parser->reportError($4, CSSParser::InvalidPropertyValueError);
+ parser->reportError($4, InvalidPropertyValueCSSError);
parser->endProperty(false, false);
$$ = false;
}
|
property ':' maybe_space error_location error error_recovery {
- parser->reportError($4, CSSParser::InvalidPropertyValueError);
+ parser->reportError($4, InvalidPropertyValueCSSError);
parser->endProperty(false, false);
$$ = false;
}
|
property error error_location error_recovery {
- parser->reportError($3, CSSParser::PropertyDeclarationError);
- parser->endProperty(false, false, CSSParser::GeneralError);
+ parser->reportError($3, PropertyDeclarationCSSError);
+ parser->endProperty(false, false, GeneralCSSError);
$$ = false;
}
|
error error_location error_recovery {
- parser->reportError($2, CSSParser::PropertyDeclarationError);
+ parser->reportError($2, PropertyDeclarationCSSError);
$$ = false;
}
;
@@ -1641,7 +1528,7 @@ property:
$$ = cssPropertyID($2);
parser->setCurrentProperty($$);
if ($$ == CSSPropertyInvalid)
- parser->reportError($1, CSSParser::InvalidPropertyError);
+ parser->reportError($1, InvalidPropertyCSSError);
}
;
@@ -1691,7 +1578,7 @@ expr:
expr_recovery:
error error_location error_recovery {
- parser->reportError($2, CSSParser::PropertyDeclarationError);
+ parser->reportError($2, PropertyDeclarationCSSError);
}
;
@@ -1707,29 +1594,20 @@ operator:
term:
unary_term maybe_space
| unary_operator unary_term maybe_space { $$ = $2; $$.fValue *= $1; }
- | STRING maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.unit = CSSPrimitiveValue::CSS_STRING; }
+ | STRING maybe_space { $$.id = CSSValueInvalid; $$.isInt = false; $$.string = $1; $$.unit = CSSPrimitiveValue::CSS_STRING; }
| IDENT maybe_space { $$ = makeIdentValue($1); }
/* We might need to actually parse the number from a dimension, but we can't just put something that uses $$.string into unary_term. */
- | DIMEN maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.unit = CSSPrimitiveValue::CSS_DIMENSION; }
- | unary_operator DIMEN maybe_space { $$.id = CSSValueInvalid; $$.string = $2; $$.unit = CSSPrimitiveValue::CSS_DIMENSION; }
- | URI maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.unit = CSSPrimitiveValue::CSS_URI; }
- | UNICODERANGE maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.unit = CSSPrimitiveValue::CSS_UNICODE_RANGE; }
- | HEX maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.unit = CSSPrimitiveValue::CSS_PARSER_HEXCOLOR; }
- | '#' maybe_space { $$.id = CSSValueInvalid; $$.string = CSSParserString(); $$.unit = CSSPrimitiveValue::CSS_PARSER_HEXCOLOR; } /* Handle error case: "color: #;" */
- | VARFUNCTION maybe_space IDENT closing_parenthesis maybe_space {
- $$.id = CSSValueInvalid;
- $$.string = $3;
- $$.unit = CSSPrimitiveValue::CSS_VARIABLE_NAME;
- }
- | VARFUNCTION maybe_space expr_recovery closing_parenthesis {
- YYERROR;
- }
+ | DIMEN maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.isInt = false; $$.unit = CSSPrimitiveValue::CSS_DIMENSION; }
+ | unary_operator DIMEN maybe_space { $$.id = CSSValueInvalid; $$.string = $2; $$.isInt = false; $$.unit = CSSPrimitiveValue::CSS_DIMENSION; }
+ | URI maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.isInt = false; $$.unit = CSSPrimitiveValue::CSS_URI; }
+ | UNICODERANGE maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.isInt = false; $$.unit = CSSPrimitiveValue::CSS_UNICODE_RANGE; }
+ | HEX maybe_space { $$.id = CSSValueInvalid; $$.string = $1; $$.isInt = false; $$.unit = CSSPrimitiveValue::CSS_PARSER_HEXCOLOR; }
+ | '#' maybe_space { $$.id = CSSValueInvalid; $$.string = CSSParserString(); $$.isInt = false; $$.unit = CSSPrimitiveValue::CSS_PARSER_HEXCOLOR; } /* Handle error case: "color: #;" */
/* FIXME: according to the specs a function can have a unary_operator in front. I know no case where this makes sense */
| function maybe_space
| calc_function maybe_space
- | min_or_max_function maybe_space
| '%' maybe_space { /* Handle width: %; */
- $$.id = CSSValueInvalid; $$.unit = 0;
+ $$.id = CSSValueInvalid; $$.isInt = false; $$.unit = 0;
}
| track_names_list maybe_space
;
@@ -1785,11 +1663,6 @@ function:
calc_func_term:
unary_term
- | VARFUNCTION maybe_space IDENT closing_parenthesis {
- $$.id = CSSValueInvalid;
- $$.string = $3;
- $$.unit = CSSPrimitiveValue::CSS_VARIABLE_NAME;
- }
| unary_operator unary_term { $$ = $2; $$.fValue *= $1; }
;
@@ -1837,20 +1710,11 @@ calc_func_expr:
| calc_func_expr calc_func_operator calc_func_paren_expr {
$$ = $1;
$$->addValue(makeOperatorValue($2));
- $$->extend(*($3));
+ $$->stealValues(*($3));
}
| calc_func_paren_expr
;
-calc_func_expr_list:
- calc_func_expr calc_maybe_space
- | calc_func_expr_list ',' maybe_space calc_func_expr calc_maybe_space {
- $$ = $1;
- $$->addValue(makeOperatorValue(','));
- $$->extend(*($4));
- }
- ;
-
calc_function:
CALCFUNCTION maybe_space calc_func_expr calc_maybe_space closing_parenthesis {
$$.setFromFunction(parser->createFloatingFunction($1, parser->sinkFloatingValueList($3)));
@@ -1861,20 +1725,6 @@ calc_function:
;
-min_or_max:
- MINFUNCTION
- | MAXFUNCTION
- ;
-
-min_or_max_function:
- min_or_max maybe_space calc_func_expr_list closing_parenthesis {
- $$.setFromFunction(parser->createFloatingFunction($1, parser->sinkFloatingValueList($3)));
- }
- | min_or_max maybe_space expr_recovery closing_parenthesis {
- YYERROR;
- }
- ;
-
invalid_at:
ATKEYWORD
| margin_sym
@@ -1886,7 +1736,7 @@ at_rule_recovery:
at_rule_header_recovery:
error error_location rule_error_recovery {
- parser->reportError($2, CSSParser::InvalidRuleError);
+ parser->reportError($2, InvalidRuleCSSError);
}
;
@@ -1900,25 +1750,23 @@ regular_invalid_at_rule_header:
| before_page_rule PAGE_SYM at_rule_header_recovery
| before_font_face_rule FONT_FACE_SYM at_rule_header_recovery
| before_supports_rule SUPPORTS_SYM error error_location rule_error_recovery {
- parser->reportError($4, CSSParser::InvalidSupportsConditionError);
+ parser->reportError($4, InvalidSupportsConditionCSSError);
parser->popSupportsRuleData();
}
| before_viewport_rule VIEWPORT_RULE_SYM at_rule_header_recovery {
parser->markViewportRuleBodyEnd();
}
- | before_filter_rule WEBKIT_FILTER_RULE_SYM at_rule_header_recovery
| import_rule_start at_rule_header_recovery
| NAMESPACE_SYM at_rule_header_recovery
- | before_region_rule WEBKIT_REGION_RULE_SYM at_rule_header_recovery
| error_location invalid_at at_rule_header_recovery {
parser->resumeErrorLogging();
- parser->reportError($1, CSSParser::InvalidRuleError);
+ parser->reportError($1, InvalidRuleCSSError);
}
;
invalid_rule:
error error_location rule_error_recovery at_invalid_rule_header_end invalid_block {
- parser->reportError($2, CSSParser::InvalidRuleError);
+ parser->reportError($2, InvalidRuleCSSError);
}
| regular_invalid_at_rule_header at_invalid_rule_header_end ';'
| regular_invalid_at_rule_header at_invalid_rule_header_end invalid_block
@@ -1927,7 +1775,7 @@ invalid_rule:
invalid_rule_header:
error error_location rule_error_recovery at_invalid_rule_header_end {
- parser->reportError($2, CSSParser::InvalidRuleError);
+ parser->reportError($2, InvalidRuleCSSError);
}
| regular_invalid_at_rule_header at_invalid_rule_header_end
| media_rule_start maybe_media_list
@@ -1953,7 +1801,7 @@ invalid_parentheses_block:
opening_parenthesis error_recovery closing_parenthesis;
opening_parenthesis:
- '(' | FUNCTION | CALCFUNCTION | VARFUNCTION | MINFUNCTION | MAXFUNCTION | ANYFUNCTION | NOTFUNCTION | CUEFUNCTION | DISTRIBUTEDFUNCTION | HOSTFUNCTION
+ '(' | FUNCTION | CALCFUNCTION | ANYFUNCTION | NOTFUNCTION | CUEFUNCTION | DISTRIBUTEDFUNCTION | HOSTFUNCTION
;
error_location: {
@@ -1982,4 +1830,3 @@ rule_error_recovery:
;
%%
-
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.cpp
index 3a2877d9ae9..5b100a553d8 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.cpp
@@ -43,9 +43,9 @@ CSSGridLineNamesValue::CSSGridLineNamesValue()
{
}
-PassRefPtr<CSSGridLineNamesValue> CSSGridLineNamesValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSGridLineNamesValue> CSSGridLineNamesValue::cloneForCSSOM() const
{
- return adoptRef(new CSSGridLineNamesValue(*this));
+ return adoptRefWillBeNoop(new CSSGridLineNamesValue(*this));
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.h b/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.h
index da97e059579..3e4298fa39f 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGridLineNamesValue.h
@@ -38,14 +38,16 @@ namespace WebCore {
class CSSGridLineNamesValue : public CSSValueList {
public:
- static PassRefPtr<CSSGridLineNamesValue> create()
+ static PassRefPtrWillBeRawPtr<CSSGridLineNamesValue> create()
{
- return adoptRef(new CSSGridLineNamesValue());
+ return adoptRefWillBeNoop(new CSSGridLineNamesValue());
}
String customCSSText() const;
- PassRefPtr<CSSGridLineNamesValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSGridLineNamesValue> cloneForCSSOM() const;
+
+ void traceAfterDispatch(Visitor* visitor) { CSSValueList::traceAfterDispatch(visitor); }
private:
CSSGridLineNamesValue();
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateAreasValue.cpp
index d1ad1d8d056..9541f52715a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateAreasValue.cpp
@@ -29,14 +29,14 @@
*/
#include "config.h"
-#include "core/css/CSSGridTemplateValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
-CSSGridTemplateValue::CSSGridTemplateValue(const NamedGridAreaMap& gridAreaMap, size_t rowCount, size_t columnCount)
- : CSSValue(GridTemplateClass)
+CSSGridTemplateAreasValue::CSSGridTemplateAreasValue(const NamedGridAreaMap& gridAreaMap, size_t rowCount, size_t columnCount)
+ : CSSValue(GridTemplateAreasClass)
, m_gridAreaMap(gridAreaMap)
, m_rowCount(rowCount)
, m_columnCount(columnCount)
@@ -52,21 +52,21 @@ static String stringForPosition(const NamedGridAreaMap& gridAreaMap, size_t row,
NamedGridAreaMap::const_iterator end = gridAreaMap.end();
for (NamedGridAreaMap::const_iterator it = gridAreaMap.begin(); it != end; ++it) {
const GridCoordinate& coordinate = it->value;
- if (row >= coordinate.rows.initialPositionIndex && row <= coordinate.rows.finalPositionIndex)
+ if (row >= coordinate.rows.resolvedInitialPosition.toInt() && row <= coordinate.rows.resolvedFinalPosition.toInt())
candidates.append(it->key);
}
end = gridAreaMap.end();
for (NamedGridAreaMap::const_iterator it = gridAreaMap.begin(); it != end; ++it) {
const GridCoordinate& coordinate = it->value;
- if (column >= coordinate.columns.initialPositionIndex && column <= coordinate.columns.finalPositionIndex && candidates.contains(it->key))
+ if (column >= coordinate.columns.resolvedInitialPosition.toInt() && column <= coordinate.columns.resolvedFinalPosition.toInt() && candidates.contains(it->key))
return it->key;
}
return ".";
}
-String CSSGridTemplateValue::customCSSText() const
+String CSSGridTemplateAreasValue::customCSSText() const
{
StringBuilder builder;
for (size_t row = 0; row < m_rowCount; ++row) {
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateValue.h b/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateAreasValue.h
index faa988053f6..070cc8488cd 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGridTemplateAreasValue.h
@@ -28,8 +28,8 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef CSSGridTemplateValue_h
-#define CSSGridTemplateValue_h
+#ifndef CSSGridTemplateAreasValue_h
+#define CSSGridTemplateAreasValue_h
#include "core/css/CSSValue.h"
#include "core/rendering/style/GridCoordinate.h"
@@ -37,10 +37,13 @@
namespace WebCore {
-class CSSGridTemplateValue : public CSSValue {
+class CSSGridTemplateAreasValue : public CSSValue {
public:
- static PassRefPtr<CSSGridTemplateValue> create(const NamedGridAreaMap& gridAreaMap, size_t rowCount, size_t columnCount) { return adoptRef(new CSSGridTemplateValue(gridAreaMap, rowCount, columnCount)); }
- ~CSSGridTemplateValue() { }
+ static PassRefPtrWillBeRawPtr<CSSGridTemplateAreasValue> create(const NamedGridAreaMap& gridAreaMap, size_t rowCount, size_t columnCount)
+ {
+ return adoptRefWillBeNoop(new CSSGridTemplateAreasValue(gridAreaMap, rowCount, columnCount));
+ }
+ ~CSSGridTemplateAreasValue() { }
String customCSSText() const;
@@ -48,16 +51,18 @@ public:
size_t rowCount() const { return m_rowCount; }
size_t columnCount() const { return m_columnCount; }
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
- CSSGridTemplateValue(const NamedGridAreaMap&, size_t rowCount, size_t columnCount);
+ CSSGridTemplateAreasValue(const NamedGridAreaMap&, size_t rowCount, size_t columnCount);
NamedGridAreaMap m_gridAreaMap;
size_t m_rowCount;
size_t m_columnCount;
};
-DEFINE_CSS_VALUE_TYPE_CASTS(CSSGridTemplateValue, isGridTemplateValue());
+DEFINE_CSS_VALUE_TYPE_CASTS(CSSGridTemplateAreasValue, isGridTemplateAreasValue());
} // namespace WebCore
-#endif // CSSGridTemplateValue_h
+#endif // CSSGridTemplateAreasValue_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.cpp
index 0c0bf2a9d20..ec56762b027 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.cpp
@@ -32,10 +32,11 @@
#include "core/css/CSSGroupingRule.h"
#include "bindings/v8/ExceptionState.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSRuleList.h"
#include "core/css/CSSStyleSheet.h"
#include "core/dom/ExceptionCode.h"
+#include "core/frame/UseCounter.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
@@ -49,11 +50,13 @@ CSSGroupingRule::CSSGroupingRule(StyleRuleGroup* groupRule, CSSStyleSheet* paren
CSSGroupingRule::~CSSGroupingRule()
{
+#if !ENABLE(OILPAN)
ASSERT(m_childRuleCSSOMWrappers.size() == m_groupRule->childRules().size());
for (unsigned i = 0; i < m_childRuleCSSOMWrappers.size(); ++i) {
if (m_childRuleCSSOMWrappers[i])
m_childRuleCSSOMWrappers[i]->setParentRule(0);
}
+#endif
}
unsigned CSSGroupingRule::insertRule(const String& ruleString, unsigned index, ExceptionState& exceptionState)
@@ -66,8 +69,9 @@ unsigned CSSGroupingRule::insertRule(const String& ruleString, unsigned index, E
}
CSSStyleSheet* styleSheet = parentStyleSheet();
- CSSParser parser(parserContext(), UseCounter::getFrom(styleSheet));
- RefPtr<StyleRuleBase> newRule = parser.parseRule(styleSheet ? styleSheet->contents() : 0, ruleString);
+ CSSParserContext context(parserContext(), UseCounter::getFrom(styleSheet));
+ BisonCSSParser parser(context);
+ RefPtrWillBeRawPtr<StyleRuleBase> newRule = parser.parseRule(styleSheet ? styleSheet->contents() : 0, ruleString);
if (!newRule) {
exceptionState.throwDOMException(SyntaxError, "the rule '" + ruleString + "' is invalid and cannot be parsed.");
return 0;
@@ -84,7 +88,7 @@ unsigned CSSGroupingRule::insertRule(const String& ruleString, unsigned index, E
m_groupRule->wrapperInsertRule(index, newRule);
- m_childRuleCSSOMWrappers.insert(index, RefPtr<CSSRule>());
+ m_childRuleCSSOMWrappers.insert(index, RefPtrWillBeMember<CSSRule>(nullptr));
return index;
}
@@ -126,7 +130,7 @@ CSSRule* CSSGroupingRule::item(unsigned index) const
if (index >= length())
return 0;
ASSERT(m_childRuleCSSOMWrappers.size() == m_groupRule->childRules().size());
- RefPtr<CSSRule>& rule = m_childRuleCSSOMWrappers[index];
+ RefPtrWillBeMember<CSSRule>& rule = m_childRuleCSSOMWrappers[index];
if (!rule)
rule = m_groupRule->childRules()[index]->createCSSOMWrapper(const_cast<CSSGroupingRule*>(this));
return rule.get();
@@ -135,7 +139,7 @@ CSSRule* CSSGroupingRule::item(unsigned index) const
CSSRuleList* CSSGroupingRule::cssRules() const
{
if (!m_ruleListCSSOMWrapper)
- m_ruleListCSSOMWrapper = adoptPtr(new LiveCSSRuleList<CSSGroupingRule>(const_cast<CSSGroupingRule*>(this)));
+ m_ruleListCSSOMWrapper = LiveCSSRuleList<CSSGroupingRule>::create(const_cast<CSSGroupingRule*>(this));
return m_ruleListCSSOMWrapper.get();
}
@@ -149,4 +153,14 @@ void CSSGroupingRule::reattach(StyleRuleBase* rule)
}
}
+void CSSGroupingRule::trace(Visitor* visitor)
+{
+ CSSRule::trace(visitor);
+#if ENABLE(OILPAN)
+ visitor->trace(m_childRuleCSSOMWrappers);
+#endif
+ visitor->trace(m_groupRule);
+ visitor->trace(m_ruleListCSSOMWrapper);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.h b/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.h
index 9ba64484b95..cdc98da3477 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSGroupingRule.h
@@ -47,14 +47,16 @@ public:
unsigned length() const;
CSSRule* item(unsigned index) const;
+ virtual void trace(Visitor*) OVERRIDE;
+
protected:
CSSGroupingRule(StyleRuleGroup* groupRule, CSSStyleSheet* parent);
void appendCSSTextForItems(StringBuilder&) const;
- RefPtr<StyleRuleGroup> m_groupRule;
- mutable Vector<RefPtr<CSSRule> > m_childRuleCSSOMWrappers;
- mutable OwnPtr<CSSRuleList> m_ruleListCSSOMWrapper;
+ RefPtrWillBeMember<StyleRuleGroup> m_groupRule;
+ mutable WillBeHeapVector<RefPtrWillBeMember<CSSRule> > m_childRuleCSSOMWrappers;
+ mutable OwnPtrWillBeMember<CSSRuleList> m_ruleListCSSOMWrapper;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.cpp
index fa3f22a05e6..41b0ea18c95 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.cpp
@@ -44,9 +44,16 @@ CSSImageGeneratorValue::~CSSImageGeneratorValue()
void CSSImageGeneratorValue::addClient(RenderObject* renderer, const IntSize& size)
{
+ ASSERT(renderer);
+#if !ENABLE(OILPAN)
ref();
+#else
+ if (m_clients.isEmpty()) {
+ ASSERT(!m_keepAlive);
+ m_keepAlive = adoptPtr(new Persistent<CSSImageGeneratorValue>(this));
+ }
+#endif
- ASSERT(renderer);
if (!size.isEmpty())
m_sizes.add(size);
@@ -77,7 +84,14 @@ void CSSImageGeneratorValue::removeClient(RenderObject* renderer)
if (!--sizeCount.count)
m_clients.remove(renderer);
+#if !ENABLE(OILPAN)
deref();
+#else
+ if (m_clients.isEmpty()) {
+ ASSERT(m_keepAlive);
+ m_keepAlive = nullptr;
+ }
+#endif
}
Image* CSSImageGeneratorValue::getImage(RenderObject* renderer, const IntSize& size)
@@ -87,7 +101,9 @@ Image* CSSImageGeneratorValue::getImage(RenderObject* renderer, const IntSize& s
SizeAndCount& sizeCount = it->value;
IntSize oldSize = sizeCount.size;
if (oldSize != size) {
+#if !ENABLE_OILPAN
RefPtr<CSSImageGeneratorValue> protect(this);
+#endif
removeClient(renderer);
addClient(renderer, size);
}
@@ -120,7 +136,7 @@ PassRefPtr<Image> CSSImageGeneratorValue::image(RenderObject* renderer, const In
default:
ASSERT_NOT_REACHED();
}
- return 0;
+ return nullptr;
}
bool CSSImageGeneratorValue::isFixedSize() const
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.h b/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.h
index d5803d3d52f..09b63b08cff 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImageGeneratorValue.h
@@ -67,6 +67,8 @@ public:
void loadSubimages(ResourceFetcher*);
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
protected:
explicit CSSImageGeneratorValue(ClassType);
@@ -77,6 +79,14 @@ protected:
HashCountedSet<IntSize> m_sizes; // A count of how many times a given image size is in use.
RenderObjectSizeCountMap m_clients; // A map from RenderObjects (with entry count) to image sizes.
HashMap<IntSize, RefPtr<Image> > m_images; // A cache of Image objects by image size.
+
+#if ENABLE(OILPAN)
+ // FIXME: Oilpan: when/if we can make the renderer point directly to the CSSImageGenerator value using
+ // a member we don't need to have this hack where we keep a persistent to the instance as long as
+ // there are clients in the RenderObjectSizeCountMap.
+ GC_PLUGIN_IGNORE("366546")
+ OwnPtr<Persistent<CSSImageGeneratorValue> > m_keepAlive;
+#endif
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSImageGeneratorValue, isImageGeneratorValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.cpp
index ef6321908a1..c081fbeea4c 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.cpp
@@ -26,7 +26,7 @@
#include "config.h"
#include "core/css/CSSImageSetValue.h"
-#include "FetchInitiatorTypeNames.h"
+#include "core/FetchInitiatorTypeNames.h"
#include "core/css/CSSImageValue.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/dom/Document.h"
@@ -57,8 +57,8 @@ void CSSImageSetValue::fillImageSet()
size_t length = this->length();
size_t i = 0;
while (i < length) {
- CSSValue* imageValue = item(i);
- String imageURL = toCSSImageValue(imageValue)->url();
+ CSSImageValue* imageValue = toCSSImageValue(item(i));
+ String imageURL = imageValue->url();
++i;
ASSERT_WITH_SECURITY_IMPLICATION(i < length);
@@ -67,6 +67,7 @@ void CSSImageSetValue::fillImageSet()
ImageWithScale image;
image.imageURL = imageURL;
+ image.referrer = imageValue->referrer();
image.scaleFactor = scaleFactor;
m_imagesInSet.append(image);
++i;
@@ -88,7 +89,7 @@ CSSImageSetValue::ImageWithScale CSSImageSetValue::bestImageForScaleFactor()
return image;
}
-StyleFetchedImageSet* CSSImageSetValue::cachedImageSet(ResourceFetcher* loader, float deviceScaleFactor)
+StyleFetchedImageSet* CSSImageSetValue::cachedImageSet(ResourceFetcher* loader, float deviceScaleFactor, const ResourceLoaderOptions& options)
{
ASSERT(loader);
@@ -99,11 +100,16 @@ StyleFetchedImageSet* CSSImageSetValue::cachedImageSet(ResourceFetcher* loader,
if (!m_accessedBestFitImage) {
// FIXME: In the future, we want to take much more than deviceScaleFactor into acount here.
- // All forms of scale should be included: Page::pageScaleFactor(), Frame::pageZoomFactor(),
+ // All forms of scale should be included: Page::pageScaleFactor(), LocalFrame::pageZoomFactor(),
// and any CSS transforms. https://bugs.webkit.org/show_bug.cgi?id=81698
ImageWithScale image = bestImageForScaleFactor();
if (Document* document = loader->document()) {
- FetchRequest request(ResourceRequest(document->completeURL(image.imageURL)), FetchInitiatorTypeNames::css);
+ FetchRequest request(ResourceRequest(document->completeURL(image.imageURL)), FetchInitiatorTypeNames::css, options);
+ request.mutableResourceRequest().setHTTPReferrer(image.referrer);
+
+ if (options.corsEnabled == IsCORSEnabled)
+ request.setCrossOriginAccessControl(loader->document()->securityOrigin(), options.allowCredentials, options.credentialsRequested);
+
if (ResourcePtr<ImageResource> cachedImage = loader->fetchImage(request)) {
m_imageSet = StyleFetchedImageSet::create(cachedImage.get(), image.scaleFactor, this);
m_accessedBestFitImage = true;
@@ -114,6 +120,11 @@ StyleFetchedImageSet* CSSImageSetValue::cachedImageSet(ResourceFetcher* loader,
return (m_imageSet && m_imageSet->isImageResourceSet()) ? toStyleFetchedImageSet(m_imageSet) : 0;
}
+StyleFetchedImageSet* CSSImageSetValue::cachedImageSet(ResourceFetcher* fetcher, float deviceScaleFactor)
+{
+ return cachedImageSet(fetcher, deviceScaleFactor, ResourceFetcher::defaultResourceOptions());
+}
+
StyleImage* CSSImageSetValue::cachedOrPendingImageSet(float deviceScaleFactor)
{
if (!m_imageSet) {
@@ -176,9 +187,9 @@ CSSImageSetValue::CSSImageSetValue(const CSSImageSetValue& cloneFrom)
// Non-CSSValueList data is not accessible through CSS OM, no need to clone.
}
-PassRefPtr<CSSImageSetValue> CSSImageSetValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSImageSetValue> CSSImageSetValue::cloneForCSSOM() const
{
- return adoptRef(new CSSImageSetValue(*this));
+ return adoptRefWillBeNoop(new CSSImageSetValue(*this));
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.h b/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.h
index ee6e86b4313..2b9ea861607 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImageSetValue.h
@@ -27,6 +27,8 @@
#define CSSImageSetValue_h
#include "core/css/CSSValueList.h"
+#include "core/fetch/ResourceFetcher.h"
+#include "platform/weborigin/Referrer.h"
namespace WebCore {
@@ -37,12 +39,13 @@ class StyleImage;
class CSSImageSetValue : public CSSValueList {
public:
- static PassRefPtr<CSSImageSetValue> create()
+ static PassRefPtrWillBeRawPtr<CSSImageSetValue> create()
{
- return adoptRef(new CSSImageSetValue());
+ return adoptRefWillBeNoop(new CSSImageSetValue());
}
~CSSImageSetValue();
+ StyleFetchedImageSet* cachedImageSet(ResourceFetcher*, float deviceScaleFactor, const ResourceLoaderOptions&);
StyleFetchedImageSet* cachedImageSet(ResourceFetcher*, float deviceScaleFactor);
// Returns a StyleFetchedImageSet if the best fit image has been cached already, otherwise a StylePendingImage.
@@ -54,12 +57,15 @@ public:
struct ImageWithScale {
String imageURL;
+ Referrer referrer;
float scaleFactor;
};
bool hasFailedOrCanceledSubresources() const;
- PassRefPtr<CSSImageSetValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSImageSetValue> cloneForCSSOM() const;
+
+ void traceAfterDispatch(Visitor* visitor) { CSSValueList::traceAfterDispatch(visitor); }
protected:
ImageWithScale bestImageForScaleFactor();
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImageValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSImageValue.cpp
index 4dd0799e101..7163e58c6f6 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImageValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImageValue.cpp
@@ -21,29 +21,24 @@
#include "config.h"
#include "core/css/CSSImageValue.h"
-#include "FetchInitiatorTypeNames.h"
-#include "core/css/CSSParser.h"
+#include "core/FetchInitiatorTypeNames.h"
+#include "core/css/CSSMarkup.h"
#include "core/dom/Document.h"
#include "core/fetch/CrossOriginAccessControl.h"
#include "core/fetch/FetchRequest.h"
#include "core/fetch/ImageResource.h"
#include "core/rendering/style/StyleFetchedImage.h"
#include "core/rendering/style/StylePendingImage.h"
+#include "platform/weborigin/KURL.h"
namespace WebCore {
-CSSImageValue::CSSImageValue(const String& url)
+CSSImageValue::CSSImageValue(const String& rawValue, const KURL& url, StyleImage* image)
: CSSValue(ImageClass)
- , m_url(url)
- , m_accessedImage(false)
-{
-}
-
-CSSImageValue::CSSImageValue(const String& url, StyleImage* image)
- : CSSValue(ImageClass)
- , m_url(url)
+ , m_relativeURL(rawValue)
+ , m_absoluteURL(url.string())
, m_image(image)
- , m_accessedImage(true)
+ , m_accessedImage(image)
{
}
@@ -59,17 +54,18 @@ StyleImage* CSSImageValue::cachedOrPendingImage()
return m_image.get();
}
-StyleFetchedImage* CSSImageValue::cachedImage(ResourceFetcher* fetcher, const ResourceLoaderOptions& options, CORSEnabled corsEnabled)
+StyleFetchedImage* CSSImageValue::cachedImage(ResourceFetcher* fetcher, const ResourceLoaderOptions& options)
{
ASSERT(fetcher);
if (!m_accessedImage) {
m_accessedImage = true;
- FetchRequest request(ResourceRequest(fetcher->document()->completeURL(m_url)), m_initiatorName.isEmpty() ? FetchInitiatorTypeNames::css : m_initiatorName, options);
+ FetchRequest request(ResourceRequest(m_absoluteURL), m_initiatorName.isEmpty() ? FetchInitiatorTypeNames::css : m_initiatorName, options);
+ request.mutableResourceRequest().setHTTPReferrer(m_referrer);
- if (corsEnabled == PotentiallyCORSEnabled)
- updateRequestForAccessControl(request.mutableResourceRequest(), fetcher->document()->securityOrigin(), options.allowCredentials);
+ if (options.corsEnabled == IsCORSEnabled)
+ request.setCrossOriginAccessControl(fetcher->document()->securityOrigin(), options.allowCredentials, options.credentialsRequested);
if (ResourcePtr<ImageResource> cachedImage = fetcher->fetchImage(request))
m_image = StyleFetchedImage::create(cachedImage.get());
@@ -78,6 +74,21 @@ StyleFetchedImage* CSSImageValue::cachedImage(ResourceFetcher* fetcher, const Re
return (m_image && m_image->isImageResource()) ? toStyleFetchedImage(m_image) : 0;
}
+void CSSImageValue::restoreCachedResourceIfNeeded(Document& document)
+{
+ if (!m_accessedImage || !m_image->isImageResource() || !document.fetcher())
+ return;
+ if (document.fetcher()->cachedResource(KURL(ParsedURLString, m_absoluteURL)))
+ return;
+
+ ImageResource* resource = m_image->cachedImage();
+ if (!resource)
+ return;
+
+ FetchRequest request(ResourceRequest(m_absoluteURL), m_initiatorName.isEmpty() ? FetchInitiatorTypeNames::css : m_initiatorName, resource->options());
+ document.fetcher()->requestLoadStarted(resource, request, ResourceFetcher::ResourceLoadingFromCache);
+}
+
bool CSSImageValue::hasFailedOrCanceledSubresources() const
{
if (!m_image || !m_image->isImageResource())
@@ -89,18 +100,18 @@ bool CSSImageValue::hasFailedOrCanceledSubresources() const
bool CSSImageValue::equals(const CSSImageValue& other) const
{
- return m_url == other.m_url;
+ return m_absoluteURL == other.m_absoluteURL;
}
String CSSImageValue::customCSSText() const
{
- return "url(" + quoteCSSURLIfNeeded(m_url) + ")";
+ return "url(" + quoteCSSURLIfNeeded(m_absoluteURL) + ")";
}
-PassRefPtr<CSSValue> CSSImageValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSValue> CSSImageValue::cloneForCSSOM() const
{
// NOTE: We expose CSSImageValues as URI primitive values in CSSOM to maintain old behavior.
- RefPtr<CSSPrimitiveValue> uriValue = CSSPrimitiveValue::create(m_url, CSSPrimitiveValue::CSS_URI);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> uriValue = CSSPrimitiveValue::create(m_absoluteURL, CSSPrimitiveValue::CSS_URI);
uriValue->setCSSOMSafe();
return uriValue.release();
}
@@ -110,4 +121,19 @@ bool CSSImageValue::knownToBeOpaque(const RenderObject* renderer) const
return m_image ? m_image->knownToBeOpaque(renderer) : false;
}
+void CSSImageValue::traceAfterDispatch(Visitor* visitor)
+{
+ CSSValue::traceAfterDispatch(visitor);
+}
+
+void CSSImageValue::reResolveURL(const Document& document)
+{
+ KURL url = document.completeURL(m_relativeURL);
+ if (url == m_absoluteURL)
+ return;
+ m_absoluteURL = url.string();
+ m_accessedImage = false;
+ m_image.clear();
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImageValue.h b/chromium/third_party/WebKit/Source/core/css/CSSImageValue.h
index a84afa5947a..4dce66191bb 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImageValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImageValue.h
@@ -23,31 +23,45 @@
#include "core/css/CSSValue.h"
#include "core/fetch/ResourceFetcher.h"
+#include "platform/weborigin/Referrer.h"
#include "wtf/RefPtr.h"
namespace WebCore {
+class Document;
class Element;
+class KURL;
class StyleFetchedImage;
class StyleImage;
class RenderObject;
class CSSImageValue : public CSSValue {
public:
- static PassRefPtr<CSSImageValue> create(const String& url) { return adoptRef(new CSSImageValue(url)); }
- static PassRefPtr<CSSImageValue> create(const String& url, StyleImage* image) { return adoptRef(new CSSImageValue(url, image)); }
+ static PassRefPtrWillBeRawPtr<CSSImageValue> create(const KURL& url, StyleImage* image = 0)
+ {
+ return adoptRefWillBeNoop(new CSSImageValue(url, url, image));
+ }
+ static PassRefPtrWillBeRawPtr<CSSImageValue> create(const String& rawValue, const KURL& url, StyleImage* image = 0)
+ {
+ return adoptRefWillBeNoop(new CSSImageValue(rawValue, url, image));
+ }
~CSSImageValue();
- StyleFetchedImage* cachedImage(ResourceFetcher*, const ResourceLoaderOptions&, CORSEnabled);
- StyleFetchedImage* cachedImage(ResourceFetcher* fetcher) { return cachedImage(fetcher, ResourceFetcher::defaultResourceOptions(), NotCORSEnabled); }
+ StyleFetchedImage* cachedImage(ResourceFetcher*, const ResourceLoaderOptions&);
+ StyleFetchedImage* cachedImage(ResourceFetcher* fetcher) { return cachedImage(fetcher, ResourceFetcher::defaultResourceOptions()); }
// Returns a StyleFetchedImage if the image is cached already, otherwise a StylePendingImage.
StyleImage* cachedOrPendingImage();
- const String& url() { return m_url; }
+ const String& url() { return m_absoluteURL; }
+
+ void setReferrer(const Referrer& referrer) { m_referrer = referrer; }
+ const Referrer& referrer() const { return m_referrer; }
+
+ void reResolveURL(const Document&);
String customCSSText() const;
- PassRefPtr<CSSValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSValue> cloneForCSSOM() const;
bool hasFailedOrCanceledSubresources() const;
@@ -57,11 +71,15 @@ public:
void setInitiator(const AtomicString& name) { m_initiatorName = name; }
+ void traceAfterDispatch(Visitor*);
+ void restoreCachedResourceIfNeeded(Document&);
+
private:
- explicit CSSImageValue(const String& url);
- CSSImageValue(const String& url, StyleImage*);
+ CSSImageValue(const String& rawValue, const KURL&, StyleImage*);
- String m_url;
+ String m_relativeURL;
+ String m_absoluteURL;
+ Referrer m_referrer;
RefPtr<StyleImage> m_image;
bool m_accessedImage;
AtomicString m_initiatorName;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImportRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSImportRule.cpp
index cf733f70f3c..e7d6219cbc1 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImportRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImportRule.cpp
@@ -38,10 +38,13 @@ CSSImportRule::CSSImportRule(StyleRuleImport* importRule, CSSStyleSheet* parent)
CSSImportRule::~CSSImportRule()
{
+#if !ENABLE(OILPAN)
if (m_styleSheetCSSOMWrapper)
m_styleSheetCSSOMWrapper->clearOwnerRule();
+
if (m_mediaCSSOMWrapper)
m_mediaCSSOMWrapper->clearParentRule();
+#endif // ENABLE(OILPAN)
}
String CSSImportRule::href() const
@@ -91,4 +94,12 @@ void CSSImportRule::reattach(StyleRuleBase*)
ASSERT_NOT_REACHED();
}
+void CSSImportRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_importRule);
+ visitor->trace(m_mediaCSSOMWrapper);
+ visitor->trace(m_styleSheetCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSImportRule.h b/chromium/third_party/WebKit/Source/core/css/CSSImportRule.h
index 0abfc9a3284..117e60de469 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSImportRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSImportRule.h
@@ -23,6 +23,7 @@
#define CSSImportRule_h
#include "core/css/CSSRule.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -31,9 +32,12 @@ class MediaList;
class MediaQuerySet;
class StyleRuleImport;
-class CSSImportRule : public CSSRule {
+class CSSImportRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSImportRule> create(StyleRuleImport* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSImportRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSImportRule> create(StyleRuleImport* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSImportRule(rule, sheet));
+ }
virtual ~CSSImportRule();
@@ -45,12 +49,14 @@ public:
MediaList* media() const;
CSSStyleSheet* styleSheet() const;
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSImportRule(StyleRuleImport*, CSSStyleSheet*);
- RefPtr<StyleRuleImport> m_importRule;
- mutable RefPtr<MediaList> m_mediaCSSOMWrapper;
- mutable RefPtr<CSSStyleSheet> m_styleSheetCSSOMWrapper;
+ RefPtrWillBeMember<StyleRuleImport> m_importRule;
+ mutable RefPtrWillBeMember<MediaList> m_mediaCSSOMWrapper;
+ mutable RefPtrWillBeMember<CSSStyleSheet> m_styleSheetCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSImportRule, IMPORT_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSInheritedValue.h b/chromium/third_party/WebKit/Source/core/css/CSSInheritedValue.h
index 7367707daf6..8f1fe97225a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSInheritedValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSInheritedValue.h
@@ -28,15 +28,17 @@ namespace WebCore {
class CSSInheritedValue : public CSSValue {
public:
- static PassRefPtr<CSSInheritedValue> create()
+ static PassRefPtrWillBeRawPtr<CSSInheritedValue> create()
{
- return adoptRef(new CSSInheritedValue);
+ return adoptRefWillBeNoop(new CSSInheritedValue);
}
String customCSSText() const;
bool equals(const CSSInheritedValue&) const { return true; }
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSInheritedValue()
: CSSValue(InheritedClass)
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSInitialValue.h b/chromium/third_party/WebKit/Source/core/css/CSSInitialValue.h
index f8f9e512fce..43d82de9631 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSInitialValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSInitialValue.h
@@ -28,13 +28,13 @@ namespace WebCore {
class CSSInitialValue : public CSSValue {
public:
- static PassRefPtr<CSSInitialValue> createExplicit()
+ static PassRefPtrWillBeRawPtr<CSSInitialValue> createExplicit()
{
- return adoptRef(new CSSInitialValue(/* implicit */ false));
+ return adoptRefWillBeNoop(new CSSInitialValue(/* implicit */ false));
}
- static PassRefPtr<CSSInitialValue> createImplicit()
+ static PassRefPtrWillBeRawPtr<CSSInitialValue> createImplicit()
{
- return adoptRef(new CSSInitialValue(/* implicit */ true));
+ return adoptRefWillBeNoop(new CSSInitialValue(/* implicit */ true));
}
String customCSSText() const;
@@ -43,6 +43,8 @@ public:
bool equals(const CSSInitialValue&) const { return true; }
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
explicit CSSInitialValue(bool implicit)
: CSSValue(InitialClass)
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.cpp
index 65aa3077c93..34e395660ad 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.cpp
@@ -27,9 +27,10 @@
#include "core/css/CSSKeyframeRule.h"
#include "core/css/CSSKeyframesRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/PropertySetCSSStyleDeclaration.h"
#include "core/css/StylePropertySet.h"
+#include "core/frame/UseCounter.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
@@ -76,7 +77,7 @@ const Vector<double>& StyleKeyframe::keys() const
// Keys can only be cleared by setting the key text from JavaScript
// and this can never be null.
ASSERT(!m_keyText.isNull());
- m_keys = CSSParser(HTMLStandardMode).parseKeyframeKeyList(m_keyText);
+ m_keys = BisonCSSParser(strictCSSParserContext()).parseKeyframeKeyList(m_keyText);
}
// If an invalid key string was set, m_keys may be empty.
ASSERT(m_keys);
@@ -91,15 +92,16 @@ void StyleKeyframe::setKeys(PassOwnPtr<Vector<double> > keys)
ASSERT(m_keyText.isNull());
}
-MutableStylePropertySet* StyleKeyframe::mutableProperties()
+MutableStylePropertySet& StyleKeyframe::mutableProperties()
{
if (!m_properties->isMutable())
m_properties = m_properties->mutableCopy();
- return toMutableStylePropertySet(m_properties);
+ return *toMutableStylePropertySet(m_properties);
}
void StyleKeyframe::setProperties(PassRefPtr<StylePropertySet> properties)
{
+ ASSERT(properties);
m_properties = properties;
}
@@ -144,8 +146,10 @@ CSSKeyframeRule::CSSKeyframeRule(StyleKeyframe* keyframe, CSSKeyframesRule* pare
CSSKeyframeRule::~CSSKeyframeRule()
{
+#if !ENABLE(OILPAN)
if (m_propertiesCSSOMWrapper)
m_propertiesCSSOMWrapper->clearParentRule();
+#endif
}
CSSStyleDeclaration* CSSKeyframeRule::style() const
@@ -161,4 +165,11 @@ void CSSKeyframeRule::reattach(StyleRuleBase*)
ASSERT_NOT_REACHED();
}
+void CSSKeyframeRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_keyframe);
+ visitor->trace(m_propertiesCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.h b/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.h
index 594314808f9..48f1bfaf0a5 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSKeyframeRule.h
@@ -37,12 +37,12 @@ class MutableStylePropertySet;
class StylePropertySet;
class StyleRuleCSSStyleDeclaration;
-class StyleKeyframe FINAL : public RefCounted<StyleKeyframe> {
- WTF_MAKE_FAST_ALLOCATED;
+class StyleKeyframe FINAL : public RefCountedWillBeGarbageCollectedFinalized<StyleKeyframe> {
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- static PassRefPtr<StyleKeyframe> create()
+ static PassRefPtrWillBeRawPtr<StyleKeyframe> create()
{
- return adoptRef(new StyleKeyframe());
+ return adoptRefWillBeNoop(new StyleKeyframe());
}
~StyleKeyframe();
@@ -52,15 +52,17 @@ public:
// Used by StyleResolver.
const Vector<double>& keys() const;
- // Used by CSSParser when constructing a new StyleKeyframe.
+ // Used by BisonCSSParser when constructing a new StyleKeyframe.
void setKeys(PassOwnPtr<Vector<double> >);
- const StylePropertySet* properties() const { return m_properties.get(); }
- MutableStylePropertySet* mutableProperties();
+ const StylePropertySet& properties() const { return *m_properties; }
+ MutableStylePropertySet& mutableProperties();
void setProperties(PassRefPtr<StylePropertySet>);
String cssText() const;
+ void trace(Visitor*) { }
+
static PassOwnPtr<Vector<double> > createKeyList(CSSParserValueList*);
private:
@@ -85,11 +87,13 @@ public:
CSSStyleDeclaration* style() const;
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSKeyframeRule(StyleKeyframe*, CSSKeyframesRule* parent);
- RefPtr<StyleKeyframe> m_keyframe;
- mutable RefPtr<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
+ RefPtrWillBeMember<StyleKeyframe> m_keyframe;
+ mutable RefPtrWillBeMember<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
friend class CSSKeyframesRule;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.cpp
index 94d5dff8e6a..cd78e79f272 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.cpp
@@ -27,9 +27,10 @@
#include "core/css/CSSKeyframesRule.h"
#include "core/css/CSSKeyframeRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSRuleList.h"
#include "core/css/CSSStyleSheet.h"
+#include "core/frame/UseCounter.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
@@ -51,14 +52,14 @@ StyleRuleKeyframes::~StyleRuleKeyframes()
{
}
-void StyleRuleKeyframes::parserAppendKeyframe(PassRefPtr<StyleKeyframe> keyframe)
+void StyleRuleKeyframes::parserAppendKeyframe(PassRefPtrWillBeRawPtr<StyleKeyframe> keyframe)
{
if (!keyframe)
return;
m_keyframes.append(keyframe);
}
-void StyleRuleKeyframes::wrapperAppendKeyframe(PassRefPtr<StyleKeyframe> keyframe)
+void StyleRuleKeyframes::wrapperAppendKeyframe(PassRefPtrWillBeRawPtr<StyleKeyframe> keyframe)
{
m_keyframes.append(keyframe);
}
@@ -85,6 +86,12 @@ int StyleRuleKeyframes::findKeyframeIndex(const String& key) const
return -1;
}
+void StyleRuleKeyframes::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_keyframes);
+ StyleRuleBase::traceAfterDispatch(visitor);
+}
+
CSSKeyframesRule::CSSKeyframesRule(StyleRuleKeyframes* keyframesRule, CSSStyleSheet* parent)
: CSSRule(parent)
, m_keyframesRule(keyframesRule)
@@ -95,12 +102,13 @@ CSSKeyframesRule::CSSKeyframesRule(StyleRuleKeyframes* keyframesRule, CSSStyleSh
CSSKeyframesRule::~CSSKeyframesRule()
{
+#if !ENABLE(OILPAN)
ASSERT(m_childRuleCSSOMWrappers.size() == m_keyframesRule->keyframes().size());
-
for (unsigned i = 0; i < m_childRuleCSSOMWrappers.size(); ++i) {
if (m_childRuleCSSOMWrappers[i])
m_childRuleCSSOMWrappers[i]->setParentRule(0);
}
+#endif
}
void CSSKeyframesRule::setName(const String& name)
@@ -115,8 +123,9 @@ void CSSKeyframesRule::insertRule(const String& ruleText)
ASSERT(m_childRuleCSSOMWrappers.size() == m_keyframesRule->keyframes().size());
CSSStyleSheet* styleSheet = parentStyleSheet();
- CSSParser parser(parserContext(), UseCounter::getFrom(styleSheet));
- RefPtr<StyleKeyframe> keyframe = parser.parseKeyframeRule(styleSheet ? styleSheet->contents() : 0, ruleText);
+ CSSParserContext context(parserContext(), UseCounter::getFrom(styleSheet));
+ BisonCSSParser parser(context);
+ RefPtrWillBeRawPtr<StyleKeyframe> keyframe = parser.parseKeyframeRule(styleSheet ? styleSheet->contents() : 0, ruleText);
if (!keyframe)
return;
@@ -181,9 +190,9 @@ CSSKeyframeRule* CSSKeyframesRule::item(unsigned index) const
return 0;
ASSERT(m_childRuleCSSOMWrappers.size() == m_keyframesRule->keyframes().size());
- RefPtr<CSSKeyframeRule>& rule = m_childRuleCSSOMWrappers[index];
+ RefPtrWillBeMember<CSSKeyframeRule>& rule = m_childRuleCSSOMWrappers[index];
if (!rule)
- rule = adoptRef(new CSSKeyframeRule(m_keyframesRule->keyframes()[index].get(), const_cast<CSSKeyframesRule*>(this)));
+ rule = adoptRefWillBeNoop(new CSSKeyframeRule(m_keyframesRule->keyframes()[index].get(), const_cast<CSSKeyframesRule*>(this)));
return rule.get();
}
@@ -191,7 +200,7 @@ CSSKeyframeRule* CSSKeyframesRule::item(unsigned index) const
CSSRuleList* CSSKeyframesRule::cssRules()
{
if (!m_ruleListCSSOMWrapper)
- m_ruleListCSSOMWrapper = adoptPtr(new LiveCSSRuleList<CSSKeyframesRule>(this));
+ m_ruleListCSSOMWrapper = LiveCSSRuleList<CSSKeyframesRule>::create(this);
return m_ruleListCSSOMWrapper.get();
}
@@ -201,4 +210,14 @@ void CSSKeyframesRule::reattach(StyleRuleBase* rule)
m_keyframesRule = toStyleRuleKeyframes(rule);
}
+void CSSKeyframesRule::trace(Visitor* visitor)
+{
+ CSSRule::trace(visitor);
+#if ENABLE(OILPAN)
+ visitor->trace(m_childRuleCSSOMWrappers);
+#endif
+ visitor->trace(m_keyframesRule);
+ visitor->trace(m_ruleListCSSOMWrapper);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.h b/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.h
index d74cf686e75..aebdc196933 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.h
@@ -39,14 +39,14 @@ class CSSKeyframeRule;
class StyleRuleKeyframes FINAL : public StyleRuleBase {
public:
- static PassRefPtr<StyleRuleKeyframes> create() { return adoptRef(new StyleRuleKeyframes()); }
+ static PassRefPtrWillBeRawPtr<StyleRuleKeyframes> create() { return adoptRefWillBeNoop(new StyleRuleKeyframes()); }
~StyleRuleKeyframes();
- const Vector<RefPtr<StyleKeyframe> >& keyframes() const { return m_keyframes; }
+ const WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >& keyframes() const { return m_keyframes; }
- void parserAppendKeyframe(PassRefPtr<StyleKeyframe>);
- void wrapperAppendKeyframe(PassRefPtr<StyleKeyframe>);
+ void parserAppendKeyframe(PassRefPtrWillBeRawPtr<StyleKeyframe>);
+ void wrapperAppendKeyframe(PassRefPtrWillBeRawPtr<StyleKeyframe>);
void wrapperRemoveKeyframe(unsigned);
String name() const { return m_name; }
@@ -57,13 +57,15 @@ public:
int findKeyframeIndex(const String& key) const;
- PassRefPtr<StyleRuleKeyframes> copy() const { return adoptRef(new StyleRuleKeyframes(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRuleKeyframes> copy() const { return adoptRefWillBeNoop(new StyleRuleKeyframes(*this)); }
+
+ void traceAfterDispatch(Visitor*);
private:
StyleRuleKeyframes();
explicit StyleRuleKeyframes(const StyleRuleKeyframes&);
- Vector<RefPtr<StyleKeyframe> > m_keyframes;
+ WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > m_keyframes;
AtomicString m_name;
bool m_isPrefixed;
};
@@ -72,7 +74,10 @@ DEFINE_STYLE_RULE_TYPE_CASTS(Keyframes);
class CSSKeyframesRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSKeyframesRule> create(StyleRuleKeyframes* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSKeyframesRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSKeyframesRule> create(StyleRuleKeyframes* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSKeyframesRule(rule, sheet));
+ }
virtual ~CSSKeyframesRule();
@@ -96,12 +101,14 @@ public:
bool isVendorPrefixed() const { return m_isPrefixed; }
void setVendorPrefixed(bool isPrefixed) { m_isPrefixed = isPrefixed; }
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSKeyframesRule(StyleRuleKeyframes*, CSSStyleSheet* parent);
- RefPtr<StyleRuleKeyframes> m_keyframesRule;
- mutable Vector<RefPtr<CSSKeyframeRule> > m_childRuleCSSOMWrappers;
- mutable OwnPtr<CSSRuleList> m_ruleListCSSOMWrapper;
+ RefPtrWillBeMember<StyleRuleKeyframes> m_keyframesRule;
+ mutable WillBeHeapVector<RefPtrWillBeMember<CSSKeyframeRule> > m_childRuleCSSOMWrappers;
+ mutable OwnPtrWillBeMember<CSSRuleList> m_ruleListCSSOMWrapper;
bool m_isPrefixed;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.idl b/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.idl
index d97dd4aae3b..d85f8d19f17 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSKeyframesRule.idl
@@ -31,7 +31,7 @@ interface CSSKeyframesRule : CSSRule {
attribute DOMString name;
readonly attribute CSSRuleList cssRules;
- [ImplementedAs=item, NotEnumerable] getter CSSKeyframeRule(unsigned long index);
+ [ImplementedAs=item, NotEnumerable] getter CSSKeyframeRule (unsigned long index);
void insertRule([Default=Undefined] optional DOMString rule);
void deleteRule([Default=Undefined] optional DOMString key);
CSSKeyframeRule findRule([Default=Undefined] optional DOMString key);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.cpp b/chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.cpp
deleted file mode 100644
index 94acda3c866..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.cpp
+++ /dev/null
@@ -1,149 +0,0 @@
-/*
- Copyright (C) 1999 Lars Knoll (knoll@kde.org)
- Copyright (C) 2006, 2008 Apple Inc. All rights reserved.
- Copyright (C) 2011 Rik Cabanier (cabanier@adobe.com)
- Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- Copyright (C) 2012 Motorola Mobility, Inc. All rights reserved.
- Copyright (C) 2013 Google, Inc. All rights reserved.
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Library General Public
- License as published by the Free Software Foundation; either
- version 2 of the License, or (at your option) any later version.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Library General Public License for more details.
-
- You should have received a copy of the GNU Library General Public License
- along with this library; see the file COPYING.LIB. If not, write to
- the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
-*/
-
-#include "config.h"
-#include "core/css/CSSLengthFunctions.h"
-
-#include "core/rendering/RenderView.h"
-#include "platform/LayoutUnit.h"
-#include "platform/Length.h"
-#include "platform/LengthFunctions.h"
-
-namespace WebCore {
-
-int minimumIntValueForLength(const Length& length, LayoutUnit maximumValue, RenderView* renderView, bool roundPercentages)
-{
- return static_cast<int>(minimumValueForLength(length, maximumValue, renderView, roundPercentages));
-}
-
-int intValueForLength(const Length& length, LayoutUnit maximumValue, RenderView* renderView, bool roundPercentages)
-{
- return static_cast<int>(valueForLength(length, maximumValue, renderView, roundPercentages));
-}
-
-LayoutUnit minimumValueForLength(const Length& length, LayoutUnit maximumValue, RenderView* renderView, bool roundPercentages)
-{
- switch (length.type()) {
- case Fixed:
- return length.value();
- case Percent:
- if (roundPercentages)
- return static_cast<LayoutUnit>(round(maximumValue * length.percent() / 100.0f));
- // Don't remove the extra cast to float. It is needed for rounding on 32-bit Intel machines that use the FPU stack.
- return static_cast<float>(maximumValue * length.percent() / 100.0f);
- case Calculated:
- return length.nonNanCalculatedValue(maximumValue);
- case ViewportPercentageWidth:
- return renderView ? renderView->viewportPercentageWidth(length.viewportPercentageLength()) : LayoutUnit(0);
- case ViewportPercentageHeight:
- return renderView ? renderView->viewportPercentageHeight(length.viewportPercentageLength()) : LayoutUnit(0);
- case ViewportPercentageMin:
- return renderView ? renderView->viewportPercentageMin(length.viewportPercentageLength()) : LayoutUnit(0);
- case ViewportPercentageMax:
- return renderView ? renderView->viewportPercentageMax(length.viewportPercentageLength()) : LayoutUnit(0);
- case FillAvailable:
- case Auto:
- return 0;
- case Intrinsic:
- case MinIntrinsic:
- case MinContent:
- case MaxContent:
- case FitContent:
- case ExtendToZoom:
- case Undefined:
- ASSERT_NOT_REACHED();
- return 0;
- }
- ASSERT_NOT_REACHED();
- return 0;
-}
-
-LayoutUnit valueForLength(const Length& length, LayoutUnit maximumValue, RenderView* renderView, bool roundPercentages)
-{
- switch (length.type()) {
- case Fixed:
- case Percent:
- case Calculated:
- case ViewportPercentageWidth:
- case ViewportPercentageHeight:
- case ViewportPercentageMin:
- case ViewportPercentageMax:
- return minimumValueForLength(length, maximumValue, renderView, roundPercentages);
- case FillAvailable:
- case Auto:
- return maximumValue;
- case Intrinsic:
- case MinIntrinsic:
- case MinContent:
- case MaxContent:
- case FitContent:
- case ExtendToZoom:
- case Undefined:
- ASSERT_NOT_REACHED();
- return 0;
- }
- ASSERT_NOT_REACHED();
- return 0;
-}
-
-// This method has code duplicated in platform/LengthFunctions.cpp.
-// Any changes here most likely also need to be applied there.
-float floatValueForLength(const Length& length, float maximumValue, RenderView* renderView)
-{
- if (!renderView)
- return floatValueForLength(length, maximumValue);
-
- switch (length.type()) {
- case Fixed:
- return length.getFloatValue();
- case Percent:
- return static_cast<float>(maximumValue * length.percent() / 100.0f);
- case FillAvailable:
- case Auto:
- return static_cast<float>(maximumValue);
- case Calculated:
- return length.nonNanCalculatedValue(maximumValue);
- case ViewportPercentageWidth:
- return static_cast<int>(renderView->viewportPercentageWidth(length.viewportPercentageLength()));
- case ViewportPercentageHeight:
- return static_cast<int>(renderView->viewportPercentageHeight(length.viewportPercentageLength()));
- case ViewportPercentageMin:
- return static_cast<int>(renderView->viewportPercentageMin(length.viewportPercentageLength()));
- case ViewportPercentageMax:
- return static_cast<int>(renderView->viewportPercentageMax(length.viewportPercentageLength()));
- case Intrinsic:
- case MinIntrinsic:
- case MinContent:
- case MaxContent:
- case FitContent:
- case ExtendToZoom:
- case Undefined:
- ASSERT_NOT_REACHED();
- return 0;
- }
- ASSERT_NOT_REACHED();
- return 0;
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.h b/chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.h
deleted file mode 100644
index 46e3540c180..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSLengthFunctions.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- Copyright (C) 1999 Lars Knoll (knoll@kde.org)
- Copyright (C) 2006, 2008 Apple Inc. All rights reserved.
- Copyright (C) 2011 Rik Cabanier (cabanier@adobe.com)
- Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- Copyright (C) 2012 Motorola Mobility, Inc. All rights reserved.
- Copyright (C) 2013 Google, Inc. All rights reserved.
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Library General Public
- License as published by the Free Software Foundation; either
- version 2 of the License, or (at your option) any later version.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Library General Public License for more details.
-
- You should have received a copy of the GNU Library General Public License
- along with this library; see the file COPYING.LIB. If not, write to
- the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
-*/
-
-#ifndef CSSLengthFunctions_h
-#define CSSLengthFunctions_h
-
-namespace WebCore {
-
-class LayoutUnit;
-class Length;
-class RenderView;
-
-int minimumIntValueForLength(const Length&, LayoutUnit maximumValue, RenderView* = 0, bool roundPercentages = false);
-int intValueForLength(const Length&, LayoutUnit maximumValue, RenderView* = 0, bool roundPercentages = false);
-LayoutUnit minimumValueForLength(const Length&, LayoutUnit maximumValue, RenderView* = 0, bool roundPercentages = false);
-LayoutUnit valueForLength(const Length&, LayoutUnit maximumValue, RenderView* = 0, bool roundPercentages = false);
-float floatValueForLength(const Length&, float maximumValue, RenderView*);
-
-} // namespace WebCore
-
-#endif // CSSLengthFunctions_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSLineBoxContainValue.h b/chromium/third_party/WebKit/Source/core/css/CSSLineBoxContainValue.h
index 657578ab251..92d6de2203f 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSLineBoxContainValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSLineBoxContainValue.h
@@ -40,15 +40,17 @@ typedef unsigned LineBoxContain;
// Used for text-CSSLineBoxContain and box-CSSLineBoxContain
class CSSLineBoxContainValue : public CSSValue {
public:
- static PassRefPtr<CSSLineBoxContainValue> create(LineBoxContain value)
+ static PassRefPtrWillBeRawPtr<CSSLineBoxContainValue> create(LineBoxContain value)
{
- return adoptRef(new CSSLineBoxContainValue(value));
+ return adoptRefWillBeNoop(new CSSLineBoxContainValue(value));
}
String customCSSText() const;
bool equals(const CSSLineBoxContainValue& other) const { return m_value == other.m_value; }
LineBoxContain value() const { return m_value; }
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
LineBoxContain m_value;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMarkup.cpp b/chromium/third_party/WebKit/Source/core/css/CSSMarkup.cpp
new file mode 100644
index 00000000000..cc473538a06
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/CSSMarkup.cpp
@@ -0,0 +1,189 @@
+/*
+ * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
+ * Copyright (C) 2005 Allan Sandfeld Jensen (kde@carewolf.com)
+ * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved.
+ * Copyright (C) 2007 Nicholas Shanks <webkit@nickshanks.com>
+ * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
+ * Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
+ * Copyright (C) 2012 Adobe Systems Incorporated. All rights reserved.
+ * Copyright (C) 2012 Intel Corporation. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include "config.h"
+#include "core/css/CSSMarkup.h"
+
+#include "wtf/HexNumber.h"
+#include "wtf/text/StringBuffer.h"
+
+namespace WebCore {
+
+template <typename CharacterType>
+static inline bool isCSSTokenizerIdentifier(const CharacterType* characters, unsigned length)
+{
+ const CharacterType* end = characters + length;
+
+ // -?
+ if (characters != end && characters[0] == '-')
+ ++characters;
+
+ // {nmstart}
+ if (characters == end || !(characters[0] == '_' || characters[0] >= 128 || isASCIIAlpha(characters[0])))
+ return false;
+ ++characters;
+
+ // {nmchar}*
+ for (; characters != end; ++characters) {
+ if (!(characters[0] == '_' || characters[0] == '-' || characters[0] >= 128 || isASCIIAlphanumeric(characters[0])))
+ return false;
+ }
+
+ return true;
+}
+
+// "ident" from the CSS tokenizer, minus backslash-escape sequences
+static bool isCSSTokenizerIdentifier(const String& string)
+{
+ unsigned length = string.length();
+
+ if (!length)
+ return false;
+
+ if (string.is8Bit())
+ return isCSSTokenizerIdentifier(string.characters8(), length);
+ return isCSSTokenizerIdentifier(string.characters16(), length);
+}
+
+template <typename CharacterType>
+static inline bool isCSSTokenizerURL(const CharacterType* characters, unsigned length)
+{
+ const CharacterType* end = characters + length;
+
+ for (; characters != end; ++characters) {
+ CharacterType c = characters[0];
+ switch (c) {
+ case '!':
+ case '#':
+ case '$':
+ case '%':
+ case '&':
+ break;
+ default:
+ if (c < '*')
+ return false;
+ if (c <= '~')
+ break;
+ if (c < 128)
+ return false;
+ }
+ }
+
+ return true;
+}
+
+// "url" from the CSS tokenizer, minus backslash-escape sequences
+static bool isCSSTokenizerURL(const String& string)
+{
+ unsigned length = string.length();
+
+ if (!length)
+ return true;
+
+ if (string.is8Bit())
+ return isCSSTokenizerURL(string.characters8(), length);
+ return isCSSTokenizerURL(string.characters16(), length);
+}
+
+template <typename CharacterType>
+static inline String quoteCSSStringInternal(const CharacterType* characters, unsigned length)
+{
+ // For efficiency, we first pre-calculate the length of the quoted string, then we build the actual one.
+ // Please see below for the actual logic.
+ unsigned quotedStringSize = 2; // Two quotes surrounding the entire string.
+ bool afterEscape = false;
+ for (unsigned i = 0; i < length; ++i) {
+ CharacterType ch = characters[i];
+ if (ch == '\\' || ch == '\'') {
+ quotedStringSize += 2;
+ afterEscape = false;
+ } else if (ch < 0x20 || ch == 0x7F) {
+ quotedStringSize += 2 + (ch >= 0x10);
+ afterEscape = true;
+ } else {
+ quotedStringSize += 1 + (afterEscape && (isASCIIHexDigit(ch) || ch == ' '));
+ afterEscape = false;
+ }
+ }
+
+ StringBuffer<CharacterType> buffer(quotedStringSize);
+ unsigned index = 0;
+ buffer[index++] = '\'';
+ afterEscape = false;
+ for (unsigned i = 0; i < length; ++i) {
+ CharacterType ch = characters[i];
+ if (ch == '\\' || ch == '\'') {
+ buffer[index++] = '\\';
+ buffer[index++] = ch;
+ afterEscape = false;
+ } else if (ch < 0x20 || ch == 0x7F) { // Control characters.
+ buffer[index++] = '\\';
+ placeByteAsHexCompressIfPossible(ch, buffer, index, Lowercase);
+ afterEscape = true;
+ } else {
+ // Space character may be required to separate backslash-escape sequence and normal characters.
+ if (afterEscape && (isASCIIHexDigit(ch) || ch == ' '))
+ buffer[index++] = ' ';
+ buffer[index++] = ch;
+ afterEscape = false;
+ }
+ }
+ buffer[index++] = '\'';
+
+ ASSERT(quotedStringSize == index);
+ return String::adopt(buffer);
+}
+
+// We use single quotes for now because markup.cpp uses double quotes.
+String quoteCSSString(const String& string)
+{
+ // This function expands each character to at most 3 characters ('\u0010' -> '\' '1' '0') as well as adds
+ // 2 quote characters (before and after). Make sure the resulting size (3 * length + 2) will not overflow unsigned.
+
+ unsigned length = string.length();
+
+ if (!length)
+ return String("\'\'");
+
+ if (length > std::numeric_limits<unsigned>::max() / 3 - 2)
+ return emptyString();
+
+ if (string.is8Bit())
+ return quoteCSSStringInternal(string.characters8(), length);
+ return quoteCSSStringInternal(string.characters16(), length);
+}
+
+String quoteCSSStringIfNeeded(const String& string)
+{
+ return isCSSTokenizerIdentifier(string) ? string : quoteCSSString(string);
+}
+
+String quoteCSSURLIfNeeded(const String& string)
+{
+ return isCSSTokenizerURL(string) ? string : quoteCSSString(string);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.cpp b/chromium/third_party/WebKit/Source/core/css/CSSMarkup.h
index 2db2bd92e9d..9d37fff3336 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSMarkup.h
@@ -1,5 +1,8 @@
/*
- * Copyright (C) 2005 Apple Computer, Inc.
+ * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
+ * Copyright (C) 2004, 2005, 2006, 2008, 2009, 2010 Apple Inc. All rights reserved.
+ * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
+ * Copyright (C) 2009 - 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
@@ -15,33 +18,23 @@
* along with this library; see the file COPYING.LIB. If not, write to
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
* Boston, MA 02110-1301, USA.
- *
*/
-#include "config.h"
-
-#ifdef SKIP_STATIC_CONSTRUCTORS_ON_GCC
-#define CSS_MEDIAQUERY_NAMES_HIDE_GLOBALS 1
-#endif
+#ifndef CSSMarkup_h
+#define CSSMarkup_h
-#include "core/css/MediaFeatureNames.h"
+#include "wtf/text/WTFString.h"
-#include "wtf/StaticConstructors.h"
+// Helper functions for converting from CSSValues to text.
+// FIXME: This file has a similar purpose to
+// CSSOMUtils.h. Perhaps the two should be combined?
namespace WebCore {
-namespace MediaFeatureNames {
-#define DEFINE_MEDIAFEATURE_GLOBAL(name, str) \
- DEFINE_GLOBAL(AtomicString, name##MediaFeature, str)
-CSS_MEDIAQUERY_NAMES_FOR_EACH_MEDIAFEATURE(DEFINE_MEDIAFEATURE_GLOBAL)
-#undef DEFINE_MEDIAFEATURE_GLOBAL
+String quoteCSSString(const String&);
+String quoteCSSStringIfNeeded(const String&);
+String quoteCSSURLIfNeeded(const String&);
-void init()
-{
-#define INITIALIZE_GLOBAL(name, str) new (NotNull, (void*)&name##MediaFeature) AtomicString(str, AtomicString::ConstructFromLiteral);
- CSS_MEDIAQUERY_NAMES_FOR_EACH_MEDIAFEATURE(INITIALIZE_GLOBAL)
-#undef INITIALIZE_GLOBAL
-}
-
-} // namespace MediaFeatureNames
} // namespace WebCore
+
+#endif // CSSMarkup_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMatrix.cpp b/chromium/third_party/WebKit/Source/core/css/CSSMatrix.cpp
index 4926df97629..dc974c1a003 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSMatrix.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSMatrix.cpp
@@ -26,10 +26,10 @@
#include "config.h"
#include "core/css/CSSMatrix.h"
-#include "CSSPropertyNames.h"
-#include "CSSValueKeywords.h"
#include "bindings/v8/ExceptionState.h"
-#include "core/css/CSSParser.h"
+#include "core/CSSPropertyNames.h"
+#include "core/CSSValueKeywords.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSToLengthConversionData.h"
#include "core/css/StylePropertySet.h"
#include "core/css/resolver/TransformBuilder.h"
@@ -57,11 +57,12 @@ void CSSMatrix::setMatrixValue(const String& string, ExceptionState& exceptionSt
if (string.isEmpty())
return;
- RefPtr<MutableStylePropertySet> styleDeclaration = MutableStylePropertySet::create();
- if (CSSParser::parseValue(styleDeclaration.get(), CSSPropertyWebkitTransform, string, true, HTMLStandardMode, 0)) {
+ // FIXME: crbug.com/154722 - should this continue to use legacy style parsing?
+ RefPtrWillBeRawPtr<MutableStylePropertySet> styleDeclaration = MutableStylePropertySet::create();
+ if (BisonCSSParser::parseValue(styleDeclaration.get(), CSSPropertyWebkitTransform, string, true, HTMLStandardMode, 0)) {
// Convert to TransformOperations. This can fail if a property
// requires style (i.e., param uses 'ems' or 'exs')
- RefPtr<CSSValue> value = styleDeclaration->getPropertyCSSValue(CSSPropertyWebkitTransform);
+ RefPtrWillBeRawPtr<CSSValue> value = styleDeclaration->getPropertyCSSValue(CSSPropertyWebkitTransform);
// Check for a "none" or empty transform. In these cases we can use the default identity matrix.
if (!value || (value->isPrimitiveValue() && (toCSSPrimitiveValue(value.get()))->getValueID() == CSSValueNone))
@@ -69,45 +70,45 @@ void CSSMatrix::setMatrixValue(const String& string, ExceptionState& exceptionSt
DEFINE_STATIC_REF(RenderStyle, defaultStyle, RenderStyle::createDefaultStyle());
TransformOperations operations;
- if (!TransformBuilder::createTransformOperations(value.get(), CSSToLengthConversionData(defaultStyle, defaultStyle), operations)) {
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
+ if (!TransformBuilder::createTransformOperations(value.get(), CSSToLengthConversionData(defaultStyle, defaultStyle, 0, 0, 1.0f), operations)) {
+ exceptionState.throwDOMException(SyntaxError, "Failed to interpret '" + string + "' as a transformation operation.");
return;
}
// Convert transform operations to a TransformationMatrix. This can fail
// if a param has a percentage ('%')
if (operations.dependsOnBoxSize())
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
+ exceptionState.throwDOMException(SyntaxError, "The transformation depends on the box size, which is not supported.");
TransformationMatrix t;
operations.apply(FloatSize(0, 0), t);
// set the matrix
m_matrix = t;
} else { // There is something there but parsing failed.
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
+ exceptionState.throwDOMException(SyntaxError, "Failed to parse '" + string + "'.");
}
}
// Perform a concatenation of the matrices (this * secondMatrix)
-PassRefPtr<CSSMatrix> CSSMatrix::multiply(CSSMatrix* secondMatrix) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::multiply(CSSMatrix* secondMatrix) const
{
if (!secondMatrix)
- return 0;
+ return nullptr;
return CSSMatrix::create(TransformationMatrix(m_matrix).multiply(secondMatrix->m_matrix));
}
-PassRefPtr<CSSMatrix> CSSMatrix::inverse(ExceptionState& exceptionState) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::inverse(ExceptionState& exceptionState) const
{
if (!m_matrix.isInvertible()) {
- exceptionState.throwUninformativeAndGenericDOMException(NotSupportedError);
- return 0;
+ exceptionState.throwDOMException(NotSupportedError, "The matrix is not invertable.");
+ return nullptr;
}
return CSSMatrix::create(m_matrix.inverse());
}
-PassRefPtr<CSSMatrix> CSSMatrix::translate(double x, double y, double z) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::translate(double x, double y, double z) const
{
if (std::isnan(x))
x = 0;
@@ -118,7 +119,7 @@ PassRefPtr<CSSMatrix> CSSMatrix::translate(double x, double y, double z) const
return CSSMatrix::create(TransformationMatrix(m_matrix).translate3d(x, y, z));
}
-PassRefPtr<CSSMatrix> CSSMatrix::scale(double scaleX, double scaleY, double scaleZ) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::scale(double scaleX, double scaleY, double scaleZ) const
{
if (std::isnan(scaleX))
scaleX = 1;
@@ -129,7 +130,7 @@ PassRefPtr<CSSMatrix> CSSMatrix::scale(double scaleX, double scaleY, double scal
return CSSMatrix::create(TransformationMatrix(m_matrix).scale3d(scaleX, scaleY, scaleZ));
}
-PassRefPtr<CSSMatrix> CSSMatrix::rotate(double rotX, double rotY, double rotZ) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::rotate(double rotX, double rotY, double rotZ) const
{
if (std::isnan(rotX))
rotX = 0;
@@ -147,7 +148,7 @@ PassRefPtr<CSSMatrix> CSSMatrix::rotate(double rotX, double rotY, double rotZ) c
return CSSMatrix::create(TransformationMatrix(m_matrix).rotate3d(rotX, rotY, rotZ));
}
-PassRefPtr<CSSMatrix> CSSMatrix::rotateAxisAngle(double x, double y, double z, double angle) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::rotateAxisAngle(double x, double y, double z, double angle) const
{
if (std::isnan(x))
x = 0;
@@ -162,14 +163,14 @@ PassRefPtr<CSSMatrix> CSSMatrix::rotateAxisAngle(double x, double y, double z, d
return CSSMatrix::create(TransformationMatrix(m_matrix).rotate3d(x, y, z, angle));
}
-PassRefPtr<CSSMatrix> CSSMatrix::skewX(double angle) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::skewX(double angle) const
{
if (std::isnan(angle))
angle = 0;
return CSSMatrix::create(TransformationMatrix(m_matrix).skewX(angle));
}
-PassRefPtr<CSSMatrix> CSSMatrix::skewY(double angle) const
+PassRefPtrWillBeRawPtr<CSSMatrix> CSSMatrix::skewY(double angle) const
{
if (std::isnan(angle))
angle = 0;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMatrix.h b/chromium/third_party/WebKit/Source/core/css/CSSMatrix.h
index 92c6cb1ab08..e62009791c2 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSMatrix.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSMatrix.h
@@ -35,15 +35,15 @@ namespace WebCore {
class ExceptionState;
-class CSSMatrix FINAL : public ScriptWrappable, public RefCounted<CSSMatrix> {
+class CSSMatrix FINAL : public RefCountedWillBeGarbageCollectedFinalized<CSSMatrix>, public ScriptWrappable {
public:
- static PassRefPtr<CSSMatrix> create(const TransformationMatrix& m)
+ static PassRefPtrWillBeRawPtr<CSSMatrix> create(const TransformationMatrix& m)
{
- return adoptRef(new CSSMatrix(m));
+ return adoptRefWillBeNoop(new CSSMatrix(m));
}
- static PassRefPtr<CSSMatrix> create(const String& s, ExceptionState& exceptionState)
+ static PassRefPtrWillBeRawPtr<CSSMatrix> create(const String& s, ExceptionState& exceptionState)
{
- return adoptRef(new CSSMatrix(s, exceptionState));
+ return adoptRefWillBeNoop(new CSSMatrix(s, exceptionState));
}
double a() const { return m_matrix.a(); }
@@ -100,53 +100,55 @@ public:
// specified operation applied. The this value is not modified.
// Multiply this matrix by secondMatrix, on the right (result = this * secondMatrix)
- PassRefPtr<CSSMatrix> multiply(CSSMatrix* secondMatrix) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> multiply(CSSMatrix* secondMatrix) const;
// Return the inverse of this matrix. Throw an exception if the matrix is not invertible
- PassRefPtr<CSSMatrix> inverse(ExceptionState&) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> inverse(ExceptionState&) const;
// Return this matrix translated by the passed values.
// Passing a NaN will use a value of 0. This allows the 3D form to used for 2D operations
// Operation is performed as though the this matrix is multiplied by a matrix with
// the translation values on the left (result = translation(x,y,z) * this)
- PassRefPtr<CSSMatrix> translate(double x, double y, double z) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> translate(double x, double y, double z) const;
// Returns this matrix scaled by the passed values.
// Passing scaleX or scaleZ as NaN uses a value of 1, but passing scaleY of NaN
// makes it the same as scaleX. This allows the 3D form to used for 2D operations
// Operation is performed as though the this matrix is multiplied by a matrix with
// the scale values on the left (result = scale(x,y,z) * this)
- PassRefPtr<CSSMatrix> scale(double scaleX, double scaleY, double scaleZ) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> scale(double scaleX, double scaleY, double scaleZ) const;
// Returns this matrix rotated by the passed values.
// If rotY and rotZ are NaN, rotate about Z (rotX=0, rotateY=0, rotateZ=rotX).
// Otherwise use a rotation value of 0 for any passed NaN.
// Operation is performed as though the this matrix is multiplied by a matrix with
// the rotation values on the left (result = rotation(x,y,z) * this)
- PassRefPtr<CSSMatrix> rotate(double rotX, double rotY, double rotZ) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> rotate(double rotX, double rotY, double rotZ) const;
// Returns this matrix rotated about the passed axis by the passed angle.
// Passing a NaN will use a value of 0. If the axis is (0,0,0) use a value
// Operation is performed as though the this matrix is multiplied by a matrix with
// the rotation values on the left (result = rotation(x,y,z,angle) * this)
- PassRefPtr<CSSMatrix> rotateAxisAngle(double x, double y, double z, double angle) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> rotateAxisAngle(double x, double y, double z, double angle) const;
// Return this matrix skewed along the X axis by the passed values.
// Passing a NaN will use a value of 0.
// Operation is performed as though the this matrix is multiplied by a matrix with
// the skew values on the left (result = skewX(angle) * this)
- PassRefPtr<CSSMatrix> skewX(double angle) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> skewX(double angle) const;
// Return this matrix skewed along the Y axis by the passed values.
// Passing a NaN will use a value of 0.
// Operation is performed as though the this matrix is multiplied by a matrix with
// the skew values on the left (result = skewY(angle) * this)
- PassRefPtr<CSSMatrix> skewY(double angle) const;
+ PassRefPtrWillBeRawPtr<CSSMatrix> skewY(double angle) const;
const TransformationMatrix& transform() const { return m_matrix; }
String toString() const;
+ void trace(Visitor*) { }
+
protected:
CSSMatrix(const TransformationMatrix&);
CSSMatrix(const String&, ExceptionState&);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.cpp
index 7e8c34a5945..dedea18c4a3 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.cpp
@@ -35,8 +35,10 @@ CSSMediaRule::CSSMediaRule(StyleRuleMedia* mediaRule, CSSStyleSheet* parent)
CSSMediaRule::~CSSMediaRule()
{
+#if !ENABLE(OILPAN)
if (m_mediaCSSOMWrapper)
m_mediaCSSOMWrapper->clearParentRule();
+#endif
}
MediaQuerySet* CSSMediaRule::mediaQueries() const
@@ -74,4 +76,9 @@ void CSSMediaRule::reattach(StyleRuleBase* rule)
m_mediaCSSOMWrapper->reattach(mediaQueries());
}
+void CSSMediaRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_mediaCSSOMWrapper);
+ CSSGroupingRule::trace(visitor);
+}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.h b/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.h
index 380c062c122..fb6895816d6 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSMediaRule.h
@@ -30,9 +30,12 @@ namespace WebCore {
class StyleRuleMedia;
-class CSSMediaRule : public CSSGroupingRule {
+class CSSMediaRule FINAL : public CSSGroupingRule {
public:
- static PassRefPtr<CSSMediaRule> create(StyleRuleMedia* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSMediaRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSMediaRule> create(StyleRuleMedia* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSMediaRule(rule, sheet));
+ }
virtual ~CSSMediaRule();
@@ -42,12 +45,14 @@ public:
MediaList* media() const;
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSMediaRule(StyleRuleMedia*, CSSStyleSheet*);
MediaQuerySet* mediaQueries() const;
- mutable RefPtr<MediaList> m_mediaCSSOMWrapper;
+ mutable RefPtrWillBeMember<MediaList> m_mediaCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSMediaRule, MEDIA_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.cpp
deleted file mode 100644
index 0dd07a58fee..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.cpp
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2012 Adobe Systems Incorporated. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER “AS IS” AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "core/css/CSSMixFunctionValue.h"
-
-namespace WebCore {
-
-CSSMixFunctionValue::CSSMixFunctionValue()
- : CSSValueList(CSSMixFunctionValueClass, SpaceSeparator)
-{
-}
-
-CSSMixFunctionValue::CSSMixFunctionValue(const CSSMixFunctionValue& cloneFrom)
- : CSSValueList(cloneFrom)
-{
-}
-
-String CSSMixFunctionValue::customCSSText() const
-{
- return "mix(" + CSSValueList::customCSSText() + ")";
-}
-
-PassRefPtr<CSSMixFunctionValue> CSSMixFunctionValue::cloneForCSSOM() const
-{
- return adoptRef(new CSSMixFunctionValue(*this));
-}
-
-bool CSSMixFunctionValue::equals(const CSSMixFunctionValue& other) const
-{
- return CSSValueList::equals(other);
-}
-
-} // namespace WebCore
-
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.h b/chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.h
deleted file mode 100644
index 04a5e2d6020..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSMixFunctionValue.h
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2012 Adobe Systems Incorporated. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER “AS IS” AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-#ifndef CSSMixFunctionValue_h
-#define CSSMixFunctionValue_h
-
-#include "core/css/CSSValueList.h"
-#include "wtf/PassRefPtr.h"
-
-namespace WebCore {
-
-class CSSMixFunctionValue : public CSSValueList {
-public:
- static PassRefPtr<CSSMixFunctionValue> create()
- {
- return adoptRef(new CSSMixFunctionValue());
- }
-
- String customCSSText() const;
-
- PassRefPtr<CSSMixFunctionValue> cloneForCSSOM() const;
-
- bool equals(const CSSMixFunctionValue&) const;
-
-private:
- CSSMixFunctionValue();
- CSSMixFunctionValue(const CSSMixFunctionValue& cloneFrom);
-};
-
-DEFINE_CSS_VALUE_TYPE_CASTS(CSSMixFunctionValue, isMixFunctionValue());
-
-} // namespace WebCore
-
-
-#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.cpp b/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.cpp
index 36545dd12bc..1e7882f2c1c 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.cpp
@@ -49,13 +49,6 @@ void serializeCharacterAsCodePoint(UChar32 c, StringBuilder& appendTo)
appendTo.append(' ');
}
-void serializeIdentifier(const String& identifier, String& appendTo)
-{
- StringBuilder addend;
- serializeIdentifier(identifier, addend);
- appendTo.append(addend.toString());
-}
-
void serializeIdentifier(const String& identifier, StringBuilder& appendTo)
{
bool isFirst = true;
@@ -85,13 +78,6 @@ void serializeIdentifier(const String& identifier, StringBuilder& appendTo)
}
}
-void serializeString(const String& string, String& appendTo)
-{
- StringBuilder addend;
- serializeString(string, addend);
- appendTo.append(addend.toString());
-}
-
void serializeString(const String& string, StringBuilder& appendTo)
{
appendTo.append('\"');
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.h b/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.h
index 3239ada94b4..813396b1e11 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSOMUtils.h
@@ -35,15 +35,15 @@
#include "wtf/unicode/Unicode.h"
// Utilities for CSSOM http://dev.w3.org/csswg/cssom/
+// FIXME: This file has a similar purpose to
+// CSSMarkup.h. Perhaps the two should be combined?
namespace WebCore {
// Common serializing methods. See: http://dev.w3.org/csswg/cssom/#common-serializing-idioms
void serializeCharacter(UChar32, StringBuilder& appendTo);
void serializeCharacterAsCodePoint(UChar32, StringBuilder& appendTo);
-void serializeIdentifier(const String& identifier, String& appendTo);
void serializeIdentifier(const String& identifier, StringBuilder& appendTo);
-void serializeString(const String&, String& appendTo);
void serializeString(const String&, StringBuilder& appendTo);
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPageRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSPageRule.cpp
index 0513e92dd99..20237e62c8b 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPageRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPageRule.cpp
@@ -22,7 +22,7 @@
#include "config.h"
#include "core/css/CSSPageRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSStyleSheet.h"
#include "core/css/PropertySetCSSStyleDeclaration.h"
@@ -40,8 +40,10 @@ CSSPageRule::CSSPageRule(StyleRulePage* pageRule, CSSStyleSheet* parent)
CSSPageRule::~CSSPageRule()
{
+#if !ENABLE(OILPAN)
if (m_propertiesCSSOMWrapper)
m_propertiesCSSOMWrapper->clearParentRule();
+#endif
}
CSSStyleDeclaration* CSSPageRule::style() const
@@ -68,7 +70,8 @@ String CSSPageRule::selectorText() const
void CSSPageRule::setSelectorText(const String& selectorText)
{
- CSSParser parser(parserContext());
+ CSSParserContext context(parserContext(), 0);
+ BisonCSSParser parser(context);
CSSSelectorList selectorList;
parser.parseSelector(selectorText, selectorList);
if (!selectorList.isValid())
@@ -84,7 +87,7 @@ String CSSPageRule::cssText() const
StringBuilder result;
result.append(selectorText());
result.appendLiteral(" { ");
- String decls = m_pageRule->properties()->asText();
+ String decls = m_pageRule->properties().asText();
result.append(decls);
if (!decls.isEmpty())
result.append(' ');
@@ -100,4 +103,11 @@ void CSSPageRule::reattach(StyleRuleBase* rule)
m_propertiesCSSOMWrapper->reattach(m_pageRule->mutableProperties());
}
+void CSSPageRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_pageRule);
+ visitor->trace(m_propertiesCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPageRule.h b/chromium/third_party/WebKit/Source/core/css/CSSPageRule.h
index 4aa0f696e63..4fc9b1be4ba 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPageRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPageRule.h
@@ -23,6 +23,7 @@
#define CSSPageRule_h
#include "core/css/CSSRule.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -31,9 +32,12 @@ class CSSStyleSheet;
class StyleRulePage;
class StyleRuleCSSStyleDeclaration;
-class CSSPageRule : public CSSRule {
+class CSSPageRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSPageRule> create(StyleRulePage* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSPageRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSPageRule> create(StyleRulePage* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSPageRule(rule, sheet));
+ }
virtual ~CSSPageRule();
@@ -46,11 +50,13 @@ public:
String selectorText() const;
void setSelectorText(const String&);
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSPageRule(StyleRulePage*, CSSStyleSheet*);
- RefPtr<StyleRulePage> m_pageRule;
- mutable RefPtr<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
+ RefPtrWillBeMember<StyleRulePage> m_pageRule;
+ mutable RefPtrWillBeMember<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSPageRule, PAGE_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParser.h b/chromium/third_party/WebKit/Source/core/css/CSSParser.h
deleted file mode 100755
index de263102892..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSParser.h
+++ /dev/null
@@ -1,676 +0,0 @@
-/*
- * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
- * Copyright (C) 2004, 2005, 2006, 2008, 2009, 2010 Apple Inc. All rights reserved.
- * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
- * Copyright (C) 2009 - 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#ifndef CSSParser_h
-#define CSSParser_h
-
-#include "CSSPropertyNames.h"
-#include "CSSValueKeywords.h"
-#include "core/css/CSSCalculationValue.h"
-#include "core/css/CSSFilterValue.h"
-#include "core/css/CSSGradientValue.h"
-#include "core/css/CSSParserMode.h"
-#include "core/css/CSSParserValues.h"
-#include "core/css/CSSProperty.h"
-#include "core/css/CSSPropertySourceData.h"
-#include "core/css/CSSSelector.h"
-#include "core/css/CSSTokenizer.h"
-#include "core/css/MediaQuery.h"
-#include "core/css/StylePropertySet.h"
-#include "core/frame/UseCounter.h"
-#include "platform/graphics/Color.h"
-#include "wtf/HashSet.h"
-#include "wtf/OwnPtr.h"
-#include "wtf/Vector.h"
-#include "wtf/text/AtomicString.h"
-#include "wtf/text/TextPosition.h"
-
-namespace WebCore {
-
-class AnimationParseContext;
-class CSSArrayFunctionValue;
-class CSSBorderImageSliceValue;
-class CSSMixFunctionValue;
-class CSSPrimitiveValue;
-class CSSSelectorList;
-class CSSShaderValue;
-class CSSValue;
-class CSSValueList;
-class CSSBasicShape;
-class Document;
-class Element;
-class ImmutableStylePropertySet;
-class MediaQueryExp;
-class MediaQuerySet;
-class MutableStylePropertySet;
-class StyleKeyframe;
-class StylePropertyShorthand;
-class StyleRuleBase;
-class StyleRuleKeyframes;
-class StyleKeyframe;
-class StyleSheetContents;
-
-// FIXME: This class is shared with CSSTokenizer so should we rename it to CSSSourceLocation?
-struct CSSParserLocation {
- unsigned offset;
- unsigned lineNumber;
- CSSParserString token;
-};
-
-class CSSParser {
- friend inline int cssyylex(void*, CSSParser*);
-
-public:
- class SourceDataHandler;
- enum ErrorType {
- NoError,
- PropertyDeclarationError,
- InvalidPropertyValueError,
- InvalidPropertyError,
- InvalidSelectorError,
- InvalidSupportsConditionError,
- InvalidRuleError,
- InvalidMediaQueryError,
- InvalidKeyframeSelectorError,
- InvalidSelectorPseudoError,
- UnterminatedCommentError,
- GeneralError
- };
-
- CSSParser(const CSSParserContext&, UseCounter* = 0);
-
- ~CSSParser();
-
- void parseSheet(StyleSheetContents*, const String&, const TextPosition& startPosition = TextPosition::minimumPosition(), SourceDataHandler* = 0, bool = false);
- PassRefPtr<StyleRuleBase> parseRule(StyleSheetContents*, const String&);
- PassRefPtr<StyleKeyframe> parseKeyframeRule(StyleSheetContents*, const String&);
- bool parseSupportsCondition(const String&);
- static bool parseValue(MutableStylePropertySet*, CSSPropertyID, const String&, bool important, CSSParserMode, StyleSheetContents*);
- static bool parseColor(RGBA32& color, const String&, bool strict = false);
- static bool parseSystemColor(RGBA32& color, const String&, Document*);
- static PassRefPtr<CSSValueList> parseFontFaceValue(const AtomicString&);
- PassRefPtr<CSSPrimitiveValue> parseValidPrimitive(CSSValueID ident, CSSParserValue*);
- bool parseDeclaration(MutableStylePropertySet*, const String&, SourceDataHandler*, StyleSheetContents* contextStyleSheet);
- static PassRefPtr<ImmutableStylePropertySet> parseInlineStyleDeclaration(const String&, Element*);
- PassRefPtr<MediaQuerySet> parseMediaQueryList(const String&);
- PassOwnPtr<Vector<double> > parseKeyframeKeyList(const String&);
-
- void addPropertyWithPrefixingVariant(CSSPropertyID, PassRefPtr<CSSValue>, bool important, bool implicit = false);
- void addProperty(CSSPropertyID, PassRefPtr<CSSValue>, bool important, bool implicit = false);
- void rollbackLastProperties(int num);
- bool hasProperties() const { return !m_parsedProperties.isEmpty(); }
- void addExpandedPropertyForValue(CSSPropertyID propId, PassRefPtr<CSSValue>, bool);
- void setCurrentProperty(CSSPropertyID);
-
- bool parseValue(CSSPropertyID, bool important);
- bool parseShorthand(CSSPropertyID, const StylePropertyShorthand&, bool important);
- bool parse4Values(CSSPropertyID, const CSSPropertyID* properties, bool important);
- bool parseContent(CSSPropertyID, bool important);
- bool parseQuotes(CSSPropertyID, bool important);
-
- static bool parseValue(MutableStylePropertySet*, CSSPropertyID, const String&, bool important, const Document&);
- void storeVariableDeclaration(const CSSParserString&, PassOwnPtr<CSSParserValueList>, bool important);
-
- PassRefPtr<CSSValue> parseAttr(CSSParserValueList* args);
-
- PassRefPtr<CSSValue> parseBackgroundColor();
-
- bool parseFillImage(CSSParserValueList*, RefPtr<CSSValue>&);
-
- enum FillPositionFlag { InvalidFillPosition = 0, AmbiguousFillPosition = 1, XFillPosition = 2, YFillPosition = 4 };
- enum FillPositionParsingMode { ResolveValuesAsPercent = 0, ResolveValuesAsKeyword = 1 };
- PassRefPtr<CSSPrimitiveValue> parseFillPositionComponent(CSSParserValueList*, unsigned& cumulativeFlags, FillPositionFlag& individualFlag, FillPositionParsingMode = ResolveValuesAsPercent);
- PassRefPtr<CSSValue> parseFillPositionX(CSSParserValueList*);
- PassRefPtr<CSSValue> parseFillPositionY(CSSParserValueList*);
- void parse2ValuesFillPosition(CSSParserValueList*, RefPtr<CSSValue>&, RefPtr<CSSValue>&);
- bool isPotentialPositionValue(CSSParserValue*);
- void parseFillPosition(CSSParserValueList*, RefPtr<CSSValue>&, RefPtr<CSSValue>&);
- void parse3ValuesFillPosition(CSSParserValueList*, RefPtr<CSSValue>&, RefPtr<CSSValue>&, PassRefPtr<CSSPrimitiveValue>, PassRefPtr<CSSPrimitiveValue>);
- void parse4ValuesFillPosition(CSSParserValueList*, RefPtr<CSSValue>&, RefPtr<CSSValue>&, PassRefPtr<CSSPrimitiveValue>, PassRefPtr<CSSPrimitiveValue>);
-
- void parseFillRepeat(RefPtr<CSSValue>&, RefPtr<CSSValue>&);
- PassRefPtr<CSSValue> parseFillSize(CSSPropertyID, bool &allowComma);
-
- bool parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, RefPtr<CSSValue>&, RefPtr<CSSValue>&);
- bool parseFillShorthand(CSSPropertyID, const CSSPropertyID* properties, int numProperties, bool important);
-
- void addFillValue(RefPtr<CSSValue>& lval, PassRefPtr<CSSValue> rval);
-
- void addAnimationValue(RefPtr<CSSValue>& lval, PassRefPtr<CSSValue> rval);
-
- PassRefPtr<CSSValue> parseAnimationDelay();
- PassRefPtr<CSSValue> parseAnimationDirection();
- PassRefPtr<CSSValue> parseAnimationDuration();
- PassRefPtr<CSSValue> parseAnimationFillMode();
- PassRefPtr<CSSValue> parseAnimationIterationCount();
- PassRefPtr<CSSValue> parseAnimationName();
- PassRefPtr<CSSValue> parseAnimationPlayState();
- PassRefPtr<CSSValue> parseAnimationProperty(AnimationParseContext&);
- PassRefPtr<CSSValue> parseAnimationTimingFunction();
-
- bool parseTransformOriginShorthand(RefPtr<CSSValue>&, RefPtr<CSSValue>&, RefPtr<CSSValue>&);
- bool parseCubicBezierTimingFunctionValue(CSSParserValueList*& args, double& result);
- bool parseAnimationProperty(CSSPropertyID, RefPtr<CSSValue>&, AnimationParseContext&);
- bool parseTransitionShorthand(CSSPropertyID, bool important);
- bool parseAnimationShorthand(CSSPropertyID, bool important);
-
- PassRefPtr<CSSValue> parseColumnWidth();
- PassRefPtr<CSSValue> parseColumnCount();
- bool parseColumnsShorthand(bool important);
-
- PassRefPtr<CSSValue> parseGridPosition();
- bool parseIntegerOrStringFromGridPosition(RefPtr<CSSPrimitiveValue>& numericValue, RefPtr<CSSPrimitiveValue>& gridLineName);
- bool parseGridItemPositionShorthand(CSSPropertyID, bool important);
- bool parseGridAreaShorthand(bool important);
- bool parseSingleGridAreaLonghand(RefPtr<CSSValue>&);
- bool parseGridTrackList(CSSPropertyID, bool important);
- bool parseGridTrackRepeatFunction(CSSValueList&);
- PassRefPtr<CSSValue> parseGridTrackSize(CSSParserValueList& inputList);
- PassRefPtr<CSSPrimitiveValue> parseGridBreadth(CSSParserValue*);
- PassRefPtr<CSSValue> parseGridTemplate();
- void parseGridLineNames(CSSParserValueList* inputList, CSSValueList&);
-
- bool parseClipShape(CSSPropertyID, bool important);
-
- bool parseBasicShape(CSSPropertyID, bool important);
- PassRefPtr<CSSBasicShape> parseBasicShapeRectangle(CSSParserValueList* args);
- PassRefPtr<CSSBasicShape> parseBasicShapeCircle(CSSParserValueList* args);
- PassRefPtr<CSSBasicShape> parseBasicShapeEllipse(CSSParserValueList* args);
- PassRefPtr<CSSBasicShape> parseBasicShapePolygon(CSSParserValueList* args);
- PassRefPtr<CSSBasicShape> parseBasicShapeInsetRectangle(CSSParserValueList* args);
-
- bool parseFont(bool important);
- PassRefPtr<CSSValueList> parseFontFamily();
-
- bool parseCounter(CSSPropertyID, int defaultValue, bool important);
- PassRefPtr<CSSValue> parseCounterContent(CSSParserValueList* args, bool counters);
-
- bool parseColorParameters(CSSParserValue*, int* colorValues, bool parseAlpha);
- bool parseHSLParameters(CSSParserValue*, double* colorValues, bool parseAlpha);
- PassRefPtr<CSSPrimitiveValue> parseColor(CSSParserValue* = 0);
- bool parseColorFromValue(CSSParserValue*, RGBA32&);
- void parseSelector(const String&, CSSSelectorList&);
-
- template<typename StringType>
- static bool fastParseColor(RGBA32&, const StringType&, bool strict);
-
- bool parseLineHeight(bool important);
- bool parseFontSize(bool important);
- bool parseFontVariant(bool important);
- bool parseFontWeight(bool important);
- bool parseFontFaceSrc();
- bool parseFontFaceUnicodeRange();
-
- bool parseSVGValue(CSSPropertyID propId, bool important);
- PassRefPtr<CSSValue> parseSVGPaint();
- PassRefPtr<CSSValue> parseSVGColor();
- PassRefPtr<CSSValue> parseSVGStrokeDasharray();
-
- PassRefPtr<CSSValue> parsePaintOrder() const;
-
- // CSS3 Parsing Routines (for properties specific to CSS3)
- PassRefPtr<CSSValueList> parseShadow(CSSParserValueList*, CSSPropertyID);
- bool parseBorderImageShorthand(CSSPropertyID, bool important);
- PassRefPtr<CSSValue> parseBorderImage(CSSPropertyID);
- bool parseBorderImageRepeat(RefPtr<CSSValue>&);
- bool parseBorderImageSlice(CSSPropertyID, RefPtr<CSSBorderImageSliceValue>&);
- bool parseBorderImageWidth(RefPtr<CSSPrimitiveValue>&);
- bool parseBorderImageOutset(RefPtr<CSSPrimitiveValue>&);
- bool parseBorderRadius(CSSPropertyID, bool important);
-
- bool parseAspectRatio(bool important);
-
- bool parseReflect(CSSPropertyID, bool important);
-
- bool parseFlex(CSSParserValueList* args, bool important);
-
- bool parseObjectPosition(bool important);
-
- // Image generators
- bool parseCanvas(CSSParserValueList*, RefPtr<CSSValue>&);
-
- bool parseDeprecatedGradient(CSSParserValueList*, RefPtr<CSSValue>&);
- bool parseDeprecatedLinearGradient(CSSParserValueList*, RefPtr<CSSValue>&, CSSGradientRepeat repeating);
- bool parseDeprecatedRadialGradient(CSSParserValueList*, RefPtr<CSSValue>&, CSSGradientRepeat repeating);
- bool parseLinearGradient(CSSParserValueList*, RefPtr<CSSValue>&, CSSGradientRepeat repeating);
- bool parseRadialGradient(CSSParserValueList*, RefPtr<CSSValue>&, CSSGradientRepeat repeating);
- bool parseGradientColorStops(CSSParserValueList*, CSSGradientValue*, bool expectComma);
-
- bool parseCrossfade(CSSParserValueList*, RefPtr<CSSValue>&);
-
- PassRefPtr<CSSValue> parseImageSet(CSSParserValueList*);
-
- PassRefPtr<CSSValueList> parseFilter();
- PassRefPtr<CSSFilterValue> parseBuiltinFilterArguments(CSSParserValueList*, CSSFilterValue::FilterOperationType);
- PassRefPtr<CSSMixFunctionValue> parseMixFunction(CSSParserValue*);
- PassRefPtr<CSSArrayFunctionValue> parseCustomFilterArrayFunction(CSSParserValue*);
- PassRefPtr<CSSValueList> parseCustomFilterTransform(CSSParserValueList*);
- PassRefPtr<CSSValueList> parseCustomFilterParameters(CSSParserValueList*);
- PassRefPtr<CSSFilterValue> parseCustomFilterFunctionWithAtRuleReferenceSyntax(CSSParserValue*);
- PassRefPtr<CSSFilterValue> parseCustomFilterFunctionWithInlineSyntax(CSSParserValue*);
- PassRefPtr<CSSFilterValue> parseCustomFilterFunction(CSSParserValue*);
- bool parseFilterRuleSrc();
- PassRefPtr<CSSShaderValue> parseFilterRuleSrcUriAndFormat(CSSParserValueList*);
-
- static bool isBlendMode(CSSValueID);
- static bool isCompositeOperator(CSSValueID);
-
- PassRefPtr<CSSValueList> parseTransform();
- PassRefPtr<CSSValue> parseTransformValue(CSSParserValue*);
- bool parseTransformOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, CSSPropertyID& propId3, RefPtr<CSSValue>&, RefPtr<CSSValue>&, RefPtr<CSSValue>&);
- bool parsePerspectiveOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, RefPtr<CSSValue>&, RefPtr<CSSValue>&);
-
- bool parseTextEmphasisStyle(bool important);
-
- bool parseTouchAction(bool important);
-
- void addTextDecorationProperty(CSSPropertyID, PassRefPtr<CSSValue>, bool important);
- bool parseTextDecoration(CSSPropertyID propId, bool important);
- bool parseTextUnderlinePosition(bool important);
-
- PassRefPtr<CSSValue> parseTextIndent();
-
- bool parseLineBoxContain(bool important);
- bool parseCalculation(CSSParserValue*, ValueRange);
-
- bool parseFontFeatureTag(CSSValueList*);
- bool parseFontFeatureSettings(bool important);
-
- bool parseFlowThread(const String& flowName);
- bool parseFlowThread(CSSPropertyID, bool important);
- bool parseRegionThread(CSSPropertyID, bool important);
-
- bool parseFontVariantLigatures(bool important);
-
- bool parseGeneratedImage(CSSParserValueList*, RefPtr<CSSValue>&);
-
- CSSParserSelector* createFloatingSelector();
- CSSParserSelector* createFloatingSelectorWithTagName(const QualifiedName&);
- PassOwnPtr<CSSParserSelector> sinkFloatingSelector(CSSParserSelector*);
-
- Vector<OwnPtr<CSSParserSelector> >* createFloatingSelectorVector();
- PassOwnPtr<Vector<OwnPtr<CSSParserSelector> > > sinkFloatingSelectorVector(Vector<OwnPtr<CSSParserSelector> >*);
-
- CSSParserValueList* createFloatingValueList();
- PassOwnPtr<CSSParserValueList> sinkFloatingValueList(CSSParserValueList*);
-
- CSSParserFunction* createFloatingFunction();
- CSSParserFunction* createFloatingFunction(const CSSParserString& name, PassOwnPtr<CSSParserValueList> args);
- PassOwnPtr<CSSParserFunction> sinkFloatingFunction(CSSParserFunction*);
-
- CSSParserValue& sinkFloatingValue(CSSParserValue&);
-
- MediaQuerySet* createMediaQuerySet();
- StyleRuleBase* createImportRule(const CSSParserString&, MediaQuerySet*);
- StyleKeyframe* createKeyframe(CSSParserValueList*);
- StyleRuleKeyframes* createKeyframesRule(const String&, PassOwnPtr<Vector<RefPtr<StyleKeyframe> > >, bool isPrefixed);
-
- typedef Vector<RefPtr<StyleRuleBase> > RuleList;
- StyleRuleBase* createMediaRule(MediaQuerySet*, RuleList*);
- RuleList* createRuleList();
- RuleList* appendRule(RuleList*, StyleRuleBase*);
- StyleRuleBase* createStyleRule(Vector<OwnPtr<CSSParserSelector> >* selectors);
- StyleRuleBase* createFontFaceRule();
- StyleRuleBase* createPageRule(PassOwnPtr<CSSParserSelector> pageSelector);
- StyleRuleBase* createRegionRule(Vector<OwnPtr<CSSParserSelector> >* regionSelector, RuleList* rules);
- StyleRuleBase* createMarginAtRule(CSSSelector::MarginBoxType);
- StyleRuleBase* createSupportsRule(bool conditionIsSupported, RuleList*);
- void markSupportsRuleHeaderStart();
- void markSupportsRuleHeaderEnd();
- PassRefPtr<CSSRuleSourceData> popSupportsRuleData();
- StyleRuleBase* createHostRule(RuleList* rules);
- StyleRuleBase* createFilterRule(const CSSParserString&);
-
- void startDeclarationsForMarginBox();
- void endDeclarationsForMarginBox();
-
- MediaQueryExp* createFloatingMediaQueryExp(const AtomicString&, CSSParserValueList*);
- PassOwnPtr<MediaQueryExp> sinkFloatingMediaQueryExp(MediaQueryExp*);
- Vector<OwnPtr<MediaQueryExp> >* createFloatingMediaQueryExpList();
- PassOwnPtr<Vector<OwnPtr<MediaQueryExp> > > sinkFloatingMediaQueryExpList(Vector<OwnPtr<MediaQueryExp> >*);
- MediaQuery* createFloatingMediaQuery(MediaQuery::Restrictor, const AtomicString&, PassOwnPtr<Vector<OwnPtr<MediaQueryExp> > >);
- MediaQuery* createFloatingMediaQuery(PassOwnPtr<Vector<OwnPtr<MediaQueryExp> > >);
- MediaQuery* createFloatingNotAllQuery();
- PassOwnPtr<MediaQuery> sinkFloatingMediaQuery(MediaQuery*);
-
- Vector<RefPtr<StyleKeyframe> >* createFloatingKeyframeVector();
- PassOwnPtr<Vector<RefPtr<StyleKeyframe> > > sinkFloatingKeyframeVector(Vector<RefPtr<StyleKeyframe> >*);
-
- void addNamespace(const AtomicString& prefix, const AtomicString& uri);
- QualifiedName determineNameInNamespace(const AtomicString& prefix, const AtomicString& localName);
-
- CSSParserSelector* rewriteSpecifiersWithElementName(const AtomicString& namespacePrefix, const AtomicString& elementName, CSSParserSelector*, bool isNamespacePlaceholder = false);
- CSSParserSelector* rewriteSpecifiersWithElementNameForCustomPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule);
- CSSParserSelector* rewriteSpecifiersWithElementNameForContentPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule);
- CSSParserSelector* rewriteSpecifiersWithNamespaceIfNeeded(CSSParserSelector*);
- CSSParserSelector* rewriteSpecifiers(CSSParserSelector*, CSSParserSelector*);
- CSSParserSelector* rewriteSpecifiersForShadowDistributed(CSSParserSelector* specifiers, CSSParserSelector* distributedPseudoElementSelector);
-
- void invalidBlockHit();
-
- Vector<OwnPtr<CSSParserSelector> >* reusableSelectorVector() { return &m_reusableSelectorVector; }
-
- void setReusableRegionSelectorVector(Vector<OwnPtr<CSSParserSelector> >* selectors);
- Vector<OwnPtr<CSSParserSelector> >* reusableRegionSelectorVector() { return &m_reusableRegionSelectorVector; }
-
- void clearProperties();
-
- PassRefPtr<ImmutableStylePropertySet> createStylePropertySet();
-
- CSSParserContext m_context;
-
- bool m_important;
- CSSPropertyID m_id;
- StyleSheetContents* m_styleSheet;
- RefPtr<StyleRuleBase> m_rule;
- RefPtr<StyleKeyframe> m_keyframe;
- RefPtr<MediaQuerySet> m_mediaList;
- OwnPtr<CSSParserValueList> m_valueList;
- bool m_supportsCondition;
-
- typedef Vector<CSSProperty, 256> ParsedPropertyVector;
- ParsedPropertyVector m_parsedProperties;
- CSSSelectorList* m_selectorListForParseSelector;
-
- unsigned m_numParsedPropertiesBeforeMarginBox;
-
- int m_inParseShorthand;
- CSSPropertyID m_currentShorthand;
- bool m_implicitShorthand;
-
- bool m_hasFontFaceOnlyValues;
- bool m_hadSyntacticallyValidCSSRule;
- bool m_logErrors;
- bool m_ignoreErrors;
-
- bool m_inFilterRule;
-
- AtomicString m_defaultNamespace;
-
- // tokenizer methods and data
- SourceDataHandler* m_sourceDataHandler;
-
- void startRule();
- void endRule(bool valid);
- void startRuleHeader(CSSRuleSourceData::Type);
- void endRuleHeader();
- void startSelector();
- void endSelector();
- void startRuleBody();
- void startProperty();
- void endProperty(bool isImportantFound, bool isPropertyParsed, ErrorType = NoError);
- void startEndUnknownRule();
-
- void endInvalidRuleHeader();
- void reportError(const CSSParserLocation&, ErrorType = GeneralError);
- void resumeErrorLogging() { m_ignoreErrors = false; }
- void setLocationLabel(const CSSParserLocation& location) { m_locationLabel = location; }
- const CSSParserLocation& lastLocationLabel() const { return m_locationLabel; }
-
- void tokenToLowerCase(const CSSParserString& token);
-
- void markViewportRuleBodyStart() { m_inViewport = true; }
- void markViewportRuleBodyEnd() { m_inViewport = false; }
- StyleRuleBase* createViewportRule();
-
- PassRefPtr<CSSPrimitiveValue> createPrimitiveNumericValue(CSSParserValue*);
- PassRefPtr<CSSPrimitiveValue> createPrimitiveStringValue(CSSParserValue*);
- PassRefPtr<CSSPrimitiveValue> createPrimitiveVariableNameValue(CSSParserValue*);
-
- static KURL completeURL(const CSSParserContext&, const String& url);
-
- CSSParserLocation currentLocation() { return m_tokenizer.currentLocation(); }
-
-private:
- enum PropertyType {
- PropertyExplicit,
- PropertyImplicit
- };
-
- class ImplicitScope {
- WTF_MAKE_NONCOPYABLE(ImplicitScope);
- public:
- ImplicitScope(WebCore::CSSParser* parser, PropertyType propertyType)
- : m_parser(parser)
- {
- m_parser->m_implicitShorthand = propertyType == CSSParser::PropertyImplicit;
- }
-
- ~ImplicitScope()
- {
- m_parser->m_implicitShorthand = false;
- }
-
- private:
- WebCore::CSSParser* m_parser;
- };
-
- class StyleDeclarationScope {
- WTF_MAKE_NONCOPYABLE(StyleDeclarationScope);
- public:
- StyleDeclarationScope(CSSParser* parser, const StylePropertySet* declaration)
- : m_parser(parser)
- , m_mode(declaration->cssParserMode())
- {
- if (isCSSViewportParsingEnabledForMode(m_mode)) {
- ASSERT(!m_parser->inViewport());
- m_parser->markViewportRuleBodyStart();
- }
- }
-
- ~StyleDeclarationScope()
- {
- if (isCSSViewportParsingEnabledForMode(m_mode))
- m_parser->markViewportRuleBodyEnd();
- }
-
- private:
- CSSParser* m_parser;
- CSSParserMode m_mode;
- };
-
- inline void ensureLineEndings();
-
- void setStyleSheet(StyleSheetContents* styleSheet) { m_styleSheet = styleSheet; }
-
- bool inQuirksMode() const { return isQuirksModeBehavior(m_context.mode()); }
- bool inViewport() const { return m_inViewport; }
-
- KURL completeURL(const String& url) const;
-
- void recheckAtKeyword(const UChar* str, int len);
-
- template<unsigned prefixLength, unsigned suffixLength>
- inline void setupParser(const char (&prefix)[prefixLength], const String& string, const char (&suffix)[suffixLength])
- {
- setupParser(prefix, prefixLength - 1, string, suffix, suffixLength - 1);
- }
- void setupParser(const char* prefix, unsigned prefixLength, const String&, const char* suffix, unsigned suffixLength);
- bool inShorthand() const { return m_inParseShorthand; }
-
- bool validWidthOrHeight(CSSParserValue*);
-
- void deleteFontFaceOnlyValues();
-
- bool parseValue(MutableStylePropertySet*, CSSPropertyID, const String&, bool important, StyleSheetContents* contextStyleSheet);
- PassRefPtr<ImmutableStylePropertySet> parseDeclaration(const String&, StyleSheetContents* contextStyleSheet);
-
- enum SizeParameterType {
- None,
- Auto,
- Length,
- PageSize,
- Orientation,
- };
-
- bool parsePage(CSSPropertyID propId, bool important);
- bool parseSize(CSSPropertyID propId, bool important);
- SizeParameterType parseSizeParameter(CSSValueList* parsedValues, CSSParserValue* value, SizeParameterType prevParamType);
-
- bool parseFontFaceSrcURI(CSSValueList*);
- bool parseFontFaceSrcLocal(CSSValueList*);
-
- bool parseColor(const String&);
-
- const String* m_source;
- TextPosition m_startPosition;
- CSSRuleSourceData::Type m_ruleHeaderType;
- unsigned m_ruleHeaderStartOffset;
- int m_ruleHeaderStartLineNumber;
- OwnPtr<Vector<unsigned> > m_lineEndings;
-
- bool m_ruleHasHeader;
-
- bool m_allowImportRules;
- bool m_allowNamespaceDeclarations;
-
- bool parseViewportProperty(CSSPropertyID propId, bool important);
- bool parseViewportShorthand(CSSPropertyID propId, CSSPropertyID first, CSSPropertyID second, bool important);
-
- bool m_inViewport;
-
- CSSParserLocation m_locationLabel;
-
- bool useLegacyBackgroundSizeShorthandBehavior() const;
-
- Vector<RefPtr<StyleRuleBase> > m_parsedRules;
- Vector<RefPtr<StyleKeyframe> > m_parsedKeyframes;
- Vector<RefPtr<MediaQuerySet> > m_parsedMediaQuerySets;
- Vector<OwnPtr<RuleList> > m_parsedRuleLists;
- Vector<CSSParserSelector*> m_floatingSelectors;
- Vector<Vector<OwnPtr<CSSParserSelector> >*> m_floatingSelectorVectors;
- Vector<CSSParserValueList*> m_floatingValueLists;
- Vector<CSSParserFunction*> m_floatingFunctions;
-
- OwnPtr<MediaQuery> m_floatingMediaQuery;
- OwnPtr<MediaQueryExp> m_floatingMediaQueryExp;
- OwnPtr<Vector<OwnPtr<MediaQueryExp> > > m_floatingMediaQueryExpList;
-
- OwnPtr<Vector<RefPtr<StyleKeyframe> > > m_floatingKeyframeVector;
-
- Vector<OwnPtr<CSSParserSelector> > m_reusableSelectorVector;
- Vector<OwnPtr<CSSParserSelector> > m_reusableRegionSelectorVector;
-
- RefPtr<CSSCalcValue> m_parsedCalculation;
-
- OwnPtr<RuleSourceDataList> m_supportsRuleDataStack;
-
- // defines units allowed for a certain property, used in parseUnit
- enum Units {
- FUnknown = 0x0000,
- FInteger = 0x0001,
- FNumber = 0x0002, // Real Numbers
- FPercent = 0x0004,
- FLength = 0x0008,
- FAngle = 0x0010,
- FTime = 0x0020,
- FFrequency = 0x0040,
- FPositiveInteger = 0x0080,
- FRelative = 0x0100,
- FResolution = 0x0200,
- FNonNeg = 0x0400
- };
-
- friend inline Units operator|(Units a, Units b)
- {
- return static_cast<Units>(static_cast<unsigned>(a) | static_cast<unsigned>(b));
- }
-
- enum ReleaseParsedCalcValueCondition {
- ReleaseParsedCalcValue,
- DoNotReleaseParsedCalcValue
- };
-
- bool isLoggingErrors();
- void logError(const String& message, const CSSParserLocation&);
-
- bool validCalculationUnit(CSSParserValue*, Units, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue);
-
- bool shouldAcceptUnitLessValues(CSSParserValue*, Units, CSSParserMode);
-
- inline bool validUnit(CSSParserValue* value, Units unitflags, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue) { return validUnit(value, unitflags, m_context.mode(), releaseCalc); }
- bool validUnit(CSSParserValue*, Units, CSSParserMode, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue);
-
- bool parseBorderImageQuad(Units, RefPtr<CSSPrimitiveValue>&);
- int colorIntFromValue(CSSParserValue*);
- double parsedDouble(CSSParserValue*, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue);
- bool isCalculation(CSSParserValue*);
-
- UseCounter* m_useCounter;
-
- CSSTokenizer m_tokenizer;
-
- friend class TransformOperationInfo;
- friend class FilterOperationInfo;
-};
-
-CSSPropertyID cssPropertyID(const CSSParserString&);
-CSSPropertyID cssPropertyID(const String&);
-CSSValueID cssValueKeywordID(const CSSParserString&);
-
-class ShorthandScope {
- WTF_MAKE_FAST_ALLOCATED;
-public:
- ShorthandScope(CSSParser* parser, CSSPropertyID propId) : m_parser(parser)
- {
- if (!(m_parser->m_inParseShorthand++))
- m_parser->m_currentShorthand = propId;
- }
- ~ShorthandScope()
- {
- if (!(--m_parser->m_inParseShorthand))
- m_parser->m_currentShorthand = CSSPropertyInvalid;
- }
-
-private:
- CSSParser* m_parser;
-};
-
-class CSSParser::SourceDataHandler {
-public:
- virtual void startRuleHeader(CSSRuleSourceData::Type, unsigned offset) = 0;
- virtual void endRuleHeader(unsigned offset) = 0;
- virtual void startSelector(unsigned offset) = 0;
- virtual void endSelector(unsigned offset) = 0;
- virtual void startRuleBody(unsigned offset) = 0;
- virtual void endRuleBody(unsigned offset, bool error) = 0;
- virtual void startEndUnknownRule() = 0;
- virtual void startProperty(unsigned offset) = 0;
- virtual void endProperty(bool isImportant, bool isParsed, unsigned offset, CSSParser::ErrorType) = 0;
- virtual void startComment(unsigned offset) = 0;
- virtual void endComment(unsigned offset) = 0;
-};
-
-String quoteCSSString(const String&);
-String quoteCSSStringIfNeeded(const String&);
-String quoteCSSURLIfNeeded(const String&);
-
-bool isValidNthToken(const CSSParserString&);
-
-inline int cssyylex(void* yylval, CSSParser* parser)
-{
- return parser->m_tokenizer.lex(yylval);
-}
-
-} // namespace WebCore
-
-#endif // CSSParser_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParserMode.cpp b/chromium/third_party/WebKit/Source/core/css/CSSParserMode.cpp
index b4d94f8a135..d403eb81fee 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSParserMode.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSParserMode.cpp
@@ -32,19 +32,33 @@
namespace WebCore {
-CSSParserContext::CSSParserContext(CSSParserMode mode)
+CSSParserContext::CSSParserContext(CSSParserMode mode, UseCounter* useCounter)
: m_mode(mode)
, m_isHTMLDocument(false)
, m_useLegacyBackgroundSizeShorthandBehavior(false)
+ , m_useCounter(useCounter)
{
}
-CSSParserContext::CSSParserContext(const Document& document, const KURL& baseURL, const String& charset)
+CSSParserContext::CSSParserContext(const Document& document, UseCounter* useCounter, const KURL& baseURL, const String& charset)
: m_baseURL(baseURL.isNull() ? document.baseURL() : baseURL)
, m_charset(charset)
, m_mode(document.inQuirksMode() ? HTMLQuirksMode : HTMLStandardMode)
+ , m_referrer(m_baseURL.strippedForUseAsReferrer(), document.referrerPolicy())
, m_isHTMLDocument(document.isHTMLDocument())
, m_useLegacyBackgroundSizeShorthandBehavior(document.settings() ? document.settings()->useLegacyBackgroundSizeShorthandBehavior() : false)
+ , m_useCounter(useCounter)
+{
+}
+
+CSSParserContext::CSSParserContext(const CSSParserContext& other, UseCounter* useCounter)
+ : m_baseURL(other.m_baseURL)
+ , m_charset(other.m_charset)
+ , m_mode(other.m_mode)
+ , m_referrer(other.m_referrer)
+ , m_isHTMLDocument(other.m_isHTMLDocument)
+ , m_useLegacyBackgroundSizeShorthandBehavior(other.m_useLegacyBackgroundSizeShorthandBehavior)
+ , m_useCounter(useCounter)
{
}
@@ -59,8 +73,17 @@ bool CSSParserContext::operator==(const CSSParserContext& other) const
const CSSParserContext& strictCSSParserContext()
{
- DEFINE_STATIC_LOCAL(CSSParserContext, strictContext, (HTMLStandardMode));
+ DEFINE_STATIC_LOCAL(CSSParserContext, strictContext, (HTMLStandardMode, 0));
return strictContext;
}
+KURL CSSParserContext::completeURL(const String& url) const
+{
+ if (url.isNull())
+ return KURL();
+ if (charset().isEmpty())
+ return KURL(baseURL(), url);
+ return KURL(baseURL(), url, charset());
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParserMode.h b/chromium/third_party/WebKit/Source/core/css/CSSParserMode.h
index efcac21a195..b379a68c77f 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSParserMode.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSParserMode.h
@@ -32,12 +32,13 @@
#define CSSParserMode_h
#include "platform/weborigin/KURL.h"
+#include "platform/weborigin/Referrer.h"
namespace WebCore {
class Document;
-// Must not grow beyond 3 bytes, due to packing in StylePropertySet.
+// Must not grow beyond 3 bits, due to packing in StylePropertySet.
enum CSSParserMode {
HTMLStandardMode,
HTMLQuirksMode,
@@ -88,11 +89,18 @@ inline bool isUseCounterEnabledForMode(CSSParserMode mode)
return mode != UASheetMode;
}
+class UseCounter;
+
class CSSParserContext {
WTF_MAKE_FAST_ALLOCATED;
public:
- CSSParserContext(CSSParserMode);
- CSSParserContext(const Document&, const KURL& baseURL = KURL(), const String& charset = emptyString());
+ CSSParserContext(CSSParserMode, UseCounter*);
+ // FIXME: We shouldn't need the UseCounter argument as we could infer it from the Document
+ // but some callers want to disable use counting (e.g. the WebInspector).
+ CSSParserContext(const Document&, UseCounter*, const KURL& baseURL = KURL(), const String& charset = emptyString());
+ // FIXME: This constructor shouldn't exist if we properly piped the UseCounter through the CSS
+ // subsystem. Currently the UseCounter life time is too crazy and we need a way to override it.
+ CSSParserContext(const CSSParserContext&, UseCounter*);
bool operator==(const CSSParserContext&) const;
bool operator!=(const CSSParserContext& other) const { return !(*this == other); }
@@ -100,6 +108,7 @@ public:
CSSParserMode mode() const { return m_mode; }
const KURL& baseURL() const { return m_baseURL; }
const String& charset() const { return m_charset; }
+ const Referrer& referrer() const { return m_referrer; }
bool isHTMLDocument() const { return m_isHTMLDocument; }
// This quirk is to maintain compatibility with Android apps built on
@@ -112,13 +121,21 @@ public:
void setMode(CSSParserMode mode) { m_mode = mode; }
void setBaseURL(const KURL& baseURL) { m_baseURL = baseURL; }
void setCharset(const String& charset) { m_charset = charset; }
+ void setReferrer(const Referrer& referrer) { m_referrer = referrer; }
+
+ KURL completeURL(const String& url) const;
+
+ UseCounter* useCounter() const { return m_useCounter; }
private:
KURL m_baseURL;
String m_charset;
CSSParserMode m_mode;
+ Referrer m_referrer;
bool m_isHTMLDocument;
bool m_useLegacyBackgroundSizeShorthandBehavior;
+
+ UseCounter* m_useCounter;
};
const CSSParserContext& strictCSSParserContext();
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParserValues.cpp b/chromium/third_party/WebKit/Source/core/css/CSSParserValues.cpp
index 10a940a6588..62196a77252 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSParserValues.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSParserValues.cpp
@@ -29,35 +29,26 @@ namespace WebCore {
using namespace WTF;
-AtomicString CSSParserString::atomicSubstring(unsigned position, unsigned length) const
+static void destroy(Vector<CSSParserValue, 4>& values)
{
- ASSERT(m_length >= position + length);
-
- if (is8Bit())
- return AtomicString(characters8() + position, length);
- return AtomicString(characters16() + position, length);
+ size_t numValues = values.size();
+ for (size_t i = 0; i < numValues; i++) {
+ if (values[i].unit == CSSParserValue::Function)
+ delete values[i].function;
+ else if (values[i].unit == CSSParserValue::ValueList)
+ delete values[i].valueList;
+ }
}
-void CSSParserString::trimTrailingWhitespace()
+void CSSParserValueList::destroyAndClear()
{
- if (is8Bit()) {
- while (m_length > 0 && isHTMLSpace<LChar>(m_data.characters8[m_length - 1]))
- --m_length;
- } else {
- while (m_length > 0 && isHTMLSpace<UChar>(m_data.characters16[m_length - 1]))
- --m_length;
- }
+ destroy(m_values);
+ clearAndLeakValues();
}
CSSParserValueList::~CSSParserValueList()
{
- size_t numValues = m_values.size();
- for (size_t i = 0; i < numValues; i++) {
- if (m_values[i].unit == CSSParserValue::Function)
- delete m_values[i].function;
- else if (m_values[i].unit == CSSParserValue::ValueList)
- delete m_values[i].valueList;
- }
+ destroy(m_values);
}
void CSSParserValueList::addValue(const CSSParserValue& v)
@@ -70,28 +61,20 @@ void CSSParserValueList::insertValueAt(unsigned i, const CSSParserValue& v)
m_values.insert(i, v);
}
-void CSSParserValueList::deleteValueAt(unsigned i)
+void CSSParserValueList::stealValues(CSSParserValueList& valueList)
{
- m_values.remove(i);
-}
-
-void CSSParserValueList::extend(CSSParserValueList& valueList)
-{
- for (unsigned int i = 0; i < valueList.size(); ++i)
+ for (unsigned i = 0; i < valueList.size(); ++i)
m_values.append(*(valueList.valueAt(i)));
+ valueList.clearAndLeakValues();
}
-PassRefPtr<CSSValue> CSSParserValue::createCSSValue()
+PassRefPtrWillBeRawPtr<CSSValue> CSSParserValue::createCSSValue()
{
- RefPtr<CSSValue> parsedValue;
if (id)
return CSSPrimitiveValue::createIdentifier(id);
- if (unit == CSSParserValue::Operator) {
- RefPtr<CSSPrimitiveValue> primitiveValue = CSSPrimitiveValue::createParserOperator(iValue);
- primitiveValue->setPrimitiveType(CSSPrimitiveValue::CSS_PARSER_OPERATOR);
- return primitiveValue;
- }
+ if (unit == CSSParserValue::Operator)
+ return CSSPrimitiveValue::createParserOperator(iValue);
if (unit == CSSParserValue::Function)
return CSSFunctionValue::create(function);
if (unit == CSSParserValue::ValueList)
@@ -99,7 +82,7 @@ PassRefPtr<CSSValue> CSSParserValue::createCSSValue()
if (unit >= CSSParserValue::Q_EMS)
return CSSPrimitiveValue::createAllowingMarginQuirk(fValue, CSSPrimitiveValue::CSS_EMS);
- CSSPrimitiveValue::UnitTypes primitiveUnit = static_cast<CSSPrimitiveValue::UnitTypes>(unit);
+ CSSPrimitiveValue::UnitType primitiveUnit = static_cast<CSSPrimitiveValue::UnitType>(unit);
switch (primitiveUnit) {
case CSSPrimitiveValue::CSS_IDENT:
case CSSPrimitiveValue::CSS_PROPERTY_ID:
@@ -109,7 +92,6 @@ PassRefPtr<CSSValue> CSSParserValue::createCSSValue()
return CSSPrimitiveValue::create(fValue, isInt ? CSSPrimitiveValue::CSS_PARSER_INTEGER : CSSPrimitiveValue::CSS_NUMBER);
case CSSPrimitiveValue::CSS_STRING:
case CSSPrimitiveValue::CSS_URI:
- case CSSPrimitiveValue::CSS_VARIABLE_NAME:
case CSSPrimitiveValue::CSS_PARSER_HEXCOLOR:
return CSSPrimitiveValue::create(string, primitiveUnit);
case CSSPrimitiveValue::CSS_PERCENTAGE:
@@ -148,31 +130,29 @@ PassRefPtr<CSSValue> CSSParserValue::createCSSValue()
case CSSPrimitiveValue::CSS_DPCM:
case CSSPrimitiveValue::CSS_PAIR:
case CSSPrimitiveValue::CSS_UNICODE_RANGE:
- case CSSPrimitiveValue::CSS_PARSER_OPERATOR:
case CSSPrimitiveValue::CSS_PARSER_INTEGER:
case CSSPrimitiveValue::CSS_PARSER_IDENTIFIER:
+ case CSSPrimitiveValue::CSS_PARSER_OPERATOR:
case CSSPrimitiveValue::CSS_COUNTER_NAME:
case CSSPrimitiveValue::CSS_SHAPE:
case CSSPrimitiveValue::CSS_QUAD:
case CSSPrimitiveValue::CSS_CALC:
case CSSPrimitiveValue::CSS_CALC_PERCENTAGE_WITH_NUMBER:
case CSSPrimitiveValue::CSS_CALC_PERCENTAGE_WITH_LENGTH:
- return 0;
+ return nullptr;
}
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
CSSParserSelector::CSSParserSelector()
: m_selector(adoptPtr(new CSSSelector()))
- , m_functionArgumentSelector(0)
{
}
CSSParserSelector::CSSParserSelector(const QualifiedName& tagQName)
: m_selector(adoptPtr(new CSSSelector(tagQName)))
- , m_functionArgumentSelector(0)
{
}
@@ -206,7 +186,7 @@ bool CSSParserSelector::isSimple() const
if (!m_tagHistory)
return true;
- if (m_selector->m_match == CSSSelector::Tag) {
+ if (m_selector->match() == CSSSelector::Tag) {
// We can't check against anyQName() here because namespace may not be nullAtom.
// Example:
// @namespace "http://www.w3.org/2000/svg";
@@ -244,17 +224,17 @@ void CSSParserSelector::prependTagSelector(const QualifiedName& tagQName, bool t
m_tagHistory = second.release();
m_selector = adoptPtr(new CSSSelector(tagQName, tagIsForNamespaceRule));
- m_selector->m_relation = CSSSelector::SubSelector;
+ m_selector->setRelation(CSSSelector::SubSelector);
}
-CSSParserSelector* CSSParserSelector::findDistributedPseudoElementSelector() const
+bool CSSParserSelector::hasHostPseudoSelector() const
{
CSSParserSelector* selector = const_cast<CSSParserSelector*>(this);
do {
- if (selector->isDistributedPseudoElement())
- return selector;
+ if (selector->pseudoType() == CSSSelector::PseudoHost || selector->pseudoType() == CSSSelector::PseudoHostContext)
+ return true;
} while ((selector = selector->tagHistory()));
- return 0;
+ return false;
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParserValues.h b/chromium/third_party/WebKit/Source/core/css/CSSParserValues.h
index 8efd3250dcf..7ab5836b858 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSParserValues.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSParserValues.h
@@ -21,7 +21,7 @@
#ifndef CSSParserValues_h
#define CSSParserValues_h
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSValueList.h"
@@ -77,8 +77,6 @@ struct CSSParserString {
m_is8Bit = true;
}
- void trimTrailingWhitespace();
-
bool is8Bit() const { return m_is8Bit; }
const LChar* characters8() const { ASSERT(is8Bit()); return m_data.characters8; }
const UChar* characters16() const { ASSERT(!is8Bit()); return m_data.characters16; }
@@ -98,9 +96,11 @@ struct CSSParserString {
bool equalIgnoringCase(const char* str) const
{
- if (is8Bit())
- return WTF::equalIgnoringCase(str, characters8(), length());
- return WTF::equalIgnoringCase(str, characters16(), length());
+ bool match = is8Bit() ? WTF::equalIgnoringCase(str, characters8(), length()) : WTF::equalIgnoringCase(str, characters16(), length());
+ if (!match)
+ return false;
+ ASSERT(strlen(str) >= length());
+ return str[length()] == '\0';
}
template <size_t strLength>
@@ -119,8 +119,6 @@ struct CSSParserString {
operator String() const { return is8Bit() ? String(m_data.characters8, m_length) : StringImpl::create8BitIfPossible(m_data.characters16, m_length); }
operator AtomicString() const { return is8Bit() ? AtomicString(m_data.characters8, m_length) : AtomicString(m_data.characters16, m_length); }
- AtomicString atomicSubstring(unsigned position, unsigned length) const;
-
bool isFunction() const { return length() > 0 && (*this)[length() - 1] == '('; }
union {
@@ -161,7 +159,7 @@ struct CSSParserValue {
inline void setFromFunction(CSSParserFunction*);
inline void setFromValueList(PassOwnPtr<CSSParserValueList>);
- PassRefPtr<CSSValue> createCSSValue();
+ PassRefPtrWillBeRawPtr<CSSValue> createCSSValue();
};
class CSSParserValueList {
@@ -175,8 +173,7 @@ public:
void addValue(const CSSParserValue&);
void insertValueAt(unsigned, const CSSParserValue&);
- void deleteValueAt(unsigned);
- void extend(CSSParserValueList&);
+ void stealValues(CSSParserValueList&);
unsigned size() const { return m_values.size(); }
unsigned currentIndex() { return m_current; }
@@ -189,10 +186,17 @@ public:
--m_current;
return current();
}
+ void setCurrentIndex(unsigned index)
+ {
+ ASSERT(index < m_values.size());
+ if (index < m_values.size())
+ m_current = index;
+ }
CSSParserValue* valueAt(unsigned i) { return i < m_values.size() ? &m_values[i] : 0; }
- void clear() { m_values.clear(); }
+ void clearAndLeakValues() { m_values.clear(); m_current = 0;}
+ void destroyAndClear();
private:
unsigned m_current;
@@ -219,23 +223,20 @@ public:
void setValue(const AtomicString& value) { m_selector->setValue(value); }
void setAttribute(const QualifiedName& value) { m_selector->setAttribute(value); }
void setArgument(const AtomicString& value) { m_selector->setArgument(value); }
- void setMatch(CSSSelector::Match value) { m_selector->m_match = value; }
- void setRelation(CSSSelector::Relation value) { m_selector->m_relation = value; }
+ void setMatch(CSSSelector::Match value) { m_selector->setMatch(value); }
+ void setRelation(CSSSelector::Relation value) { m_selector->setRelation(value); }
void setForPage() { m_selector->setForPage(); }
void setRelationIsAffectedByPseudoContent() { m_selector->setRelationIsAffectedByPseudoContent(); }
bool relationIsAffectedByPseudoContent() const { return m_selector->relationIsAffectedByPseudoContent(); }
void adoptSelectorVector(Vector<OwnPtr<CSSParserSelector> >& selectorVector);
- CSSParserSelector* functionArgumentSelector() const { return m_functionArgumentSelector; }
- void setFunctionArgumentSelector(CSSParserSelector* selector) { m_functionArgumentSelector = selector; }
- bool isDistributedPseudoElement() const { return m_selector->isDistributedPseudoElement(); }
- CSSParserSelector* findDistributedPseudoElementSelector() const;
+ bool hasHostPseudoSelector() const;
bool isContentPseudoElement() const { return m_selector->isContentPseudoElement(); }
CSSSelector::PseudoType pseudoType() const { return m_selector->pseudoType(); }
bool isCustomPseudoElement() const { return m_selector->isCustomPseudoElement(); }
- bool needsCrossingTreeScopeBoundary() const { return isCustomPseudoElement() || pseudoType() == CSSSelector::PseudoCue; }
+ bool crossesTreeScopes() const { return isCustomPseudoElement() || pseudoType() == CSSSelector::PseudoCue || pseudoType() == CSSSelector::PseudoShadow; }
bool isSimple() const;
bool hasShadowPseudo() const;
@@ -250,7 +251,6 @@ public:
private:
OwnPtr<CSSSelector> m_selector;
OwnPtr<CSSParserSelector> m_tagHistory;
- CSSParserSelector* m_functionArgumentSelector;
};
inline bool CSSParserSelector::hasShadowPseudo() const
@@ -274,6 +274,7 @@ inline void CSSParserValue::setFromFunction(CSSParserFunction* function)
id = CSSValueInvalid;
this->function = function;
unit = Function;
+ isInt = false;
}
inline void CSSParserValue::setFromValueList(PassOwnPtr<CSSParserValueList> valueList)
@@ -281,6 +282,7 @@ inline void CSSParserValue::setFromValueList(PassOwnPtr<CSSParserValueList> valu
id = CSSValueInvalid;
this->valueList = valueList.leakPtr();
unit = ValueList;
+ isInt = false;
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParserValuesTest.cpp b/chromium/third_party/WebKit/Source/core/css/CSSParserValuesTest.cpp
index 6d1ac8b939d..5e7bd926f40 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSParserValuesTest.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSParserValuesTest.cpp
@@ -56,4 +56,45 @@ TEST(CSSParserValuesTest, InitWithEmpty16BitsString)
ASSERT_EQ(0u, cssParserString.length());
}
+TEST(CSSParserValuesTest, EqualIgnoringCase8BitsString)
+{
+ CSSParserString cssParserString;
+ String string8bit("sHaDOw");
+ cssParserString.init(string8bit, 0, string8bit.length());
+
+ ASSERT_TRUE(cssParserString.equalIgnoringCase("shadow"));
+ ASSERT_TRUE(cssParserString.equalIgnoringCase("ShaDow"));
+ ASSERT_FALSE(cssParserString.equalIgnoringCase("shadow-all"));
+ ASSERT_FALSE(cssParserString.equalIgnoringCase("sha"));
+ ASSERT_FALSE(cssParserString.equalIgnoringCase("abCD"));
+}
+
+TEST(CSSParserValuesTest, EqualIgnoringCase16BitsString)
+{
+ String string16bit("sHaDOw");
+ string16bit.ensure16Bit();
+
+ CSSParserString cssParserString;
+ cssParserString.init(string16bit, 0, string16bit.length());
+
+ ASSERT_TRUE(cssParserString.equalIgnoringCase("shadow"));
+ ASSERT_TRUE(cssParserString.equalIgnoringCase("ShaDow"));
+ ASSERT_FALSE(cssParserString.equalIgnoringCase("shadow-all"));
+ ASSERT_FALSE(cssParserString.equalIgnoringCase("sha"));
+ ASSERT_FALSE(cssParserString.equalIgnoringCase("abCD"));
+}
+
+TEST(CSSParserValuesTest, CSSParserValuelistClear)
+{
+ CSSParserValueList list;
+ for (int i = 0; i < 3; ++i) {
+ CSSParserValue value;
+ value.setFromNumber(3);
+ list.addValue(value);
+ }
+ list.clearAndLeakValues();
+ ASSERT_FALSE(list.size());
+ ASSERT_FALSE(list.currentIndex());
+}
+
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.cpp
index eb350e7a9c0..97497512b54 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.cpp
@@ -25,7 +25,7 @@
#include "core/css/CSSBasicShapes.h"
#include "core/css/CSSCalculationValue.h"
#include "core/css/CSSHelper.h"
-#include "core/css/CSSParser.h"
+#include "core/css/CSSMarkup.h"
#include "core/css/CSSToLengthConversionData.h"
#include "core/css/Counter.h"
#include "core/css/Pair.h"
@@ -35,8 +35,9 @@
#include "core/dom/ExceptionCode.h"
#include "core/dom/Node.h"
#include "core/rendering/style/RenderStyle.h"
+#include "platform/Decimal.h"
#include "platform/LayoutUnit.h"
-#include "wtf/DecimalNumber.h"
+#include "platform/fonts/FontMetrics.h"
#include "wtf/StdLibExtras.h"
#include "wtf/text/StringBuffer.h"
#include "wtf/text/StringBuilder.h"
@@ -50,7 +51,7 @@ namespace WebCore {
const int maxValueForCssLength = INT_MAX / kFixedPointDenominator - 2;
const int minValueForCssLength = INT_MIN / kFixedPointDenominator + 2;
-static inline bool isValidCSSUnitTypeForDoubleConversion(CSSPrimitiveValue::UnitTypes unitType)
+static inline bool isValidCSSUnitTypeForDoubleConversion(CSSPrimitiveValue::UnitType unitType)
{
switch (unitType) {
case CSSPrimitiveValue::CSS_CALC:
@@ -105,7 +106,6 @@ static inline bool isValidCSSUnitTypeForDoubleConversion(CSSPrimitiveValue::Unit
case CSSPrimitiveValue::CSS_UNICODE_RANGE:
case CSSPrimitiveValue::CSS_UNKNOWN:
case CSSPrimitiveValue::CSS_URI:
- case CSSPrimitiveValue::CSS_VARIABLE_NAME:
return false;
}
@@ -113,7 +113,44 @@ static inline bool isValidCSSUnitTypeForDoubleConversion(CSSPrimitiveValue::Unit
return false;
}
-CSSPrimitiveValue::UnitCategory CSSPrimitiveValue::unitCategory(CSSPrimitiveValue::UnitTypes type)
+typedef HashMap<String, CSSPrimitiveValue::UnitType> StringToUnitTable;
+
+StringToUnitTable createStringToUnitTable()
+{
+ StringToUnitTable table;
+ table.set(String("em"), CSSPrimitiveValue::CSS_EMS);
+ table.set(String("ex"), CSSPrimitiveValue::CSS_EXS);
+ table.set(String("px"), CSSPrimitiveValue::CSS_PX);
+ table.set(String("cm"), CSSPrimitiveValue::CSS_CM);
+ table.set(String("mm"), CSSPrimitiveValue::CSS_MM);
+ table.set(String("in"), CSSPrimitiveValue::CSS_IN);
+ table.set(String("pt"), CSSPrimitiveValue::CSS_PT);
+ table.set(String("pc"), CSSPrimitiveValue::CSS_PC);
+ table.set(String("deg"), CSSPrimitiveValue::CSS_DEG);
+ table.set(String("rad"), CSSPrimitiveValue::CSS_RAD);
+ table.set(String("grad"), CSSPrimitiveValue::CSS_GRAD);
+ table.set(String("ms"), CSSPrimitiveValue::CSS_MS);
+ table.set(String("s"), CSSPrimitiveValue::CSS_S);
+ table.set(String("hz"), CSSPrimitiveValue::CSS_HZ);
+ table.set(String("khz"), CSSPrimitiveValue::CSS_KHZ);
+ table.set(String("dpi"), CSSPrimitiveValue::CSS_DPI);
+ table.set(String("dpcm"), CSSPrimitiveValue::CSS_DPCM);
+ table.set(String("dppx"), CSSPrimitiveValue::CSS_DPPX);
+ table.set(String("vw"), CSSPrimitiveValue::CSS_VW);
+ table.set(String("vh"), CSSPrimitiveValue::CSS_VH);
+ table.set(String("vmax"), CSSPrimitiveValue::CSS_VMIN);
+ table.set(String("vmin"), CSSPrimitiveValue::CSS_VMAX);
+ return table;
+}
+
+
+CSSPrimitiveValue::UnitType CSSPrimitiveValue::fromName(const String& unit)
+{
+ DEFINE_STATIC_LOCAL(StringToUnitTable, unitTable, (createStringToUnitTable()));
+ return unitTable.get(unit.lower());
+}
+
+CSSPrimitiveValue::UnitCategory CSSPrimitiveValue::unitCategory(UnitType type)
{
// Here we violate the spec (http://www.w3.org/TR/DOM-Level-2-Style/css.html#CSS-CSSPrimitiveValue) and allow conversions
// between CSS_PX and relative lengths (see cssPixelsPerInch comment in core/css/CSSHelper.h for the topic treatment).
@@ -140,11 +177,6 @@ CSSPrimitiveValue::UnitCategory CSSPrimitiveValue::unitCategory(CSSPrimitiveValu
case CSS_HZ:
case CSS_KHZ:
return CSSPrimitiveValue::UFrequency;
- case CSS_VW:
- case CSS_VH:
- case CSS_VMIN:
- case CSS_VMAX:
- return CSSPrimitiveValue::UViewportPercentageLength;
case CSS_DPPX:
case CSS_DPI:
case CSS_DPCM:
@@ -175,13 +207,13 @@ static CSSTextCache& cssTextCache()
return cache;
}
-unsigned short CSSPrimitiveValue::primitiveType() const
+CSSPrimitiveValue::UnitType CSSPrimitiveValue::primitiveType() const
{
if (m_primitiveUnitType == CSS_PROPERTY_ID || m_primitiveUnitType == CSS_VALUE_ID)
return CSS_IDENT;
if (m_primitiveUnitType != CSS_CALC)
- return m_primitiveUnitType;
+ return static_cast<UnitType>(m_primitiveUnitType);
switch (m_value.calc->category()) {
case CalcNumber:
@@ -194,8 +226,6 @@ unsigned short CSSPrimitiveValue::primitiveType() const
return CSS_CALC_PERCENTAGE_WITH_NUMBER;
case CalcPercentLength:
return CSS_CALC_PERCENTAGE_WITH_LENGTH;
- case CalcVariable:
- return CSS_UNKNOWN; // The type of a calculation containing a variable cannot be known until the value of the variable is determined.
case CalcOther:
return CSS_UNKNOWN;
}
@@ -242,14 +272,15 @@ CSSPrimitiveValue::CSSPrimitiveValue(CSSPropertyID propertyID)
m_value.propertyID = propertyID;
}
-CSSPrimitiveValue::CSSPrimitiveValue(int parserOperator)
+CSSPrimitiveValue::CSSPrimitiveValue(int parserOperator, UnitType type)
: CSSValue(PrimitiveClass)
{
+ ASSERT(type == CSS_PARSER_OPERATOR);
m_primitiveUnitType = CSS_PARSER_OPERATOR;
m_value.parserOperator = parserOperator;
}
-CSSPrimitiveValue::CSSPrimitiveValue(double num, UnitTypes type)
+CSSPrimitiveValue::CSSPrimitiveValue(double num, UnitType type)
: CSSValue(PrimitiveClass)
{
m_primitiveUnitType = type;
@@ -257,7 +288,7 @@ CSSPrimitiveValue::CSSPrimitiveValue(double num, UnitTypes type)
m_value.num = num;
}
-CSSPrimitiveValue::CSSPrimitiveValue(const String& str, UnitTypes type)
+CSSPrimitiveValue::CSSPrimitiveValue(const String& str, UnitType type)
: CSSValue(PrimitiveClass)
{
m_primitiveUnitType = type;
@@ -265,10 +296,16 @@ CSSPrimitiveValue::CSSPrimitiveValue(const String& str, UnitTypes type)
m_value.string->ref();
}
+CSSPrimitiveValue::CSSPrimitiveValue(const LengthSize& lengthSize, const RenderStyle& style)
+ : CSSValue(PrimitiveClass)
+{
+ init(lengthSize, style);
+}
-CSSPrimitiveValue::CSSPrimitiveValue(RGBA32 color)
+CSSPrimitiveValue::CSSPrimitiveValue(RGBA32 color, UnitType type)
: CSSValue(PrimitiveClass)
{
+ ASSERT(type == CSS_RGBCOLOR);
m_primitiveUnitType = CSS_RGBCOLOR;
m_value.rgbcolor = color;
}
@@ -278,136 +315,116 @@ CSSPrimitiveValue::CSSPrimitiveValue(const Length& length, float zoom)
{
switch (length.type()) {
case Auto:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueAuto;
+ break;
case Intrinsic:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueIntrinsic;
+ break;
case MinIntrinsic:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueMinIntrinsic;
+ break;
case MinContent:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueMinContent;
+ break;
case MaxContent:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueMaxContent;
+ break;
case FillAvailable:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueWebkitFillAvailable;
+ break;
case FitContent:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueWebkitFitContent;
+ break;
case ExtendToZoom:
+ m_primitiveUnitType = CSS_VALUE_ID;
+ m_value.valueID = CSSValueInternalExtendToZoom;
+ break;
case Percent:
- case ViewportPercentageWidth:
- case ViewportPercentageHeight:
- case ViewportPercentageMin:
- case ViewportPercentageMax:
- init(length);
- return;
+ m_primitiveUnitType = CSS_PERCENTAGE;
+ ASSERT(std::isfinite(length.percent()));
+ m_value.num = length.percent();
+ break;
case Fixed:
m_primitiveUnitType = CSS_PX;
m_value.num = length.value() / zoom;
- return;
- case Calculated:
- init(CSSCalcValue::create(length.calculationValue(), zoom));
- return;
+ break;
+ case Calculated: {
+ const CalculationValue& calc = length.calculationValue();
+ if (calc.pixels() && calc.percent()) {
+ init(CSSCalcValue::create(
+ CSSCalcValue::createExpressionNode(calc.pixels() / zoom, calc.percent()),
+ calc.isNonNegative() ? ValueRangeNonNegative : ValueRangeAll));
+ break;
+ }
+ if (calc.percent()) {
+ m_primitiveUnitType = CSS_PERCENTAGE;
+ m_value.num = calc.percent();
+ } else {
+ m_primitiveUnitType = CSS_PX;
+ m_value.num = calc.pixels() / zoom;
+ }
+ if (m_value.num < 0 && calc.isNonNegative())
+ m_value.num = 0;
+ break;
+ }
+ case DeviceWidth:
+ case DeviceHeight:
case Undefined:
ASSERT_NOT_REACHED();
break;
}
}
-void CSSPrimitiveValue::init(const Length& length)
+void CSSPrimitiveValue::init(const LengthSize& lengthSize, const RenderStyle& style)
{
- switch (length.type()) {
- case Auto:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueAuto;
- break;
- case Fixed:
- m_primitiveUnitType = CSS_PX;
- m_value.num = length.value();
- break;
- case Intrinsic:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueIntrinsic;
- break;
- case MinIntrinsic:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueMinIntrinsic;
- break;
- case MinContent:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueMinContent;
- break;
- case MaxContent:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueMaxContent;
- break;
- case FillAvailable:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueWebkitFillAvailable;
- break;
- case FitContent:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueWebkitFitContent;
- break;
- case ExtendToZoom:
- m_primitiveUnitType = CSS_VALUE_ID;
- m_value.valueID = CSSValueInternalExtendToZoom;
- break;
- case Percent:
- m_primitiveUnitType = CSS_PERCENTAGE;
- ASSERT(std::isfinite(length.percent()));
- m_value.num = length.percent();
- break;
- case ViewportPercentageWidth:
- m_primitiveUnitType = CSS_VW;
- m_value.num = length.viewportPercentageLength();
- break;
- case ViewportPercentageHeight:
- m_primitiveUnitType = CSS_VH;
- m_value.num = length.viewportPercentageLength();
- break;
- case ViewportPercentageMin:
- m_primitiveUnitType = CSS_VMIN;
- m_value.num = length.viewportPercentageLength();
- break;
- case ViewportPercentageMax:
- m_primitiveUnitType = CSS_VMAX;
- m_value.num = length.viewportPercentageLength();
- break;
- case Calculated:
- case Undefined:
- ASSERT_NOT_REACHED();
- break;
- }
+ m_primitiveUnitType = CSS_PAIR;
+ m_hasCachedCSSText = false;
+ m_value.pair = Pair::create(create(lengthSize.width(), style.effectiveZoom()), create(lengthSize.height(), style.effectiveZoom()), Pair::KeepIdenticalValues).leakRef();
}
-void CSSPrimitiveValue::init(PassRefPtr<Counter> c)
+void CSSPrimitiveValue::init(PassRefPtrWillBeRawPtr<Counter> c)
{
m_primitiveUnitType = CSS_COUNTER;
m_hasCachedCSSText = false;
m_value.counter = c.leakRef();
}
-void CSSPrimitiveValue::init(PassRefPtr<Rect> r)
+void CSSPrimitiveValue::init(PassRefPtrWillBeRawPtr<Rect> r)
{
m_primitiveUnitType = CSS_RECT;
m_hasCachedCSSText = false;
m_value.rect = r.leakRef();
}
-void CSSPrimitiveValue::init(PassRefPtr<Quad> quad)
+void CSSPrimitiveValue::init(PassRefPtrWillBeRawPtr<Quad> quad)
{
m_primitiveUnitType = CSS_QUAD;
m_hasCachedCSSText = false;
m_value.quad = quad.leakRef();
}
-void CSSPrimitiveValue::init(PassRefPtr<Pair> p)
+void CSSPrimitiveValue::init(PassRefPtrWillBeRawPtr<Pair> p)
{
m_primitiveUnitType = CSS_PAIR;
m_hasCachedCSSText = false;
m_value.pair = p.leakRef();
}
-void CSSPrimitiveValue::init(PassRefPtr<CSSCalcValue> c)
+void CSSPrimitiveValue::init(PassRefPtrWillBeRawPtr<CSSCalcValue> c)
{
m_primitiveUnitType = CSS_CALC;
m_hasCachedCSSText = false;
m_value.calc = c.leakRef();
}
-void CSSPrimitiveValue::init(PassRefPtr<CSSBasicShape> shape)
+void CSSPrimitiveValue::init(PassRefPtrWillBeRawPtr<CSSBasicShape> shape)
{
m_primitiveUnitType = CSS_SHAPE;
m_hasCachedCSSText = false;
@@ -421,37 +438,54 @@ CSSPrimitiveValue::~CSSPrimitiveValue()
void CSSPrimitiveValue::cleanup()
{
- switch (static_cast<UnitTypes>(m_primitiveUnitType)) {
+ switch (static_cast<UnitType>(m_primitiveUnitType)) {
case CSS_STRING:
case CSS_URI:
case CSS_ATTR:
case CSS_COUNTER_NAME:
- case CSS_VARIABLE_NAME:
case CSS_PARSER_HEXCOLOR:
if (m_value.string)
m_value.string->deref();
break;
case CSS_COUNTER:
+ // We must not call deref() when oilpan is enabled because m_value.counter is traced.
+#if !ENABLE(OILPAN)
m_value.counter->deref();
+#endif
break;
case CSS_RECT:
+ // We must not call deref() when oilpan is enabled because m_value.rect is traced.
+#if !ENABLE(OILPAN)
m_value.rect->deref();
+#endif
break;
case CSS_QUAD:
+ // We must not call deref() when oilpan is enabled because m_value.quad is traced.
+#if !ENABLE(OILPAN)
m_value.quad->deref();
+#endif
break;
case CSS_PAIR:
+ // We must not call deref() when oilpan is enabled because m_value.pair is traced.
+#if !ENABLE(OILPAN)
m_value.pair->deref();
+#endif
break;
case CSS_CALC:
+ // We must not call deref() when oilpan is enabled because m_value.calc is traced.
+#if !ENABLE(OILPAN)
m_value.calc->deref();
+#endif
break;
case CSS_CALC_PERCENTAGE_WITH_NUMBER:
case CSS_CALC_PERCENTAGE_WITH_LENGTH:
ASSERT_NOT_REACHED();
break;
case CSS_SHAPE:
+ // We must not call deref() when oilpan is enabled because m_value.shape is traced.
+#if !ENABLE(OILPAN)
m_value.shape->deref();
+#endif
break;
case CSS_NUMBER:
case CSS_PARSER_INTEGER:
@@ -554,11 +588,14 @@ template<> double CSSPrimitiveValue::computeLength(const CSSToLengthConversionDa
double CSSPrimitiveValue::computeLengthDouble(const CSSToLengthConversionData& conversionData)
{
+ // The logic in this function is duplicated in MediaValues::computeLength
+ // because MediaValues::computeLength needs nearly identical logic, but we haven't found a way to make
+ // CSSPrimitiveValue::computeLengthDouble more generic (to solve both cases) without hurting performance.
if (m_primitiveUnitType == CSS_CALC)
return m_value.calc->computeLengthPx(conversionData);
const RenderStyle& style = conversionData.style();
- const RenderStyle& rootStyle = conversionData.rootStyle();
+ const RenderStyle* rootStyle = conversionData.rootStyle();
bool computingFontSize = conversionData.computingFontSize();
double factor;
@@ -577,7 +614,10 @@ double CSSPrimitiveValue::computeLengthDouble(const CSSToLengthConversionData& c
factor = (computingFontSize ? style.fontDescription().specifiedSize() : style.fontDescription().computedSize()) / 2.0;
break;
case CSS_REMS:
- factor = computingFontSize ? rootStyle.fontDescription().specifiedSize() : rootStyle.fontDescription().computedSize();
+ if (rootStyle)
+ factor = computingFontSize ? rootStyle->fontDescription().specifiedSize() : rootStyle->fontDescription().computedSize();
+ else
+ factor = 1.0;
break;
case CSS_CHS:
factor = style.fontMetrics().zeroWidth();
@@ -600,6 +640,18 @@ double CSSPrimitiveValue::computeLengthDouble(const CSSToLengthConversionData& c
case CSS_PC:
factor = cssPixelsPerPica;
break;
+ case CSS_VW:
+ factor = conversionData.viewportWidthPercent();
+ break;
+ case CSS_VH:
+ factor = conversionData.viewportHeightPercent();
+ break;
+ case CSS_VMIN:
+ factor = conversionData.viewportMinPercent();
+ break;
+ case CSS_VMAX:
+ factor = conversionData.viewportMaxPercent();
+ break;
case CSS_CALC_PERCENTAGE_WITH_LENGTH:
case CSS_CALC_PERCENTAGE_WITH_NUMBER:
ASSERT_NOT_REACHED();
@@ -619,15 +671,29 @@ double CSSPrimitiveValue::computeLengthDouble(const CSSToLengthConversionData& c
return result * conversionData.zoom();
}
+void CSSPrimitiveValue::accumulateLengthArray(CSSLengthArray& lengthArray, double multiplier) const
+{
+ ASSERT(lengthArray.size() == LengthUnitTypeCount);
+
+ if (m_primitiveUnitType == CSS_CALC) {
+ cssCalcValue()->accumulateLengthArray(lengthArray, multiplier);
+ return;
+ }
+
+ LengthUnitType lengthType;
+ if (unitTypeToLengthUnitType(static_cast<UnitType>(m_primitiveUnitType), lengthType))
+ lengthArray.at(lengthType) += m_value.num * conversionToCanonicalUnitsScaleFactor(static_cast<UnitType>(m_primitiveUnitType)) * multiplier;
+}
+
void CSSPrimitiveValue::setFloatValue(unsigned short, double, ExceptionState& exceptionState)
{
// Keeping values immutable makes optimizations easier and allows sharing of the primitive value objects.
// No other engine supports mutating style through this API. Computed style is always read-only anyway.
// Supporting setter would require making primitive value copy-on-write and taking care of style invalidation.
- exceptionState.throwUninformativeAndGenericDOMException(NoModificationAllowedError);
+ exceptionState.throwDOMException(NoModificationAllowedError, "CSSPrimitiveValue objects are read-only.");
}
-double CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(unsigned short unitType)
+double CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(UnitType unitType)
{
double factor = 1.0;
// FIXME: the switch can be replaced by an array of scale factors.
@@ -679,22 +745,22 @@ double CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(unsigned short u
return factor;
}
-double CSSPrimitiveValue::getDoubleValue(unsigned short unitType, ExceptionState& exceptionState) const
+double CSSPrimitiveValue::getDoubleValue(UnitType unitType, ExceptionState& exceptionState) const
{
double result = 0;
- bool success = getDoubleValueInternal(static_cast<UnitTypes>(unitType), &result);
+ bool success = getDoubleValueInternal(unitType, &result);
if (!success) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
+ exceptionState.throwDOMException(InvalidAccessError, "Failed to obtain a double value.");
return 0.0;
}
return result;
}
-double CSSPrimitiveValue::getDoubleValue(unsigned short unitType) const
+double CSSPrimitiveValue::getDoubleValue(UnitType unitType) const
{
double result = 0;
- getDoubleValueInternal(static_cast<UnitTypes>(unitType), &result);
+ getDoubleValueInternal(unitType, &result);
return result;
}
@@ -703,9 +769,9 @@ double CSSPrimitiveValue::getDoubleValue() const
return m_primitiveUnitType != CSS_CALC ? m_value.num : m_value.calc->doubleValue();
}
-CSSPrimitiveValue::UnitTypes CSSPrimitiveValue::canonicalUnitTypeForCategory(UnitCategory category)
+CSSPrimitiveValue::UnitType CSSPrimitiveValue::canonicalUnitTypeForCategory(UnitCategory category)
{
- // The canonical unit type is chosen according to the way CSSParser::validUnit() chooses the default unit
+ // The canonical unit type is chosen according to the way BisonCSSParser::validUnit() chooses the default unit
// in each category (based on unitflags).
switch (category) {
case UNumber:
@@ -720,8 +786,6 @@ CSSPrimitiveValue::UnitTypes CSSPrimitiveValue::canonicalUnitTypeForCategory(Uni
return CSS_DEG;
case UFrequency:
return CSS_HZ;
- case UViewportPercentageLength:
- return CSS_UNKNOWN; // Cannot convert between numbers and relative lengths.
case UResolution:
return CSS_DPPX;
default:
@@ -729,12 +793,12 @@ CSSPrimitiveValue::UnitTypes CSSPrimitiveValue::canonicalUnitTypeForCategory(Uni
}
}
-bool CSSPrimitiveValue::getDoubleValueInternal(UnitTypes requestedUnitType, double* result) const
+bool CSSPrimitiveValue::getDoubleValueInternal(UnitType requestedUnitType, double* result) const
{
- if (!isValidCSSUnitTypeForDoubleConversion(static_cast<UnitTypes>(m_primitiveUnitType)) || !isValidCSSUnitTypeForDoubleConversion(requestedUnitType))
+ if (!isValidCSSUnitTypeForDoubleConversion(static_cast<UnitType>(m_primitiveUnitType)) || !isValidCSSUnitTypeForDoubleConversion(requestedUnitType))
return false;
- UnitTypes sourceUnitType = static_cast<UnitTypes>(primitiveType());
+ UnitType sourceUnitType = primitiveType();
if (requestedUnitType == sourceUnitType || requestedUnitType == CSS_DIMENSION) {
*result = getDoubleValue();
return true;
@@ -743,7 +807,7 @@ bool CSSPrimitiveValue::getDoubleValueInternal(UnitTypes requestedUnitType, doub
UnitCategory sourceCategory = unitCategory(sourceUnitType);
ASSERT(sourceCategory != UOther);
- UnitTypes targetUnitType = requestedUnitType;
+ UnitType targetUnitType = requestedUnitType;
UnitCategory targetCategory = unitCategory(targetUnitType);
ASSERT(targetCategory != UOther);
@@ -759,7 +823,7 @@ bool CSSPrimitiveValue::getDoubleValueInternal(UnitTypes requestedUnitType, doub
}
if (sourceUnitType == CSS_NUMBER) {
- // We interpret conversion from CSS_NUMBER in the same way as CSSParser::validUnit() while using non-strict mode.
+ // We interpret conversion from CSS_NUMBER in the same way as BisonCSSParser::validUnit() while using non-strict mode.
sourceUnitType = canonicalUnitTypeForCategory(targetCategory);
if (sourceUnitType == CSS_UNKNOWN)
return false;
@@ -779,12 +843,85 @@ bool CSSPrimitiveValue::getDoubleValueInternal(UnitTypes requestedUnitType, doub
return true;
}
+bool CSSPrimitiveValue::unitTypeToLengthUnitType(UnitType unitType, LengthUnitType& lengthType)
+{
+ switch (unitType) {
+ case CSSPrimitiveValue::CSS_PX:
+ case CSSPrimitiveValue::CSS_CM:
+ case CSSPrimitiveValue::CSS_MM:
+ case CSSPrimitiveValue::CSS_IN:
+ case CSSPrimitiveValue::CSS_PT:
+ case CSSPrimitiveValue::CSS_PC:
+ lengthType = UnitTypePixels;
+ return true;
+ case CSSPrimitiveValue::CSS_EMS:
+ lengthType = UnitTypeFontSize;
+ return true;
+ case CSSPrimitiveValue::CSS_EXS:
+ lengthType = UnitTypeFontXSize;
+ return true;
+ case CSSPrimitiveValue::CSS_REMS:
+ lengthType = UnitTypeRootFontSize;
+ return true;
+ case CSSPrimitiveValue::CSS_CHS:
+ lengthType = UnitTypeZeroCharacterWidth;
+ return true;
+ case CSSPrimitiveValue::CSS_PERCENTAGE:
+ lengthType = UnitTypePercentage;
+ return true;
+ case CSSPrimitiveValue::CSS_VW:
+ lengthType = UnitTypeViewportWidth;
+ return true;
+ case CSSPrimitiveValue::CSS_VH:
+ lengthType = UnitTypeViewportHeight;
+ return true;
+ case CSSPrimitiveValue::CSS_VMIN:
+ lengthType = UnitTypeViewportMin;
+ return true;
+ case CSSPrimitiveValue::CSS_VMAX:
+ lengthType = UnitTypeViewportMax;
+ return true;
+ default:
+ return false;
+ }
+}
+
+CSSPrimitiveValue::UnitType CSSPrimitiveValue::lengthUnitTypeToUnitType(LengthUnitType type)
+{
+ switch (type) {
+ case UnitTypePixels:
+ return CSSPrimitiveValue::CSS_PX;
+ case UnitTypeFontSize:
+ return CSSPrimitiveValue::CSS_EMS;
+ case UnitTypeFontXSize:
+ return CSSPrimitiveValue::CSS_EXS;
+ case UnitTypeRootFontSize:
+ return CSSPrimitiveValue::CSS_REMS;
+ case UnitTypeZeroCharacterWidth:
+ return CSSPrimitiveValue::CSS_CHS;
+ case UnitTypePercentage:
+ return CSSPrimitiveValue::CSS_PERCENTAGE;
+ case UnitTypeViewportWidth:
+ return CSSPrimitiveValue::CSS_VW;
+ case UnitTypeViewportHeight:
+ return CSSPrimitiveValue::CSS_VH;
+ case UnitTypeViewportMin:
+ return CSSPrimitiveValue::CSS_VMIN;
+ case UnitTypeViewportMax:
+ return CSSPrimitiveValue::CSS_VMAX;
+ case LengthUnitTypeCount:
+ break;
+ }
+ ASSERT_NOT_REACHED();
+ return CSSPrimitiveValue::CSS_UNKNOWN;
+}
+
void CSSPrimitiveValue::setStringValue(unsigned short, const String&, ExceptionState& exceptionState)
{
// Keeping values immutable makes optimizations easier and allows sharing of the primitive value objects.
// No other engine supports mutating style through this API. Computed style is always read-only anyway.
// Supporting setter would require making primitive value copy-on-write and taking care of style invalidation.
- exceptionState.throwUninformativeAndGenericDOMException(NoModificationAllowedError);
+ exceptionState.throwDOMException(NoModificationAllowedError, "CSSPrimitiveValue objects are read-only.");
}
String CSSPrimitiveValue::getStringValue(ExceptionState& exceptionState) const
@@ -793,14 +930,13 @@ String CSSPrimitiveValue::getStringValue(ExceptionState& exceptionState) const
case CSS_STRING:
case CSS_ATTR:
case CSS_URI:
- case CSS_VARIABLE_NAME:
return m_value.string;
case CSS_VALUE_ID:
return valueName(m_value.valueID);
case CSS_PROPERTY_ID:
return propertyName(m_value.propertyID);
default:
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
+ exceptionState.throwDOMException(InvalidAccessError, "This object's value cannot be represented as a string.");
break;
}
@@ -813,7 +949,6 @@ String CSSPrimitiveValue::getStringValue() const
case CSS_STRING:
case CSS_ATTR:
case CSS_URI:
- case CSS_VARIABLE_NAME:
return m_value.string;
case CSS_VALUE_ID:
return valueName(m_value.valueID);
@@ -829,7 +964,7 @@ String CSSPrimitiveValue::getStringValue() const
Counter* CSSPrimitiveValue::getCounterValue(ExceptionState& exceptionState) const
{
if (m_primitiveUnitType != CSS_COUNTER) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
+ exceptionState.throwDOMException(InvalidAccessError, "This object is not a counter value.");
return 0;
}
@@ -839,7 +974,7 @@ Counter* CSSPrimitiveValue::getCounterValue(ExceptionState& exceptionState) cons
Rect* CSSPrimitiveValue::getRectValue(ExceptionState& exceptionState) const
{
if (m_primitiveUnitType != CSS_RECT) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
+ exceptionState.throwDOMException(InvalidAccessError, "This object is not a rect value.");
return 0;
}
@@ -849,18 +984,18 @@ Rect* CSSPrimitiveValue::getRectValue(ExceptionState& exceptionState) const
Quad* CSSPrimitiveValue::getQuadValue(ExceptionState& exceptionState) const
{
if (m_primitiveUnitType != CSS_QUAD) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
+ exceptionState.throwDOMException(InvalidAccessError, "This object is not a quad value.");
return 0;
}
return m_value.quad;
}
-PassRefPtr<RGBColor> CSSPrimitiveValue::getRGBColorValue(ExceptionState& exceptionState) const
+PassRefPtrWillBeRawPtr<RGBColor> CSSPrimitiveValue::getRGBColorValue(ExceptionState& exceptionState) const
{
if (m_primitiveUnitType != CSS_RGBCOLOR) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
- return 0;
+ exceptionState.throwDOMException(InvalidAccessError, "This object is not an RGB color value.");
+ return nullptr;
}
// FIMXE: This should not return a new object for each invocation.
@@ -870,7 +1005,7 @@ PassRefPtr<RGBColor> CSSPrimitiveValue::getRGBColorValue(ExceptionState& excepti
Pair* CSSPrimitiveValue::getPairValue(ExceptionState& exceptionState) const
{
if (m_primitiveUnitType != CSS_PAIR) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidAccessError);
+ exceptionState.throwDOMException(InvalidAccessError, "This object is not a pair value.");
return 0;
}
@@ -879,16 +1014,10 @@ Pair* CSSPrimitiveValue::getPairValue(ExceptionState& exceptionState) const
static String formatNumber(double number, const char* suffix, unsigned suffixLength)
{
- DecimalNumber decimal(number);
-
- StringBuffer<LChar> buffer(decimal.bufferLengthForStringDecimal() + suffixLength);
- unsigned length = decimal.toStringDecimal(buffer.characters(), buffer.length());
- ASSERT(length + suffixLength == buffer.length());
-
- for (unsigned i = 0; i < suffixLength; ++i)
- buffer[length + i] = static_cast<LChar>(suffix[i]);
-
- return String::adopt(buffer);
+ Decimal decimal = Decimal::fromDouble(number);
+ String result = decimal.toString();
+ result.append(suffix, suffixLength);
+ return result;
}
template <unsigned characterCount>
@@ -897,6 +1026,99 @@ ALWAYS_INLINE static String formatNumber(double number, const char (&characters)
return formatNumber(number, characters, characterCount - 1);
}
+static String formatNumber(double number, const char* characters)
+{
+ return formatNumber(number, characters, strlen(characters));
+}
+
+const char* CSSPrimitiveValue::unitTypeToString(UnitType type)
+{
+ switch (type) {
+ case CSS_NUMBER:
+ case CSS_PARSER_INTEGER:
+ return "";
+ case CSS_PERCENTAGE:
+ return "%";
+ case CSS_EMS:
+ return "em";
+ case CSS_EXS:
+ return "ex";
+ case CSS_REMS:
+ return "rem";
+ case CSS_CHS:
+ return "ch";
+ case CSS_PX:
+ return "px";
+ case CSS_CM:
+ return "cm";
+ case CSS_DPPX:
+ return "dppx";
+ case CSS_DPI:
+ return "dpi";
+ case CSS_DPCM:
+ return "dpcm";
+ case CSS_MM:
+ return "mm";
+ case CSS_IN:
+ return "in";
+ case CSS_PT:
+ return "pt";
+ case CSS_PC:
+ return "pc";
+ case CSS_DEG:
+ return "deg";
+ case CSS_RAD:
+ return "rad";
+ case CSS_GRAD:
+ return "grad";
+ case CSS_MS:
+ return "ms";
+ case CSS_S:
+ return "s";
+ case CSS_HZ:
+ return "hz";
+ case CSS_KHZ:
+ return "khz";
+ case CSS_TURN:
+ return "turn";
+ case CSS_FR:
+ return "fr";
+ case CSS_VW:
+ return "vw";
+ case CSS_VH:
+ return "vh";
+ case CSS_VMIN:
+ return "vmin";
+ case CSS_VMAX:
+ return "vmax";
+ case CSS_UNKNOWN:
+ case CSS_DIMENSION:
+ case CSS_STRING:
+ case CSS_URI:
+ case CSS_VALUE_ID:
+ case CSS_PROPERTY_ID:
+ case CSS_ATTR:
+ case CSS_COUNTER_NAME:
+ case CSS_COUNTER:
+ case CSS_RECT:
+ case CSS_QUAD:
+ case CSS_RGBCOLOR:
+ case CSS_PARSER_HEXCOLOR:
+ case CSS_PAIR:
+ case CSS_PARSER_OPERATOR:
+ case CSS_PARSER_IDENTIFIER:
+ case CSS_CALC:
+ case CSS_SHAPE:
+ case CSS_IDENT:
+ case CSS_UNICODE_RANGE:
+ case CSS_CALC_PERCENTAGE_WITH_NUMBER:
+ case CSS_CALC_PERCENTAGE_WITH_LENGTH:
+ break;
+ };
+ ASSERT_NOT_REACHED();
+ return "";
+}
+
String CSSPrimitiveValue::customCSSText(CSSTextFormattingFlags formattingFlag) const
{
// FIXME: return the original value instead of a generated one (e.g. color
@@ -914,74 +1136,34 @@ String CSSPrimitiveValue::customCSSText(CSSTextFormattingFlags formattingFlag) c
break;
case CSS_NUMBER:
case CSS_PARSER_INTEGER:
- text = formatNumber(m_value.num, "");
- break;
case CSS_PERCENTAGE:
- text = formatNumber(m_value.num, "%");
- break;
case CSS_EMS:
- text = formatNumber(m_value.num, "em");
- break;
case CSS_EXS:
- text = formatNumber(m_value.num, "ex");
- break;
case CSS_REMS:
- text = formatNumber(m_value.num, "rem");
- break;
case CSS_CHS:
- text = formatNumber(m_value.num, "ch");
- break;
case CSS_PX:
- text = formatNumber(m_value.num, "px");
- break;
case CSS_CM:
- text = formatNumber(m_value.num, "cm");
- break;
case CSS_DPPX:
- text = formatNumber(m_value.num, "dppx");
- break;
case CSS_DPI:
- text = formatNumber(m_value.num, "dpi");
- break;
case CSS_DPCM:
- text = formatNumber(m_value.num, "dpcm");
- break;
case CSS_MM:
- text = formatNumber(m_value.num, "mm");
- break;
case CSS_IN:
- text = formatNumber(m_value.num, "in");
- break;
case CSS_PT:
- text = formatNumber(m_value.num, "pt");
- break;
case CSS_PC:
- text = formatNumber(m_value.num, "pc");
- break;
case CSS_DEG:
- text = formatNumber(m_value.num, "deg");
- break;
case CSS_RAD:
- text = formatNumber(m_value.num, "rad");
- break;
case CSS_GRAD:
- text = formatNumber(m_value.num, "grad");
- break;
case CSS_MS:
- text = formatNumber(m_value.num, "ms");
- break;
case CSS_S:
- text = formatNumber(m_value.num, "s");
- break;
case CSS_HZ:
- text = formatNumber(m_value.num, "hz");
- break;
case CSS_KHZ:
- text = formatNumber(m_value.num, "khz");
- break;
case CSS_TURN:
- text = formatNumber(m_value.num, "turn");
- break;
+ case CSS_FR:
+ case CSS_VW:
+ case CSS_VH:
+ case CSS_VMIN:
+ case CSS_VMAX:
+ text = formatNumber(m_value.num, unitTypeToString((UnitType)m_primitiveUnitType));
case CSS_DIMENSION:
// FIXME: We currently don't handle CSS_DIMENSION properly as we don't store
// the actual dimension, just the numeric value as a string.
@@ -1046,37 +1228,9 @@ String CSSPrimitiveValue::customCSSText(CSSTextFormattingFlags formattingFlag) c
if (m_primitiveUnitType == CSS_PARSER_HEXCOLOR)
Color::parseHexColor(m_value.string, rgbColor);
Color color(rgbColor);
-
- StringBuilder result;
- result.reserveCapacity(32);
- bool colorHasAlpha = color.hasAlpha();
- if (colorHasAlpha)
- result.append("rgba(", 5);
- else
- result.append("rgb(", 4);
-
- result.appendNumber(static_cast<unsigned char>(color.red()));
- result.append(", ", 2);
-
- result.appendNumber(static_cast<unsigned char>(color.green()));
- result.append(", ", 2);
-
- result.appendNumber(static_cast<unsigned char>(color.blue()));
- if (colorHasAlpha) {
- result.append(", ", 2);
-
- NumberToStringBuffer buffer;
- const char* alphaString = numberToFixedPrecisionString(color.alpha() / 255.0f, 6, buffer, true);
- result.append(alphaString, strlen(alphaString));
- }
-
- result.append(')');
- text = result.toString();
+ text = color.serializedAsCSSComponentValue();
break;
}
- case CSS_FR:
- text = formatNumber(m_value.num, "fr");
- break;
case CSS_PAIR:
text = getPairValue()->cssText();
break;
@@ -1094,21 +1248,6 @@ String CSSPrimitiveValue::customCSSText(CSSTextFormattingFlags formattingFlag) c
case CSS_SHAPE:
text = m_value.shape->cssText();
break;
- case CSS_VW:
- text = formatNumber(m_value.num, "vw");
- break;
- case CSS_VH:
- text = formatNumber(m_value.num, "vh");
- break;
- case CSS_VMIN:
- text = formatNumber(m_value.num, "vmin");
- break;
- case CSS_VMAX:
- text = formatNumber(m_value.num, "vmax");
- break;
- case CSS_VARIABLE_NAME:
- text = "var(" + String(m_value.string) + ")";
- break;
}
ASSERT(!cssTextCache().contains(this));
@@ -1117,80 +1256,16 @@ String CSSPrimitiveValue::customCSSText(CSSTextFormattingFlags formattingFlag) c
return text;
}
-String CSSPrimitiveValue::customSerializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPrimitiveValue::cloneForCSSOM() const
{
- if (isVariableName()) {
- AtomicString variableName(m_value.string);
- if (variables.contains(variableName))
- return variables.get(variableName);
- }
- if (CSSCalcValue* calcValue = cssCalcValue())
- return calcValue->customSerializeResolvingVariables(variables);
- if (Pair* pairValue = getPairValue())
- return pairValue->serializeResolvingVariables(variables);
- if (Rect* rectVal = getRectValue())
- return rectVal->serializeResolvingVariables(variables);
- if (Quad* quadVal = getQuadValue())
- return quadVal->serializeResolvingVariables(variables);
- if (CSSBasicShape* shapeValue = getShapeValue())
- return shapeValue->serializeResolvingVariables(variables);
- return customCSSText();
-}
-
-bool CSSPrimitiveValue::hasVariableReference() const
-{
- if (CSSCalcValue* calcValue = cssCalcValue())
- return calcValue->hasVariableReference();
- if (Pair* pairValue = getPairValue())
- return pairValue->hasVariableReference();
- if (Quad* quadValue = getQuadValue())
- return quadValue->hasVariableReference();
- if (Rect* rectValue = getRectValue())
- return rectValue->hasVariableReference();
- if (CSSBasicShape* shapeValue = getShapeValue())
- return shapeValue->hasVariableReference();
- return isVariableName();
-}
-
-void CSSPrimitiveValue::addSubresourceStyleURLs(ListHashSet<KURL>& urls, const StyleSheetContents* styleSheet) const
-{
- if (m_primitiveUnitType == CSS_URI)
- addSubresourceURL(urls, styleSheet->completeURL(m_value.string));
-}
-
-Length CSSPrimitiveValue::viewportPercentageLength()
-{
- ASSERT(isViewportPercentageLength());
- Length viewportLength;
- switch (m_primitiveUnitType) {
- case CSS_VW:
- viewportLength = Length(getDoubleValue(), ViewportPercentageWidth);
- break;
- case CSS_VH:
- viewportLength = Length(getDoubleValue(), ViewportPercentageHeight);
- break;
- case CSS_VMIN:
- viewportLength = Length(getDoubleValue(), ViewportPercentageMin);
- break;
- case CSS_VMAX:
- viewportLength = Length(getDoubleValue(), ViewportPercentageMax);
- break;
- default:
- break;
- }
- return viewportLength;
-}
-
-PassRefPtr<CSSPrimitiveValue> CSSPrimitiveValue::cloneForCSSOM() const
-{
- RefPtr<CSSPrimitiveValue> result;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = nullptr;
switch (m_primitiveUnitType) {
case CSS_STRING:
case CSS_URI:
case CSS_ATTR:
case CSS_COUNTER_NAME:
- result = CSSPrimitiveValue::create(m_value.string, static_cast<UnitTypes>(m_primitiveUnitType));
+ result = CSSPrimitiveValue::create(m_value.string, static_cast<UnitType>(m_primitiveUnitType));
break;
case CSS_COUNTER:
result = CSSPrimitiveValue::create(m_value.counter->cloneForCSSOM());
@@ -1242,7 +1317,7 @@ PassRefPtr<CSSPrimitiveValue> CSSPrimitiveValue::cloneForCSSOM() const
case CSS_DPI:
case CSS_DPCM:
case CSS_FR:
- result = CSSPrimitiveValue::create(m_value.num, static_cast<UnitTypes>(m_primitiveUnitType));
+ result = CSSPrimitiveValue::create(m_value.num, static_cast<UnitType>(m_primitiveUnitType));
break;
case CSS_PROPERTY_ID:
result = CSSPrimitiveValue::createIdentifier(m_value.propertyID);
@@ -1315,7 +1390,6 @@ bool CSSPrimitiveValue::equals(const CSSPrimitiveValue& other) const
case CSS_COUNTER_NAME:
case CSS_PARSER_IDENTIFIER:
case CSS_PARSER_HEXCOLOR:
- case CSS_VARIABLE_NAME:
return equal(m_value.string, other.m_value.string);
case CSS_COUNTER:
return m_value.counter && other.m_value.counter && m_value.counter->equals(*other.m_value.counter);
@@ -1337,4 +1411,31 @@ bool CSSPrimitiveValue::equals(const CSSPrimitiveValue& other) const
return false;
}
+void CSSPrimitiveValue::traceAfterDispatch(Visitor* visitor)
+{
+ switch (m_primitiveUnitType) {
+ case CSS_COUNTER:
+ visitor->trace(m_value.counter);
+ break;
+ case CSS_RECT:
+ visitor->trace(m_value.rect);
+ break;
+ case CSS_QUAD:
+ visitor->trace(m_value.quad);
+ break;
+ case CSS_PAIR:
+ visitor->trace(m_value.pair);
+ break;
+ case CSS_CALC:
+ visitor->trace(m_value.calc);
+ break;
+ case CSS_SHAPE:
+ visitor->trace(m_value.shape);
+ break;
+ default:
+ break;
+ }
+ CSSValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.h b/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.h
index 65b1cfbf66f..76846ab687d 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValue.h
@@ -22,8 +22,8 @@
#ifndef CSSPrimitiveValue_h
#define CSSPrimitiveValue_h
-#include "CSSPropertyNames.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSPropertyNames.h"
+#include "core/CSSValueKeywords.h"
#include "core/css/CSSValue.h"
#include "platform/graphics/Color.h"
#include "wtf/Forward.h"
@@ -38,6 +38,7 @@ class CSSToLengthConversionData;
class Counter;
class ExceptionState;
class Length;
+class LengthSize;
class Pair;
class Quad;
class RGBColor;
@@ -64,9 +65,13 @@ template<> inline float roundForImpreciseConversion(double value)
return static_cast<float>(value);
}
+// CSSPrimitiveValues are immutable. This class has manual ref-counting
+// of unioned types and does not have the code necessary
+// to handle any kind of mutations. All DOM-exposed "setters" just throw
+// exceptions.
class CSSPrimitiveValue : public CSSValue {
public:
- enum UnitTypes {
+ enum UnitType {
CSS_UNKNOWN = 0,
CSS_NUMBER = 1,
CSS_PERCENTAGE = 2,
@@ -130,13 +135,31 @@ public:
CSS_CALC = 113,
CSS_CALC_PERCENTAGE_WITH_NUMBER = 114,
CSS_CALC_PERCENTAGE_WITH_LENGTH = 115,
- CSS_VARIABLE_NAME = 116,
CSS_PROPERTY_ID = 117,
CSS_VALUE_ID = 118
};
- // This enum follows the CSSParser::Units enum augmented with UNIT_FREQUENCY for frequencies.
+ enum LengthUnitType {
+ UnitTypePixels = 0,
+ UnitTypePercentage,
+ UnitTypeFontSize,
+ UnitTypeFontXSize,
+ UnitTypeRootFontSize,
+ UnitTypeZeroCharacterWidth,
+ UnitTypeViewportWidth,
+ UnitTypeViewportHeight,
+ UnitTypeViewportMin,
+ UnitTypeViewportMax,
+
+ // This value must come after the last length unit type to enable iteration over the length unit types.
+ LengthUnitTypeCount,
+ };
+
+ typedef Vector<double, CSSPrimitiveValue::LengthUnitTypeCount> CSSLengthArray;
+ void accumulateLengthArray(CSSLengthArray&, double multiplier = 1) const;
+
+ // This enum follows the BisonCSSParser::Units enum augmented with UNIT_FREQUENCY for frequencies.
enum UnitCategory {
UNumber,
UPercent,
@@ -144,11 +167,12 @@ public:
UAngle,
UTime,
UFrequency,
- UViewportPercentageLength,
UResolution,
UOther
};
- static UnitCategory unitCategory(CSSPrimitiveValue::UnitTypes);
+ static UnitCategory unitCategory(UnitType);
+
+ static UnitType fromName(const String& unit);
bool isAngle() const
{
@@ -167,11 +191,13 @@ public:
|| m_primitiveUnitType == CSS_REMS
|| m_primitiveUnitType == CSS_CHS;
}
- bool isLength() const
+ bool isViewportPercentageLength() const { return isViewportPercentageLength(static_cast<UnitType>(m_primitiveUnitType)); }
+ static bool isViewportPercentageLength(UnitType type) { return type >= CSS_VW && type <= CSS_VMAX; }
+ static bool isLength(UnitType type)
{
- unsigned short type = primitiveType();
- return (type >= CSS_EMS && type <= CSS_PC) || type == CSS_REMS || type == CSS_CHS;
+ return (type >= CSS_EMS && type <= CSS_PC) || type == CSS_REMS || type == CSS_CHS || isViewportPercentageLength(type);
}
+ bool isLength() const { return isLength(primitiveType()); }
bool isNumber() const { return primitiveType() == CSS_NUMBER; }
bool isPercentage() const { return primitiveType() == CSS_PERCENTAGE; }
bool isPx() const { return primitiveType() == CSS_PX; }
@@ -184,49 +210,67 @@ public:
bool isCalculated() const { return m_primitiveUnitType == CSS_CALC; }
bool isCalculatedPercentageWithNumber() const { return primitiveType() == CSS_CALC_PERCENTAGE_WITH_NUMBER; }
bool isCalculatedPercentageWithLength() const { return primitiveType() == CSS_CALC_PERCENTAGE_WITH_LENGTH; }
- bool isDotsPerInch() const { return primitiveType() == CSS_DPI; }
- bool isDotsPerPixel() const { return primitiveType() == CSS_DPPX; }
- bool isDotsPerCentimeter() const { return primitiveType() == CSS_DPCM; }
- bool isResolution() const
- {
- unsigned short type = primitiveType();
- return type >= CSS_DPPX && type <= CSS_DPCM;
- }
- bool isVariableName() const { return primitiveType() == CSS_VARIABLE_NAME; }
- bool isViewportPercentageLength() const { return m_primitiveUnitType >= CSS_VW && m_primitiveUnitType <= CSS_VMAX; }
+ static bool isDotsPerInch(UnitType type) { return type == CSS_DPI; }
+ static bool isDotsPerPixel(UnitType type) { return type == CSS_DPPX; }
+ static bool isDotsPerCentimeter(UnitType type) { return type == CSS_DPCM; }
+ static bool isResolution(UnitType type) { return type >= CSS_DPPX && type <= CSS_DPCM; }
bool isFlex() const { return primitiveType() == CSS_FR; }
bool isValueID() const { return m_primitiveUnitType == CSS_VALUE_ID; }
bool colorIsDerivedFromElement() const;
- static PassRefPtr<CSSPrimitiveValue> createIdentifier(CSSValueID valueID) { return adoptRef(new CSSPrimitiveValue(valueID)); }
- static PassRefPtr<CSSPrimitiveValue> createIdentifier(CSSPropertyID propertyID) { return adoptRef(new CSSPrimitiveValue(propertyID)); }
- static PassRefPtr<CSSPrimitiveValue> createParserOperator(int parserOperator) { return adoptRef(new CSSPrimitiveValue(parserOperator)); }
- static PassRefPtr<CSSPrimitiveValue> createColor(unsigned rgbValue) { return adoptRef(new CSSPrimitiveValue(rgbValue)); }
- static PassRefPtr<CSSPrimitiveValue> create(double value, UnitTypes type) { return adoptRef(new CSSPrimitiveValue(value, type)); }
- static PassRefPtr<CSSPrimitiveValue> create(const String& value, UnitTypes type) { return adoptRef(new CSSPrimitiveValue(value, type)); }
- static PassRefPtr<CSSPrimitiveValue> create(const Length& value, float zoom) { return adoptRef(new CSSPrimitiveValue(value, zoom)); }
-
- template<typename T> static PassRefPtr<CSSPrimitiveValue> create(T value)
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createIdentifier(CSSValueID valueID)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(valueID));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createIdentifier(CSSPropertyID propertyID)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(propertyID));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createParserOperator(int parserOperator)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(parserOperator, CSS_PARSER_OPERATOR));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createColor(unsigned rgbValue)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(rgbValue, CSS_RGBCOLOR));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> create(double value, UnitType type)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(value, type));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> create(const String& value, UnitType type)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(value, type));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> create(const Length& value, float zoom)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(value, zoom));
+ }
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> create(const LengthSize& value, const RenderStyle& style)
+ {
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(value, style));
+ }
+ template<typename T> static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> create(T value)
{
- return adoptRef(new CSSPrimitiveValue(value));
+ return adoptRefWillBeNoop(new CSSPrimitiveValue(value));
}
// This value is used to handle quirky margins in reflow roots (body, td, and th) like WinIE.
// The basic idea is that a stylesheet can use the value __qem (for quirky em) instead of em.
// When the quirky value is used, if you're in quirks mode, the margin will collapse away
// inside a table cell.
- static PassRefPtr<CSSPrimitiveValue> createAllowingMarginQuirk(double value, UnitTypes type)
+ static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createAllowingMarginQuirk(double value, UnitType type)
{
CSSPrimitiveValue* quirkValue = new CSSPrimitiveValue(value, type);
quirkValue->m_isQuirkValue = true;
- return adoptRef(quirkValue);
+ return adoptRefWillBeNoop(quirkValue);
}
~CSSPrimitiveValue();
void cleanup();
- unsigned short primitiveType() const;
+ UnitType primitiveType() const;
double computeDegrees();
@@ -259,24 +303,22 @@ public:
// Converts to a Length, mapping various unit types appropriately.
template<int> Length convertToLength(const CSSToLengthConversionData&);
- // use with care!!!
- void setPrimitiveType(unsigned short type) { m_primitiveUnitType = type; }
-
- double getDoubleValue(unsigned short unitType, ExceptionState&) const;
- double getDoubleValue(unsigned short unitType) const;
+ double getDoubleValue(UnitType, ExceptionState&) const;
+ double getDoubleValue(UnitType) const;
double getDoubleValue() const;
+ // setFloatValue(..., ExceptionState&) and setStringValue() must use unsigned short instead of UnitType to match IDL bindings.
void setFloatValue(unsigned short unitType, double floatValue, ExceptionState&);
- float getFloatValue(unsigned short unitType, ExceptionState& exceptionState) const { return getValue<float>(unitType, exceptionState); }
- float getFloatValue(unsigned short unitType) const { return getValue<float>(unitType); }
+ float getFloatValue(unsigned short unitType, ExceptionState& exceptionState) const { return getValue<float>(static_cast<UnitType>(unitType), exceptionState); }
+ float getFloatValue(UnitType type) const { return getValue<float>(type); }
float getFloatValue() const { return getValue<float>(); }
- int getIntValue(unsigned short unitType, ExceptionState& exceptionState) const { return getValue<int>(unitType, exceptionState); }
- int getIntValue(unsigned short unitType) const { return getValue<int>(unitType); }
+ int getIntValue(UnitType type, ExceptionState& exceptionState) const { return getValue<int>(type, exceptionState); }
+ int getIntValue(UnitType type) const { return getValue<int>(type); }
int getIntValue() const { return getValue<int>(); }
- template<typename T> inline T getValue(unsigned short unitType, ExceptionState& exceptionState) const { return clampTo<T>(getDoubleValue(unitType, exceptionState)); }
- template<typename T> inline T getValue(unsigned short unitType) const { return clampTo<T>(getDoubleValue(unitType)); }
+ template<typename T> inline T getValue(UnitType type, ExceptionState& exceptionState) const { return clampTo<T>(getDoubleValue(type, exceptionState)); }
+ template<typename T> inline T getValue(UnitType type) const { return clampTo<T>(getDoubleValue(type)); }
template<typename T> inline T getValue() const { return clampTo<T>(getDoubleValue()); }
void setStringValue(unsigned short stringType, const String& stringValue, ExceptionState&);
@@ -292,7 +334,7 @@ public:
Quad* getQuadValue(ExceptionState&) const;
Quad* getQuadValue() const { return m_primitiveUnitType != CSS_QUAD ? 0 : m_value.quad; }
- PassRefPtr<RGBColor> getRGBColorValue(ExceptionState&) const;
+ PassRefPtrWillBeRawPtr<RGBColor> getRGBColorValue(ExceptionState&) const;
RGBA32 getRGBA32Value() const { return m_primitiveUnitType != CSS_RGBCOLOR ? 0 : m_value.rgbcolor; }
Pair* getPairValue(ExceptionState&) const;
@@ -307,47 +349,44 @@ public:
template<typename T> inline operator T() const; // Defined in CSSPrimitiveValueMappings.h
+ static const char* unitTypeToString(UnitType);
String customCSSText(CSSTextFormattingFlags = QuoteCSSStringIfNeeded) const;
- String customSerializeResolvingVariables(const HashMap<AtomicString, String>&) const;
- bool hasVariableReference() const;
bool isQuirkValue() { return m_isQuirkValue; }
- void addSubresourceStyleURLs(ListHashSet<KURL>&, const StyleSheetContents*) const;
-
- Length viewportPercentageLength();
-
- PassRefPtr<CSSPrimitiveValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> cloneForCSSOM() const;
void setCSSOMSafe() { m_isCSSOMSafe = true; }
bool equals(const CSSPrimitiveValue&) const;
- static UnitTypes canonicalUnitTypeForCategory(UnitCategory);
- static double conversionToCanonicalUnitsScaleFactor(unsigned short unitType);
+ void traceAfterDispatch(Visitor*);
+
+ static UnitType canonicalUnitTypeForCategory(UnitCategory);
+ static double conversionToCanonicalUnitsScaleFactor(UnitType);
+
+ // Returns true and populates lengthUnitType, if unitType is a length unit. Otherwise, returns false.
+ static bool unitTypeToLengthUnitType(UnitType, LengthUnitType&);
+ static UnitType lengthUnitTypeToUnitType(LengthUnitType);
private:
CSSPrimitiveValue(CSSValueID);
CSSPrimitiveValue(CSSPropertyID);
- // FIXME: int vs. unsigned overloading is too subtle to distinguish the color and operator cases.
- CSSPrimitiveValue(int parserOperator);
- CSSPrimitiveValue(unsigned color); // RGB value
- CSSPrimitiveValue(const Length& length)
- : CSSValue(PrimitiveClass)
- {
- init(length);
- }
+ // int vs. unsigned is too subtle to distinguish types, so require a UnitType.
+ CSSPrimitiveValue(int parserOperator, UnitType);
+ CSSPrimitiveValue(unsigned color, UnitType); // RGB value
CSSPrimitiveValue(const Length&, float zoom);
- CSSPrimitiveValue(const String&, UnitTypes);
- CSSPrimitiveValue(double, UnitTypes);
+ CSSPrimitiveValue(const LengthSize&, const RenderStyle&);
+ CSSPrimitiveValue(const String&, UnitType);
+ CSSPrimitiveValue(double, UnitType);
template<typename T> CSSPrimitiveValue(T); // Defined in CSSPrimitiveValueMappings.h
template<typename T> CSSPrimitiveValue(T* val)
: CSSValue(PrimitiveClass)
{
- init(PassRefPtr<T>(val));
+ init(PassRefPtrWillBeRawPtr<T>(val));
}
- template<typename T> CSSPrimitiveValue(PassRefPtr<T> val)
+ template<typename T> CSSPrimitiveValue(PassRefPtrWillBeRawPtr<T> val)
: CSSValue(PrimitiveClass)
{
init(val);
@@ -358,13 +397,14 @@ private:
template<typename T> operator T*(); // compile-time guard
void init(const Length&);
- void init(PassRefPtr<Counter>);
- void init(PassRefPtr<Rect>);
- void init(PassRefPtr<Pair>);
- void init(PassRefPtr<Quad>);
- void init(PassRefPtr<CSSBasicShape>);
- void init(PassRefPtr<CSSCalcValue>);
- bool getDoubleValueInternal(UnitTypes targetUnitType, double* result) const;
+ void init(const LengthSize&, const RenderStyle&);
+ void init(PassRefPtrWillBeRawPtr<Counter>);
+ void init(PassRefPtrWillBeRawPtr<Rect>);
+ void init(PassRefPtrWillBeRawPtr<Pair>);
+ void init(PassRefPtrWillBeRawPtr<Quad>);
+ void init(PassRefPtrWillBeRawPtr<CSSBasicShape>);
+ void init(PassRefPtrWillBeRawPtr<CSSCalcValue>);
+ bool getDoubleValueInternal(UnitType targetUnitType, double* result) const;
double computeLengthDouble(const CSSToLengthConversionData&);
@@ -374,16 +414,19 @@ private:
int parserOperator;
double num;
StringImpl* string;
- Counter* counter;
- Rect* rect;
- Quad* quad;
unsigned rgbcolor;
- Pair* pair;
+ // FIXME: oilpan: Should be members, but no support for members in unions. Just trace the raw ptr for now.
CSSBasicShape* shape;
CSSCalcValue* calc;
+ Counter* counter;
+ Pair* pair;
+ Rect* rect;
+ Quad* quad;
} m_value;
};
+typedef CSSPrimitiveValue::CSSLengthArray CSSLengthArray;
+
DEFINE_CSS_VALUE_TYPE_CASTS(CSSPrimitiveValue, isPrimitiveValue());
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValueMappings.h b/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValueMappings.h
index 3f386133793..c2bf9d8e714 100755..100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValueMappings.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPrimitiveValueMappings.h
@@ -30,7 +30,7 @@
#ifndef CSSPrimitiveValueMappings_h
#define CSSPrimitiveValueMappings_h
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
#include "core/css/CSSCalculationValue.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSReflectionDirection.h"
@@ -45,6 +45,7 @@
#include "platform/fonts/TextRenderingMode.h"
#include "platform/graphics/GraphicsTypes.h"
#include "platform/graphics/Path.h"
+#include "platform/scroll/ScrollableArea.h"
#include "platform/text/TextDirection.h"
#include "platform/text/UnicodeBidi.h"
#include "platform/text/WritingMode.h"
@@ -61,11 +62,8 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(short i)
template<> inline CSSPrimitiveValue::operator short() const
{
- if (m_primitiveUnitType == CSS_NUMBER)
- return clampTo<short>(m_value.num);
-
- ASSERT_NOT_REACHED();
- return 0;
+ ASSERT(isNumber());
+ return clampTo<short>(getDoubleValue());
}
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(unsigned short i)
@@ -77,29 +75,20 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(unsigned short i)
template<> inline CSSPrimitiveValue::operator unsigned short() const
{
- if (m_primitiveUnitType == CSS_NUMBER)
- return clampTo<unsigned short>(m_value.num);
-
- ASSERT_NOT_REACHED();
- return 0;
+ ASSERT(isNumber());
+ return clampTo<unsigned short>(getDoubleValue());
}
template<> inline CSSPrimitiveValue::operator int() const
{
- if (m_primitiveUnitType == CSS_NUMBER)
- return clampTo<int>(m_value.num);
-
- ASSERT_NOT_REACHED();
- return 0;
+ ASSERT(isNumber());
+ return clampTo<int>(getDoubleValue());
}
template<> inline CSSPrimitiveValue::operator unsigned() const
{
- if (m_primitiveUnitType == CSS_NUMBER)
- return clampTo<unsigned>(m_value.num);
-
- ASSERT_NOT_REACHED();
- return 0;
+ ASSERT(isNumber());
+ return clampTo<unsigned>(getDoubleValue());
}
@@ -112,11 +101,8 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(float i)
template<> inline CSSPrimitiveValue::operator float() const
{
- if (m_primitiveUnitType == CSS_NUMBER)
- return clampTo<float>(m_value.num);
-
- ASSERT_NOT_REACHED();
- return 0.0f;
+ ASSERT(isNumber());
+ return clampTo<float>(getDoubleValue());
}
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineClampValue i)
@@ -460,18 +446,6 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ControlPart e)
case MediaMuteButtonPart:
m_value.valueID = CSSValueMediaMuteButton;
break;
- case MediaSeekBackButtonPart:
- m_value.valueID = CSSValueMediaSeekBackButton;
- break;
- case MediaSeekForwardButtonPart:
- m_value.valueID = CSSValueMediaSeekForwardButton;
- break;
- case MediaRewindButtonPart:
- m_value.valueID = CSSValueMediaRewindButton;
- break;
- case MediaReturnToRealtimeButtonPart:
- m_value.valueID = CSSValueMediaReturnToRealtimeButton;
- break;
case MediaToggleClosedCaptionsButtonPart:
m_value.valueID = CSSValueMediaToggleClosedCaptionsButton;
break;
@@ -487,9 +461,6 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ControlPart e)
case MediaVolumeSliderPart:
m_value.valueID = CSSValueMediaVolumeSlider;
break;
- case MediaVolumeSliderMuteButtonPart:
- m_value.valueID = CSSValueMediaVolumeSliderMuteButton;
- break;
case MediaVolumeSliderThumbPart:
m_value.valueID = CSSValueMediaVolumeSliderthumb;
break;
@@ -580,11 +551,6 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ControlPart e)
case CapsLockIndicatorPart:
m_value.valueID = CSSValueCapsLockIndicator;
break;
- case InputSpeechButtonPart:
-#if ENABLE(INPUT_SPEECH)
- m_value.valueID = CSSValueWebkitInputSpeechButton;
-#endif
- break;
}
}
@@ -1150,11 +1116,11 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ECursor e)
case CURSOR_NOT_ALLOWED:
m_value.valueID = CSSValueNotAllowed;
break;
- case CURSOR_WEBKIT_ZOOM_IN:
- m_value.valueID = CSSValueWebkitZoomIn;
+ case CURSOR_ZOOM_IN:
+ m_value.valueID = CSSValueZoomIn;
break;
- case CURSOR_WEBKIT_ZOOM_OUT:
- m_value.valueID = CSSValueWebkitZoomOut;
+ case CURSOR_ZOOM_OUT:
+ m_value.valueID = CSSValueZoomOut;
break;
case CURSOR_E_RESIZE:
m_value.valueID = CSSValueEResize;
@@ -1222,11 +1188,18 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ECursor e)
template<> inline CSSPrimitiveValue::operator ECursor() const
{
ASSERT(isValueID());
- if (m_value.valueID == CSSValueCopy)
+ switch (m_value.valueID) {
+ case CSSValueCopy:
return CURSOR_COPY;
- if (m_value.valueID == CSSValueNone)
+ case CSSValueWebkitZoomIn:
+ return CURSOR_ZOOM_IN;
+ case CSSValueWebkitZoomOut:
+ return CURSOR_ZOOM_OUT;
+ case CSSValueNone:
return CURSOR_NONE;
- return static_cast<ECursor>(m_value.valueID - CSSValueAuto);
+ default:
+ return static_cast<ECursor>(m_value.valueID - CSSValueAuto);
+ }
}
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EDisplay e)
@@ -1346,56 +1319,6 @@ template<> inline CSSPrimitiveValue::operator EEmptyCell() const
return SHOW;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EAlignItems e)
- : CSSValue(PrimitiveClass)
-{
- m_primitiveUnitType = CSS_VALUE_ID;
- switch (e) {
- case AlignAuto:
- m_value.valueID = CSSValueAuto;
- break;
- case AlignFlexStart:
- m_value.valueID = CSSValueFlexStart;
- break;
- case AlignFlexEnd:
- m_value.valueID = CSSValueFlexEnd;
- break;
- case AlignCenter:
- m_value.valueID = CSSValueCenter;
- break;
- case AlignStretch:
- m_value.valueID = CSSValueStretch;
- break;
- case AlignBaseline:
- m_value.valueID = CSSValueBaseline;
- break;
- }
-}
-
-template<> inline CSSPrimitiveValue::operator EAlignItems() const
-{
- ASSERT(isValueID());
- switch (m_value.valueID) {
- case CSSValueAuto:
- return AlignAuto;
- case CSSValueFlexStart:
- return AlignFlexStart;
- case CSSValueFlexEnd:
- return AlignFlexEnd;
- case CSSValueCenter:
- return AlignCenter;
- case CSSValueStretch:
- return AlignStretch;
- case CSSValueBaseline:
- return AlignBaseline;
- default:
- break;
- }
-
- ASSERT_NOT_REACHED();
- return AlignFlexStart;
-}
-
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EJustifyContent e)
: CSSValue(PrimitiveClass)
{
@@ -2014,36 +1937,6 @@ template<> inline CSSPrimitiveValue::operator EMarqueeBehavior() const
return MNONE;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(RegionFragment e)
- : CSSValue(PrimitiveClass)
-{
- m_primitiveUnitType = CSS_VALUE_ID;
- switch (e) {
- case AutoRegionFragment:
- m_value.valueID = CSSValueAuto;
- break;
- case BreakRegionFragment:
- m_value.valueID = CSSValueBreak;
- break;
- }
-}
-
-template<> inline CSSPrimitiveValue::operator RegionFragment() const
-{
- ASSERT(isValueID());
- switch (m_value.valueID) {
- case CSSValueAuto:
- return AutoRegionFragment;
- case CSSValueBreak:
- return BreakRegionFragment;
- default:
- break;
- }
-
- ASSERT_NOT_REACHED();
- return AutoRegionFragment;
-}
-
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EMarqueeDirection e)
: CSSValue(PrimitiveClass)
{
@@ -3591,15 +3484,15 @@ template<> inline CSSPrimitiveValue::operator FontWeight() const
return FontWeightNormal;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontItalic italic)
+template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontStyle italic)
: CSSValue(PrimitiveClass)
{
m_primitiveUnitType = CSS_VALUE_ID;
switch (italic) {
- case FontItalicOff:
+ case FontStyleNormal:
m_value.valueID = CSSValueNormal;
return;
- case FontItalicOn:
+ case FontStyleItalic:
m_value.valueID = CSSValueItalic;
return;
}
@@ -3608,32 +3501,32 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontItalic italic)
m_value.valueID = CSSValueNormal;
}
-template<> inline CSSPrimitiveValue::operator FontItalic() const
+template<> inline CSSPrimitiveValue::operator FontStyle() const
{
ASSERT(isValueID());
switch (m_value.valueID) {
case CSSValueOblique:
// FIXME: oblique is the same as italic for the moment...
case CSSValueItalic:
- return FontItalicOn;
+ return FontStyleItalic;
case CSSValueNormal:
- return FontItalicOff;
+ return FontStyleNormal;
default:
break;
}
ASSERT_NOT_REACHED();
- return FontItalicOff;
+ return FontStyleNormal;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontSmallCaps smallCaps)
+template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontVariant smallCaps)
: CSSValue(PrimitiveClass)
{
m_primitiveUnitType = CSS_VALUE_ID;
switch (smallCaps) {
- case FontSmallCapsOff:
+ case FontVariantNormal:
m_value.valueID = CSSValueNormal;
return;
- case FontSmallCapsOn:
+ case FontVariantSmallCaps:
m_value.valueID = CSSValueSmallCaps;
return;
}
@@ -3642,19 +3535,19 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(FontSmallCaps smallCaps)
m_value.valueID = CSSValueNormal;
}
-template<> inline CSSPrimitiveValue::operator FontSmallCaps() const
+template<> inline CSSPrimitiveValue::operator FontVariant() const
{
ASSERT(isValueID());
switch (m_value.valueID) {
case CSSValueSmallCaps:
- return FontSmallCapsOn;
+ return FontVariantSmallCaps;
case CSSValueNormal:
- return FontSmallCapsOff;
+ return FontVariantNormal;
default:
break;
}
ASSERT_NOT_REACHED();
- return FontSmallCapsOff;
+ return FontVariantNormal;
}
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(TextRenderingMode e)
@@ -3697,71 +3590,6 @@ template<> inline CSSPrimitiveValue::operator TextRenderingMode() const
return AutoTextRendering;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineSnap gridSnap)
- : CSSValue(PrimitiveClass)
-{
- m_primitiveUnitType = CSS_VALUE_ID;
- switch (gridSnap) {
- case LineSnapNone:
- m_value.valueID = CSSValueNone;
- break;
- case LineSnapBaseline:
- m_value.valueID = CSSValueBaseline;
- break;
- case LineSnapContain:
- m_value.valueID = CSSValueContain;
- break;
- }
-}
-
-template<> inline CSSPrimitiveValue::operator LineSnap() const
-{
- ASSERT(isValueID());
- switch (m_value.valueID) {
- case CSSValueNone:
- return LineSnapNone;
- case CSSValueBaseline:
- return LineSnapBaseline;
- case CSSValueContain:
- return LineSnapContain;
- default:
- break;
- }
-
- ASSERT_NOT_REACHED();
- return LineSnapNone;
-}
-
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LineAlign lineAlign)
- : CSSValue(PrimitiveClass)
-{
- m_primitiveUnitType = CSS_VALUE_ID;
- switch (lineAlign) {
- case LineAlignNone:
- m_value.valueID = CSSValueNone;
- break;
- case LineAlignEdges:
- m_value.valueID = CSSValueEdges;
- break;
- }
-}
-
-template<> inline CSSPrimitiveValue::operator LineAlign() const
-{
- ASSERT(isValueID());
- switch (m_value.valueID) {
- case CSSValueNone:
- return LineAlignNone;
- case CSSValueEdges:
- return LineAlignEdges;
- default:
- break;
- }
-
- ASSERT_NOT_REACHED();
- return LineAlignNone;
-}
-
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ESpeak e)
: CSSValue(PrimitiveClass)
{
@@ -4253,71 +4081,6 @@ template<> inline CSSPrimitiveValue::operator ETransformStyle3D() const
return TransformStyle3DFlat;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ColumnAxis e)
- : CSSValue(PrimitiveClass)
-{
- m_primitiveUnitType = CSS_VALUE_ID;
- switch (e) {
- case HorizontalColumnAxis:
- m_value.valueID = CSSValueHorizontal;
- break;
- case VerticalColumnAxis:
- m_value.valueID = CSSValueVertical;
- break;
- case AutoColumnAxis:
- m_value.valueID = CSSValueAuto;
- break;
- }
-}
-
-template<> inline CSSPrimitiveValue::operator ColumnAxis() const
-{
- ASSERT(isValueID());
- switch (m_value.valueID) {
- case CSSValueHorizontal:
- return HorizontalColumnAxis;
- case CSSValueVertical:
- return VerticalColumnAxis;
- case CSSValueAuto:
- return AutoColumnAxis;
- default:
- break;
- }
-
- ASSERT_NOT_REACHED();
- return AutoColumnAxis;
-}
-
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ColumnProgression e)
- : CSSValue(PrimitiveClass)
-{
- m_primitiveUnitType = CSS_VALUE_ID;
- switch (e) {
- case NormalColumnProgression:
- m_value.valueID = CSSValueNormal;
- break;
- case ReverseColumnProgression:
- m_value.valueID = CSSValueReverse;
- break;
- }
-}
-
-template<> inline CSSPrimitiveValue::operator ColumnProgression() const
-{
- ASSERT(isValueID());
- switch (m_value.valueID) {
- case CSSValueNormal:
- return NormalColumnProgression;
- case CSSValueReverse:
- return ReverseColumnProgression;
- default:
- break;
- }
-
- ASSERT_NOT_REACHED();
- return NormalColumnProgression;
-}
-
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(WrapFlow wrapFlow)
: CSSValue(PrimitiveClass)
{
@@ -4443,7 +4206,6 @@ enum LengthConversion {
template<int supported> Length CSSPrimitiveValue::convertToLength(const CSSToLengthConversionData& conversionData)
{
- ASSERT(!hasVariableReference());
if ((supported & FixedConversion) && isLength())
return computeLength<Length>(conversionData);
if ((supported & PercentConversion) && isPercentage())
@@ -4452,9 +4214,8 @@ template<int supported> Length CSSPrimitiveValue::convertToLength(const CSSToLen
return Length(Auto);
if ((supported & FixedConversion) && (supported & PercentConversion) && isCalculated())
return Length(cssCalcValue()->toCalcValue(conversionData));
- if ((supported & FixedConversion) && isViewportPercentageLength())
- return viewportPercentageLength();
- return Length(Undefined);
+ ASSERT_NOT_REACHED();
+ return Length(0, Fixed);
}
template<> inline CSSPrimitiveValue::CSSPrimitiveValue(EBufferedRendering e)
@@ -4878,6 +4639,8 @@ template<> inline CSSPrimitiveValue::operator TouchAction() const
return TouchActionPanX;
case CSSValuePanY:
return TouchActionPanY;
+ case CSSValueManipulation:
+ return TouchActionPanX | TouchActionPanY | TouchActionPinchZoom;
default:
break;
}
@@ -4945,11 +4708,11 @@ template<> inline CSSPrimitiveValue::operator TouchActionDelay() const
return TouchActionDelayNone;
}
-template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LayoutBox layoutBox)
+template<> inline CSSPrimitiveValue::CSSPrimitiveValue(CSSBoxType cssBox)
: CSSValue(PrimitiveClass)
{
m_primitiveUnitType = CSS_VALUE_ID;
- switch (layoutBox) {
+ switch (cssBox) {
case MarginBox:
m_value.valueID = CSSValueMarginBox;
break;
@@ -4962,10 +4725,13 @@ template<> inline CSSPrimitiveValue::CSSPrimitiveValue(LayoutBox layoutBox)
case ContentBox:
m_value.valueID = CSSValueContentBox;
break;
+ case BoxMissing:
+ // The missing box should convert to a null primitive value.
+ ASSERT_NOT_REACHED();
}
}
-template<> inline CSSPrimitiveValue::operator LayoutBox() const
+template<> inline CSSPrimitiveValue::operator CSSBoxType() const
{
switch (getValueID()) {
case CSSValueMarginBox:
@@ -4983,6 +4749,147 @@ template<> inline CSSPrimitiveValue::operator LayoutBox() const
return ContentBox;
}
+template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ItemPosition itemPosition)
+ : CSSValue(PrimitiveClass)
+{
+ m_primitiveUnitType = CSS_VALUE_ID;
+ switch (itemPosition) {
+ case ItemPositionAuto:
+ m_value.valueID = CSSValueAuto;
+ break;
+ case ItemPositionStretch:
+ m_value.valueID = CSSValueStretch;
+ break;
+ case ItemPositionBaseline:
+ m_value.valueID = CSSValueBaseline;
+ break;
+ case ItemPositionCenter:
+ m_value.valueID = CSSValueCenter;
+ break;
+ case ItemPositionStart:
+ m_value.valueID = CSSValueStart;
+ break;
+ case ItemPositionEnd:
+ m_value.valueID = CSSValueEnd;
+ break;
+ case ItemPositionSelfStart:
+ m_value.valueID = CSSValueSelfStart;
+ break;
+ case ItemPositionSelfEnd:
+ m_value.valueID = CSSValueSelfEnd;
+ break;
+ case ItemPositionFlexStart:
+ m_value.valueID = CSSValueFlexStart;
+ break;
+ case ItemPositionFlexEnd:
+ m_value.valueID = CSSValueFlexEnd;
+ break;
+ case ItemPositionLeft:
+ m_value.valueID = CSSValueLeft;
+ break;
+ case ItemPositionRight:
+ m_value.valueID = CSSValueRight;
+ break;
+ }
+}
+
+template<> inline CSSPrimitiveValue::operator ItemPosition() const
+{
+ switch (m_value.valueID) {
+ case CSSValueAuto:
+ return ItemPositionAuto;
+ case CSSValueStretch:
+ return ItemPositionStretch;
+ case CSSValueBaseline:
+ return ItemPositionBaseline;
+ case CSSValueCenter:
+ return ItemPositionCenter;
+ case CSSValueStart:
+ return ItemPositionStart;
+ case CSSValueEnd:
+ return ItemPositionEnd;
+ case CSSValueSelfStart:
+ return ItemPositionSelfStart;
+ case CSSValueSelfEnd:
+ return ItemPositionSelfEnd;
+ case CSSValueFlexStart:
+ return ItemPositionFlexStart;
+ case CSSValueFlexEnd:
+ return ItemPositionFlexEnd;
+ case CSSValueLeft:
+ return ItemPositionLeft;
+ case CSSValueRight:
+ return ItemPositionRight;
+ default:
+ break;
+ }
+ ASSERT_NOT_REACHED();
+ return ItemPositionAuto;
+}
+
+template<> inline CSSPrimitiveValue::CSSPrimitiveValue(OverflowAlignment overflowAlignment)
+ : CSSValue(PrimitiveClass)
+{
+ m_primitiveUnitType = CSS_VALUE_ID;
+ switch (overflowAlignment) {
+ case OverflowAlignmentDefault:
+ m_value.valueID = CSSValueDefault;
+ break;
+ case OverflowAlignmentTrue:
+ m_value.valueID = CSSValueTrue;
+ break;
+ case OverflowAlignmentSafe:
+ m_value.valueID = CSSValueSafe;
+ break;
+ }
+}
+
+template<> inline CSSPrimitiveValue::operator OverflowAlignment() const
+{
+ switch (m_value.valueID) {
+ case CSSValueTrue:
+ return OverflowAlignmentTrue;
+ case CSSValueSafe:
+ return OverflowAlignmentSafe;
+ default:
+ break;
+ }
+ ASSERT_NOT_REACHED();
+ return OverflowAlignmentTrue;
+}
+
+template<> inline CSSPrimitiveValue::CSSPrimitiveValue(ScrollBehavior behavior)
+ : CSSValue(PrimitiveClass)
+{
+ m_primitiveUnitType = CSS_VALUE_ID;
+ switch (behavior) {
+ case ScrollBehaviorInstant:
+ m_value.valueID = CSSValueInstant;
+ break;
+ case ScrollBehaviorSmooth:
+ m_value.valueID = CSSValueSmooth;
+ break;
+ case ScrollBehaviorAuto:
+ // Behavior 'auto' is only allowed in ScrollOptions arguments passed to
+ // CSSOM scroll APIs.
+ ASSERT_NOT_REACHED();
+ }
+}
+
+template<> inline CSSPrimitiveValue::operator ScrollBehavior() const
+{
+ switch (getValueID()) {
+ case CSSValueInstant:
+ return ScrollBehaviorInstant;
+ case CSSValueSmooth:
+ return ScrollBehaviorSmooth;
+ default:
+ break;
+ }
+ ASSERT_NOT_REACHED();
+ return ScrollBehaviorInstant;
+}
+
}
#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSProperties.in b/chromium/third_party/WebKit/Source/core/css/CSSProperties.in
index 26318517545..ef861db7d13 100755..100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSProperties.in
+++ b/chromium/third_party/WebKit/Source/core/css/CSSProperties.in
@@ -1,10 +1,12 @@
// FIXME: When we have all the properties using the new StyleBuilder, we
// should use this for make_css_property_names.py
+// Note that type_name is currently only used for non-custom value application
+// and when explicitly referred to in generated applicators.
// Note: Mandatory blank line to skip parameter parsing phase
align-content
-align-items
-align-self type_name=EAlignItems
+align-items custom_value
+align-self custom_value
background-attachment custom_all
background-blend-mode custom_all
background-clip custom_all
@@ -45,6 +47,7 @@ caption-side
clear
clip custom_all
color custom_all
+content custom_all
counter-increment custom_all
counter-reset custom_all
cursor custom_all
@@ -57,17 +60,30 @@ flex-grow type_name=float
flex-shrink type_name=float
flex-wrap
float type_name=EFloat, name_for_methods=Floating
+font custom_all
font-family custom_all
-font-kerning custom_all
+font-kerning font, type_name=FontDescription::Kerning, name_for_methods=Kerning
font-size custom_all
-font-style custom_all
-font-variant custom_all
+font-style font, type_name=FontStyle, name_for_methods=Style
+font-variant font, type_name=FontVariant, name_for_methods=Variant
+font-variant-ligatures custom_all
font-weight custom_all
grid-auto-flow type_name=GridAutoFlow
+grid-auto-columns converter=convertGridTrackSize
+grid-auto-rows converter=convertGridTrackSize
+grid-column-start converter=convertGridPosition
+grid-column-end converter=convertGridPosition
+grid-row-start converter=convertGridPosition
+grid-row-end converter=convertGridPosition
+grid-template-columns custom_all
+grid-template-rows custom_all
+grid-template-areas custom_all
height type_name=Length, initial=initialSize, converter=convertLengthSizing
justify-content
image-rendering
+internal-callback custom_all
isolation
+justify-self custom_value
left type_name=Length, initial=initialOffset, converter=convertLengthOrAuto
letter-spacing type_name=float, initial=initialLetterWordSpacing, converter=convertSpacing
line-height getter=specifiedLineHeight, custom_value
@@ -103,15 +119,16 @@ padding-top type_name=Length, initial=initialPadding, converter=convertLength
page-break-after type_name=EPageBreak, initial=initialPageBreak
page-break-before type_name=EPageBreak, initial=initialPageBreak
page-break-inside type_name=EPageBreak, initial=initialPageBreak
+perspective custom_value
pointer-events
position
+quotes converter=convertQuotes
resize custom_value
right type_name=Length, initial=initialOffset, converter=convertLengthOrAuto
+scroll-behavior type_name=ScrollBehavior
shape-image-threshold type_name=float
-shape-inside type_name=ShapeValue*, custom_value
shape-margin type_name=Length, converter=convertLength
shape-outside type_name=ShapeValue*, custom_value
-shape-padding type_name=Length, converter=convertLength
size custom_all
speak
table-layout
@@ -125,18 +142,19 @@ text-decoration-style type_name=TextDecorationStyle
text-indent custom_all
text-justify type_name=TextJustify
text-overflow type_name=TextOverflow
-text-rendering custom_all
+text-rendering font, type_name=TextRenderingMode
text-shadow converter=convertShadow
text-transform
top type_name=Length, initial=initialOffset, converter=convertLengthOrAuto
touch-action type_name=TouchAction, custom_value
touch-action-delay type_name=TouchActionDelay, initial=initialTouchActionDelay
unicode-bidi
-vertical-align custom_value
+vertical-align custom_inherit, custom_value
visibility
white-space
widows type_name=short, custom_all
width type_name=Length, initial=initialSize, converter=convertLengthSizing
+will-change custom_all
word-break
word-spacing type_name=float, initial=initialLetterWordSpacing, converter=convertSpacing
// UAs must treat 'word-wrap' as an alternate name for the 'overflow-wrap' property. So using the same handlers.
@@ -152,8 +170,10 @@ z-index type_name=int, custom_all
-webkit-animation-name custom_all
-webkit-animation-play-state custom_all
-webkit-animation-timing-function custom_all
+-webkit-app-region custom_all
-webkit-appearance type_name=ControlPart
-webkit-aspect-ratio custom_all
+backface-visibility
-webkit-backface-visibility
-webkit-background-clip use_handlers_for=CSSPropertyBackgroundClip
-webkit-background-composite custom_all
@@ -172,32 +192,29 @@ z-index type_name=int, custom_all
-webkit-box-ordinal-group type_name=unsigned int
-webkit-box-orient
-webkit-box-pack
+-webkit-box-reflect converter=convertBoxReflect
-webkit-box-shadow use_handlers_for=CSSPropertyBoxShadow
-webkit-clip-path custom_value
--webkit-column-axis type_name=ColumnAxis
-webkit-column-break-after type_name=EPageBreak, initial=initialPageBreak
-webkit-column-break-before type_name=EPageBreak, initial=initialPageBreak
-webkit-column-break-inside type_name=EPageBreak, initial=initialPageBreak
-webkit-column-count type_name=unsigned short, custom_all
column-fill type_name=ColumnFill
-webkit-column-gap type_name=float, custom_all
--webkit-column-progression type_name=ColumnProgression
-webkit-column-rule-color custom_all
-webkit-column-rule-style type_name=EBorderStyle, initial=initialBorderStyle
-webkit-column-rule-width type_name=unsigned short, converter=convertLineWidth<unsigned short>
-webkit-column-span type_name=ColumnSpan
-webkit-column-width type_name=float, custom_all
--webkit-flow-from type_name=AtomicString, name_for_methods=RegionThread, converter=convertString<CSSValueNone>
--webkit-flow-into type_name=AtomicString, name_for_methods=FlowThread, converter=convertString<CSSValueNone>
--webkit-font-smoothing custom_all
--webkit-font-variant-ligatures custom_all
+-webkit-filter custom_value
+-webkit-font-feature-settings custom_all
+-webkit-font-smoothing font, type_name=FontSmoothingMode
-webkit-highlight type_name=AtomicString, converter=convertString<CSSValueNone>
-webkit-hyphenate-character type_name=AtomicString, name_for_methods=HyphenationString, converter=convertString<CSSValueAuto>
--webkit-line-align type_name=LineAlign
+-webkit-line-box-contain converter=convertLineBoxContain
-webkit-line-break type_name=LineBreak
-webkit-line-clamp type_name=LineClampValue
--webkit-line-grid type_name=AtomicString, converter=convertString<CSSValueNone>
--webkit-line-snap type_name=LineSnap
+-webkit-locale custom_value
-webkit-margin-after-collapse type_name=EMarginCollapse
-webkit-margin-before-collapse type_name=EMarginCollapse
-webkit-margin-bottom-collapse type_name=EMarginCollapse, name_for_methods=MarginAfterCollapse
@@ -221,27 +238,32 @@ column-fill type_name=ColumnFill
-webkit-mask-repeat-x custom_all
-webkit-mask-repeat-y custom_all
-webkit-mask-size custom_all
+-webkit-perspective custom_all
+perspective-origin custom_all
-webkit-perspective-origin custom_all
-webkit-perspective-origin-x type_name=Length, converter=convertLength
-webkit-perspective-origin-y type_name=Length, converter=convertLength
-webkit-print-color-adjust type_name=PrintColorAdjust
--webkit-region-break-after type_name=EPageBreak, initial=initialPageBreak
--webkit-region-break-before type_name=EPageBreak, initial=initialPageBreak
--webkit-region-break-inside type_name=EPageBreak, initial=initialPageBreak
--webkit-region-fragment type_name=RegionFragment
-webkit-rtl-ordering type_name=Order, getter=rtlOrdering, setter=setRTLOrdering, initial=initialRTLOrdering
-webkit-ruby-position type_name=RubyPosition
+-webkit-tap-highlight-color custom_value
-webkit-text-combine type_name=TextCombine
-webkit-text-emphasis-color custom_all
-webkit-text-emphasis-position type_name=TextEmphasisPosition
-webkit-text-emphasis-style custom_all
-webkit-text-fill-color custom_all
+-webkit-text-orientation custom_value
-webkit-text-security
-webkit-text-stroke-color custom_all
+-webkit-text-stroke-width converter=convertTextStrokeWidth
text-underline-position custom_value
+transform custom_value
+-webkit-transform use_handlers_for=CSSPropertyTransform
+transform-origin custom_all
-webkit-transform-origin-x type_name=Length, converter=convertLength
-webkit-transform-origin-y type_name=Length, converter=convertLength
-webkit-transform-origin-z type_name=float, converter=convertComputedLength<float>
+transform-style name_for_methods=TransformStyle3D
-webkit-transform-style name_for_methods=TransformStyle3D
-webkit-transition-delay custom_all
-webkit-transition-duration custom_all
@@ -252,8 +274,10 @@ text-underline-position custom_value
-webkit-user-select
-webkit-wrap-flow type_name=WrapFlow
-webkit-wrap-through type_name=WrapThrough
+-webkit-writing-mode custom_value
alignment-baseline svg
+baseline-shift svg, custom_value
buffered-rendering svg
clip-path svg, type_name=String, name_for_methods=ClipperResource, converter=convertFragmentIdentifier
clip-rule svg, type_name=WindRule
@@ -261,18 +285,26 @@ color-interpolation svg
color-interpolation-filters svg, type_name=EColorInterpolation
color-rendering svg
dominant-baseline svg
+fill svg, setter=setFillPaint, custom_all
fill-opacity svg, type_name=float, converter=convertNumberOrPercentage
fill-rule svg, type_name=WindRule
filter svg, type_name=String, name_for_methods=FilterResource, converter=convertFragmentIdentifier
+flood-color svg, converter=convertSVGColor
flood-opacity svg, type_name=float, converter=convertNumberOrPercentage
-kerning svg, type_name=SVGLength, converter=convertSVGLength
+glyph-orientation-horizontal svg, converter=convertGlyphOrientation
+glyph-orientation-vertical svg, custom_value
+lighting-color svg, converter=convertSVGColor
marker-start svg, type_name=String, name_for_methods=MarkerStartResource, converter=convertFragmentIdentifier
marker-mid svg, type_name=String, name_for_methods=MarkerMidResource, converter=convertFragmentIdentifier
marker-end svg, type_name=String, name_for_methods=MarkerEndResource, converter=convertFragmentIdentifier
mask svg, type_name=String, name_for_methods=MaskerResource, converter=convertFragmentIdentifier
mask-type svg
+paint-order svg, converter=convertPaintOrder
shape-rendering svg
+stop-color svg, converter=convertSVGColor
stop-opacity svg, type_name=float, converter=convertNumberOrPercentage
+stroke svg, setter=setStrokePaint, custom_all
+stroke-dasharray svg, name_for_methods=StrokeDashArray, converter=convertStrokeDasharray
stroke-dashoffset svg, type_name=SVGLength, name_for_methods=StrokeDashOffset, converter=convertSVGLength
stroke-linecap svg, type_name=LineCap, name_for_methods=CapStyle
stroke-linejoin svg, type_name=LineJoin, name_for_methods=JoinStyle
@@ -282,3 +314,70 @@ stroke-width svg, type_name=SVGLength, converter=convertSVGLength
text-anchor svg
vector-effect svg
writing-mode svg, type_name=SVGWritingMode
+
+-webkit-border-end-color direction_aware
+-webkit-border-end-style direction_aware
+-webkit-border-end-width direction_aware
+-webkit-border-start-color direction_aware
+-webkit-border-start-style direction_aware
+-webkit-border-start-width direction_aware
+-webkit-border-before-color direction_aware
+-webkit-border-before-style direction_aware
+-webkit-border-before-width direction_aware
+-webkit-border-after-color direction_aware
+-webkit-border-after-style direction_aware
+-webkit-border-after-width direction_aware
+-webkit-margin-end direction_aware
+-webkit-margin-start direction_aware
+-webkit-margin-before direction_aware
+-webkit-margin-after direction_aware
+-webkit-padding-end direction_aware
+-webkit-padding-start direction_aware
+-webkit-padding-before direction_aware
+-webkit-padding-after direction_aware
+-webkit-logical-width direction_aware
+-webkit-logical-height direction_aware
+-webkit-min-logical-width direction_aware
+-webkit-min-logical-height direction_aware
+-webkit-max-logical-width direction_aware
+-webkit-max-logical-height direction_aware
+
+// FIXME: We should look over these and see if some should actually be
+// marked as unreachable.
+animation-delay skip
+animation-direction skip
+animation-duration skip
+animation-fill-mode skip
+animation-iteration-count skip
+animation-name skip
+animation-play-state skip
+animation-timing-function skip
+transition-delay skip
+transition-duration skip
+transition-property skip
+transition-timing-function skip
+font-stretch skip
+page skip
+src skip
+text-line-through-color skip
+text-line-through-mode skip
+text-line-through-style skip
+text-line-through-width skip
+text-overline-color skip
+text-overline-mode skip
+text-overline-style skip
+text-overline-width skip
+text-underline-color skip
+text-underline-mode skip
+text-underline-style skip
+text-underline-width skip
+unicode-range skip
+-webkit-font-size-delta skip
+-webkit-text-decorations-in-effect skip
+max-zoom skip
+min-zoom skip
+user-zoom skip
+orientation skip
+enable-background skip
+invalid skip
+all skip
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSProperty.cpp b/chromium/third_party/WebKit/Source/core/css/CSSProperty.cpp
index 59e3d9e68af..f36f4897f92 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSProperty.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSProperty.cpp
@@ -21,7 +21,7 @@
#include "config.h"
#include "core/css/CSSProperty.h"
-#include "StylePropertyShorthand.h"
+#include "core/StylePropertyShorthand.h"
#include "core/css/CSSValueList.h"
#include "core/rendering/style/RenderStyleConstants.h"
@@ -47,7 +47,7 @@ CSSPropertyID StylePropertyMetadata::shorthandID() const
void CSSProperty::wrapValueInCommaSeparatedList()
{
- RefPtr<CSSValue> value = m_value.release();
+ RefPtrWillBeRawPtr<CSSValue> value = m_value.release();
m_value = CSSValueList::createCommaSeparated();
toCSSValueList(m_value.get())->append(value.release());
}
@@ -282,7 +282,6 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyGlyphOrientationHorizontal:
case CSSPropertyGlyphOrientationVertical:
case CSSPropertyImageRendering:
- case CSSPropertyKerning:
case CSSPropertyLetterSpacing:
case CSSPropertyLineHeight:
case CSSPropertyListStyle:
@@ -317,7 +316,6 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyTextShadow:
case CSSPropertyTextTransform:
case CSSPropertyTouchActionDelay:
- case CSSPropertyVariable:
case CSSPropertyVisibility:
case CSSPropertyWebkitAspectRatio:
case CSSPropertyWebkitBorderHorizontalSpacing:
@@ -326,15 +324,12 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyWebkitFontFeatureSettings:
case CSSPropertyFontKerning:
case CSSPropertyWebkitFontSmoothing:
- case CSSPropertyWebkitFontVariantLigatures:
+ case CSSPropertyFontVariantLigatures:
case CSSPropertyWebkitLocale:
case CSSPropertyWebkitHighlight:
case CSSPropertyWebkitHyphenateCharacter:
- case CSSPropertyWebkitLineAlign:
case CSSPropertyWebkitLineBoxContain:
case CSSPropertyWebkitLineBreak:
- case CSSPropertyWebkitLineGrid:
- case CSSPropertyWebkitLineSnap:
case CSSPropertyWebkitPrintColorAdjust:
case CSSPropertyWebkitRtlOrdering:
case CSSPropertyWebkitRubyPosition:
@@ -425,7 +420,6 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyClear:
case CSSPropertyClip:
case CSSPropertyClipPath:
- case CSSPropertyColorProfile:
case CSSPropertyContent:
case CSSPropertyCounterIncrement:
case CSSPropertyCounterReset:
@@ -439,6 +433,7 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyFontStretch:
case CSSPropertyHeight:
case CSSPropertyIsolation:
+ case CSSPropertyJustifySelf:
case CSSPropertyLeft:
case CSSPropertyLightingColor:
case CSSPropertyMargin:
@@ -478,6 +473,7 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyPaintOrder:
case CSSPropertyPosition:
case CSSPropertyRight:
+ case CSSPropertyScrollBehavior:
case CSSPropertySize:
case CSSPropertySrc:
case CSSPropertyStopColor:
@@ -524,6 +520,7 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyWebkitAnimationPlayState:
case CSSPropertyWebkitAnimationTimingFunction:
case CSSPropertyWebkitAppearance:
+ case CSSPropertyBackfaceVisibility:
case CSSPropertyWebkitBackfaceVisibility:
case CSSPropertyWebkitBackgroundClip:
case CSSPropertyWebkitBackgroundComposite:
@@ -560,14 +557,12 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyWebkitBoxShadow:
case CSSPropertyInternalCallback:
case CSSPropertyWebkitClipPath:
- case CSSPropertyWebkitColumnAxis:
case CSSPropertyWebkitColumnBreakAfter:
case CSSPropertyWebkitColumnBreakBefore:
case CSSPropertyWebkitColumnBreakInside:
case CSSPropertyWebkitColumnCount:
case CSSPropertyColumnFill:
case CSSPropertyWebkitColumnGap:
- case CSSPropertyWebkitColumnProgression:
case CSSPropertyWebkitColumnRule:
case CSSPropertyWebkitColumnRuleColor:
case CSSPropertyWebkitColumnRuleStyle:
@@ -591,12 +586,14 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyGridColumn:
case CSSPropertyGridColumnEnd:
case CSSPropertyGridColumnStart:
- case CSSPropertyGridDefinitionColumns:
- case CSSPropertyGridDefinitionRows:
+ case CSSPropertyGrid:
+ case CSSPropertyGridTemplate:
+ case CSSPropertyGridTemplateColumns:
+ case CSSPropertyGridTemplateRows:
case CSSPropertyGridRow:
case CSSPropertyGridRowEnd:
case CSSPropertyGridRowStart:
- case CSSPropertyGridTemplate:
+ case CSSPropertyGridTemplateAreas:
case CSSPropertyJustifyContent:
case CSSPropertyWebkitLineClamp:
case CSSPropertyWebkitLogicalHeight:
@@ -642,15 +639,20 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyWebkitPaddingBefore:
case CSSPropertyWebkitPaddingEnd:
case CSSPropertyWebkitPaddingStart:
+ case CSSPropertyPerspective:
case CSSPropertyWebkitPerspective:
+ case CSSPropertyPerspectiveOrigin:
case CSSPropertyWebkitPerspectiveOrigin:
case CSSPropertyWebkitPerspectiveOriginX:
case CSSPropertyWebkitPerspectiveOriginY:
+ case CSSPropertyTransform:
case CSSPropertyWebkitTransform:
+ case CSSPropertyTransformOrigin:
case CSSPropertyWebkitTransformOrigin:
case CSSPropertyWebkitTransformOriginX:
case CSSPropertyWebkitTransformOriginY:
case CSSPropertyWebkitTransformOriginZ:
+ case CSSPropertyTransformStyle:
case CSSPropertyWebkitTransformStyle:
case CSSPropertyWebkitTransition:
case CSSPropertyWebkitTransitionDelay:
@@ -658,27 +660,21 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
case CSSPropertyWebkitTransitionProperty:
case CSSPropertyWebkitTransitionTimingFunction:
case CSSPropertyWebkitUserDrag:
- case CSSPropertyWebkitFlowInto:
- case CSSPropertyWebkitFlowFrom:
- case CSSPropertyWebkitRegionBreakAfter:
- case CSSPropertyWebkitRegionBreakBefore:
- case CSSPropertyWebkitRegionBreakInside:
- case CSSPropertyWebkitRegionFragment:
case CSSPropertyWebkitWrapFlow:
case CSSPropertyShapeMargin:
case CSSPropertyShapeImageThreshold:
- case CSSPropertyShapePadding:
- case CSSPropertyShapeInside:
case CSSPropertyShapeOutside:
case CSSPropertyWebkitWrapThrough:
case CSSPropertyWebkitAppRegion:
case CSSPropertyWidth:
+ case CSSPropertyWillChange:
case CSSPropertyMaxZoom:
case CSSPropertyMinZoom:
case CSSPropertyOrientation:
case CSSPropertyUserZoom:
case CSSPropertyZIndex:
case CSSPropertyZoom:
+ case CSSPropertyAll:
return false;
case CSSPropertyInvalid:
ASSERT_NOT_REACHED();
@@ -688,4 +684,18 @@ bool CSSProperty::isInheritedProperty(CSSPropertyID propertyID)
return false;
}
+bool CSSProperty::isAffectedByAllProperty(CSSPropertyID propertyID)
+{
+ if (propertyID == CSSPropertyAll)
+ return false;
+
+ // all shorthand spec says:
+ // The all property is a shorthand that resets all CSS properties except
+ // direction and unicode-bidi. It only accepts the CSS-wide keywords.
+ // c.f. http://dev.w3.org/csswg/css-cascade/#all-shorthand
+ // So CSSPropertyUnicodeBidi and CSSPropertyDirection are not
+ // affected by all property.
+ return propertyID != CSSPropertyUnicodeBidi && propertyID != CSSPropertyDirection;
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSProperty.h b/chromium/third_party/WebKit/Source/core/css/CSSProperty.h
index a0fb377ce3f..bb54c659988 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSProperty.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSProperty.h
@@ -21,9 +21,9 @@
#ifndef CSSProperty_h
#define CSSProperty_h
-#include "CSSPropertyNames.h"
-#include "RuntimeEnabledFeatures.h"
+#include "core/CSSPropertyNames.h"
#include "core/css/CSSValue.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/text/TextDirection.h"
#include "platform/text/WritingMode.h"
#include "wtf/PassRefPtr.h"
@@ -53,12 +53,12 @@ struct StylePropertyMetadata {
};
class CSSProperty {
+ ALLOW_ONLY_INLINE_ALLOCATION();
public:
- CSSProperty(CSSPropertyID propertyID, PassRefPtr<CSSValue> value, bool important = false, bool isSetFromShorthand = false, int indexInShorthandsVector = 0, bool implicit = false)
+ CSSProperty(CSSPropertyID propertyID, PassRefPtrWillBeRawPtr<CSSValue> value, bool important = false, bool isSetFromShorthand = false, int indexInShorthandsVector = 0, bool implicit = false)
: m_metadata(propertyID, isSetFromShorthand, indexInShorthandsVector, important, implicit, isInheritedProperty(propertyID))
, m_value(value)
{
- ASSERT((propertyID == CSSPropertyVariable) == (m_value && m_value->isVariableValue()));
}
// FIXME: Remove this.
@@ -66,7 +66,6 @@ public:
: m_metadata(metadata)
, m_value(value)
{
- ASSERT((metadata.m_propertyID == CSSPropertyVariable) == (m_value && m_value->isVariableValue()));
}
CSSPropertyID id() const { return static_cast<CSSPropertyID>(m_metadata.m_propertyID); }
@@ -80,12 +79,15 @@ public:
static CSSPropertyID resolveDirectionAwareProperty(CSSPropertyID, TextDirection, WritingMode);
static bool isInheritedProperty(CSSPropertyID);
+ static bool isAffectedByAllProperty(CSSPropertyID);
const StylePropertyMetadata& metadata() const { return m_metadata; }
+ void trace(Visitor* visitor) { visitor->trace(m_value); }
+
private:
StylePropertyMetadata m_metadata;
- RefPtr<CSSValue> m_value;
+ RefPtrWillBeMember<CSSValue> m_value;
};
inline CSSPropertyID prefixingVariantForPropertyId(CSSPropertyID propId)
@@ -189,11 +191,6 @@ inline CSSPropertyID prefixingVariantForPropertyId(CSSPropertyID propId)
} // namespace WebCore
-namespace WTF {
-template <> struct VectorTraits<WebCore::CSSProperty> : VectorTraitsBase<false, WebCore::CSSProperty> {
- static const bool canInitializeWithMemset = true;
- static const bool canMoveWithMemcpy = true;
-};
-}
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::CSSProperty);
#endif // CSSProperty_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPropertyNames.in b/chromium/third_party/WebKit/Source/core/css/CSSPropertyNames.in
index 880cb61d86b..d5c0ace1c6c 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPropertyNames.in
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPropertyNames.in
@@ -49,11 +49,11 @@ font-kerning
font-size
font-style
font-variant
+font-variant-ligatures
font-weight
text-rendering
-webkit-font-feature-settings
-webkit-font-smoothing
--webkit-font-variant-ligatures
-webkit-locale
-webkit-text-orientation
-epub-text-orientation alias_for=-webkit-text-orientation
@@ -136,6 +136,7 @@ font-stretch
height
image-rendering
isolation
+justify-self
left
letter-spacing
list-style
@@ -183,6 +184,7 @@ position
quotes
resize
right
+scroll-behavior
size
src
speak
@@ -224,6 +226,7 @@ visibility
white-space
widows
width
+will-change
word-break
-epub-word-break alias_for=word-break
word-spacing
@@ -231,6 +234,7 @@ word-wrap
z-index
-webkit-appearance
-webkit-aspect-ratio
+backface-visibility
-webkit-backface-visibility
-webkit-background-clip
-webkit-background-composite
@@ -274,14 +278,12 @@ z-index
-webkit-box-reflect
-webkit-box-shadow
-internal-callback
--webkit-column-axis
-webkit-column-break-after
-webkit-column-break-before
-webkit-column-break-inside
-webkit-column-count
column-fill
-webkit-column-gap
--webkit-column-progression
-webkit-column-rule
-webkit-column-rule-color
-webkit-column-rule-style
@@ -321,20 +323,19 @@ grid-area
grid-column
grid-column-end
grid-column-start
-grid-definition-columns
-grid-definition-rows
+grid
+grid-template
+grid-template-columns
+grid-template-rows
grid-row
grid-row-end
grid-row-start
-grid-template
+grid-template-areas
-webkit-highlight
-webkit-hyphenate-character
-webkit-line-box-contain
--webkit-line-align
-webkit-line-break
-webkit-line-clamp
--webkit-line-grid
--webkit-line-snap
-webkit-logical-width
-webkit-logical-height
-webkit-margin-after-collapse
@@ -374,7 +375,9 @@ order
-webkit-padding-before
-webkit-padding-end
-webkit-padding-start
+perspective
-webkit-perspective
+perspective-origin
-webkit-perspective-origin
-webkit-perspective-origin-x
-webkit-perspective-origin-y
@@ -396,30 +399,23 @@ order
-webkit-text-stroke
-webkit-text-stroke-color
-webkit-text-stroke-width
+transform
-webkit-transform
+transform-origin
-webkit-transform-origin
-webkit-transform-origin-x
-webkit-transform-origin-y
-webkit-transform-origin-z
+transform-style
-webkit-transform-style
-webkit-user-drag
-webkit-user-modify
-webkit-user-select
--webkit-flow-into
--webkit-flow-from
--webkit-region-fragment
--webkit-region-break-after
--webkit-region-break-before
--webkit-region-break-inside
--webkit-shape-inside alias_for=shape-inside
-webkit-shape-outside alias_for=shape-outside
-webkit-shape-margin alias_for=shape-margin
--webkit-shape-padding alias_for=shape-padding
-webkit-shape-image-threshold alias_for=shape-image-threshold
-shape-inside
shape-outside
shape-margin
-shape-padding
shape-image-threshold
-webkit-wrap-flow
-webkit-wrap-through
@@ -429,6 +425,7 @@ orientation
user-zoom
-webkit-tap-highlight-color
-webkit-app-region
+all
// Internal properties.
-internal-marquee-direction
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.cpp b/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.cpp
index 6a5ff1b31bf..26bf1b68d75 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.cpp
@@ -30,10 +30,6 @@
#include "config.h"
-#ifdef SKIP_STATIC_CONSTRUCTORS_ON_GCC
-#define CSSPROPERTYSOURCEDATA_HIDE_GLOBALS 1
-#endif
-
#include "core/css/CSSPropertySourceData.h"
#include "wtf/StaticConstructors.h"
@@ -114,17 +110,13 @@ unsigned CSSPropertySourceData::hash() const
return StringHash::hash(name) + 3 * StringHash::hash(value) + 7 * important + 13 * parsedOk + 31;
}
-// Global init routines
-DEFINE_GLOBAL(CSSPropertySourceData, emptyCSSPropertySourceData, "", "e", false, false)
-
-// static
-void CSSPropertySourceData::init()
+void CSSRuleSourceData::trace(Visitor* visitor)
{
- static bool initialized;
- if (!initialized) {
- new ((void *) &emptyCSSPropertySourceData) CSSPropertySourceData("", "e", false, false, false, SourceRange(0, 0));
- initialized = true;
- }
+ visitor->trace(ruleHeaderRange);
+ visitor->trace(ruleBodyRange);
+ visitor->trace(selectorRanges);
+ visitor->trace(styleSourceData);
+ visitor->trace(childRules);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.h b/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.h
index 7b964d45f26..704235a23a2 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSPropertySourceData.h
@@ -31,6 +31,7 @@
#ifndef CSSPropertySourceData_h
#define CSSPropertySourceData_h
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/RefCounted.h"
#include "wtf/Vector.h"
@@ -41,17 +42,21 @@ namespace WebCore {
class StyleRuleBase;
struct SourceRange {
+ ALLOW_ONLY_INLINE_ALLOCATION();
+public:
SourceRange();
SourceRange(unsigned start, unsigned end);
unsigned length() const;
+ void trace(Visitor*) { }
+
unsigned start;
unsigned end;
};
struct CSSPropertySourceData {
- static void init();
-
+ ALLOW_ONLY_INLINE_ALLOCATION();
+public:
CSSPropertySourceData(const String& name, const String& value, bool important, bool disabled, bool parsedOk, const SourceRange& range);
CSSPropertySourceData(const CSSPropertySourceData& other);
CSSPropertySourceData();
@@ -59,6 +64,8 @@ struct CSSPropertySourceData {
String toString() const;
unsigned hash() const;
+ void trace(Visitor* visitor) { visitor->trace(range); }
+
String name;
String value;
bool important;
@@ -67,24 +74,22 @@ struct CSSPropertySourceData {
SourceRange range;
};
-#ifndef CSSPROPERTYSOURCEDATA_HIDE_GLOBALS
-extern const CSSPropertySourceData emptyCSSPropertySourceData;
-#endif
-
-struct CSSStyleSourceData : public RefCounted<CSSStyleSourceData> {
- static PassRefPtr<CSSStyleSourceData> create()
+struct CSSStyleSourceData : public RefCountedWillBeGarbageCollected<CSSStyleSourceData> {
+ static PassRefPtrWillBeRawPtr<CSSStyleSourceData> create()
{
- return adoptRef(new CSSStyleSourceData());
+ return adoptRefWillBeNoop(new CSSStyleSourceData());
}
- Vector<CSSPropertySourceData> propertyData;
+ void trace(Visitor* visitor) { visitor->trace(propertyData); }
+
+ WillBeHeapVector<CSSPropertySourceData> propertyData;
};
struct CSSRuleSourceData;
-typedef Vector<RefPtr<CSSRuleSourceData> > RuleSourceDataList;
-typedef Vector<SourceRange> SelectorRangeList;
+typedef WillBeHeapVector<RefPtrWillBeMember<CSSRuleSourceData> > RuleSourceDataList;
+typedef WillBeHeapVector<SourceRange> SelectorRangeList;
-struct CSSRuleSourceData : public RefCounted<CSSRuleSourceData> {
+struct CSSRuleSourceData : public RefCountedWillBeGarbageCollected<CSSRuleSourceData> {
enum Type {
UNKNOWN_RULE,
STYLE_RULE,
@@ -94,20 +99,19 @@ struct CSSRuleSourceData : public RefCounted<CSSRuleSourceData> {
FONT_FACE_RULE,
PAGE_RULE,
KEYFRAMES_RULE,
- REGION_RULE,
VIEWPORT_RULE,
SUPPORTS_RULE,
FILTER_RULE
};
- static PassRefPtr<CSSRuleSourceData> create(Type type)
+ static PassRefPtrWillBeRawPtr<CSSRuleSourceData> create(Type type)
{
- return adoptRef(new CSSRuleSourceData(type));
+ return adoptRefWillBeNoop(new CSSRuleSourceData(type));
}
- static PassRefPtr<CSSRuleSourceData> createUnknown()
+ static PassRefPtrWillBeRawPtr<CSSRuleSourceData> createUnknown()
{
- return adoptRef(new CSSRuleSourceData(UNKNOWN_RULE));
+ return adoptRefWillBeNoop(new CSSRuleSourceData(UNKNOWN_RULE));
}
CSSRuleSourceData(Type type)
@@ -117,6 +121,8 @@ struct CSSRuleSourceData : public RefCounted<CSSRuleSourceData> {
styleSourceData = CSSStyleSourceData::create();
}
+ void trace(Visitor*);
+
Type type;
// Range of the selector list in the enclosing source.
@@ -129,7 +135,7 @@ struct CSSRuleSourceData : public RefCounted<CSSRuleSourceData> {
SelectorRangeList selectorRanges;
// Only for CSSStyleRules, CSSFontFaceRules, and CSSPageRules.
- RefPtr<CSSStyleSourceData> styleSourceData;
+ RefPtrWillBeMember<CSSStyleSourceData> styleSourceData;
// Only for CSSMediaRules.
RuleSourceDataList childRules;
@@ -137,4 +143,7 @@ struct CSSRuleSourceData : public RefCounted<CSSRuleSourceData> {
} // namespace WebCore
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::SourceRange);
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::CSSPropertySourceData);
+
#endif // CSSPropertySourceData_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.cpp
index b13006ccc5e..066d6439862 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.cpp
@@ -28,8 +28,6 @@
#include "core/css/CSSPrimitiveValue.h"
-using namespace std;
-
namespace WebCore {
String CSSReflectValue::customCSSText() const
@@ -39,19 +37,6 @@ String CSSReflectValue::customCSSText() const
return m_direction->cssText() + ' ' + m_offset->cssText();
}
-String CSSReflectValue::customSerializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- if (m_mask)
- return m_direction->customSerializeResolvingVariables(variables) + ' ' + m_offset->customSerializeResolvingVariables(variables) + ' ' + m_mask->serializeResolvingVariables(variables);
- return m_direction->customSerializeResolvingVariables(variables) + ' ' + m_offset->customSerializeResolvingVariables(variables);
-}
-
-void CSSReflectValue::addSubresourceStyleURLs(ListHashSet<KURL>& urls, const StyleSheetContents* styleSheet) const
-{
- if (m_mask)
- m_mask->addSubresourceStyleURLs(urls, styleSheet);
-}
-
bool CSSReflectValue::equals(const CSSReflectValue& other) const
{
return m_direction == other.m_direction
@@ -59,4 +44,12 @@ bool CSSReflectValue::equals(const CSSReflectValue& other) const
&& compareCSSValuePtr(m_mask, other.m_mask);
}
+void CSSReflectValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_direction);
+ visitor->trace(m_offset);
+ visitor->trace(m_mask);
+ CSSValue::traceAfterDispatch(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.h b/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.h
index 0fd92a07da2..b85d430c002 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSReflectValue.h
@@ -36,10 +36,10 @@ class CSSPrimitiveValue;
class CSSReflectValue : public CSSValue {
public:
- static PassRefPtr<CSSReflectValue> create(PassRefPtr<CSSPrimitiveValue> direction,
- PassRefPtr<CSSPrimitiveValue> offset, PassRefPtr<CSSValue> mask)
+ static PassRefPtrWillBeRawPtr<CSSReflectValue> create(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> direction,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> offset, PassRefPtrWillBeRawPtr<CSSValue> mask)
{
- return adoptRef(new CSSReflectValue(direction, offset, mask));
+ return adoptRefWillBeNoop(new CSSReflectValue(direction, offset, mask));
}
CSSPrimitiveValue* direction() const { return m_direction.get(); }
@@ -47,14 +47,13 @@ public:
CSSValue* mask() const { return m_mask.get(); }
String customCSSText() const;
- String customSerializeResolvingVariables(const HashMap<AtomicString, String>&) const;
-
- void addSubresourceStyleURLs(ListHashSet<KURL>&, const StyleSheetContents*) const;
bool equals(const CSSReflectValue&) const;
+ void traceAfterDispatch(Visitor*);
+
private:
- CSSReflectValue(PassRefPtr<CSSPrimitiveValue> direction, PassRefPtr<CSSPrimitiveValue> offset, PassRefPtr<CSSValue> mask)
+ CSSReflectValue(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> direction, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> offset, PassRefPtrWillBeRawPtr<CSSValue> mask)
: CSSValue(ReflectClass)
, m_direction(direction)
, m_offset(offset)
@@ -62,9 +61,9 @@ private:
{
}
- RefPtr<CSSPrimitiveValue> m_direction;
- RefPtr<CSSPrimitiveValue> m_offset;
- RefPtr<CSSValue> m_mask;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_direction;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_offset;
+ RefPtrWillBeMember<CSSValue> m_mask;
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSReflectValue, isReflectValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRegionRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSRegionRule.cpp
deleted file mode 100644
index 94e9d0bae8c..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSRegionRule.cpp
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- * Copyright (C) 2012 Apple Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-#include "config.h"
-
-#include "core/css/CSSRegionRule.h"
-
-#include "RuntimeEnabledFeatures.h"
-#include "core/css/StyleRule.h"
-#include "wtf/text/StringBuilder.h"
-
-namespace WebCore {
-CSSRegionRule::CSSRegionRule(StyleRuleRegion* regionRule, CSSStyleSheet* parent)
- : CSSGroupingRule(regionRule, parent)
-{
- ASSERT(RuntimeEnabledFeatures::cssRegionsEnabled());
-}
-
-String CSSRegionRule::cssText() const
-{
- StringBuilder result;
- result.appendLiteral("@-webkit-region ");
-
- // First add the selectors.
- result.append(toStyleRuleRegion(m_groupRule.get())->selectorList().selectorsText());
-
- // Then add the rules.
- result.appendLiteral(" { \n");
- appendCSSTextForItems(result);
- result.append('}');
- return result.toString();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRegionRule.h b/chromium/third_party/WebKit/Source/core/css/CSSRegionRule.h
deleted file mode 100644
index e095da44af4..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSRegionRule.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- * Copyright (C) 2012 Apple Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-#ifndef CSSRegionRule_h
-#define CSSRegionRule_h
-
-#include "core/css/CSSGroupingRule.h"
-
-namespace WebCore {
-
-class StyleRuleRegion;
-
-class CSSRegionRule : public CSSGroupingRule {
-public:
- static PassRefPtr<CSSRegionRule> create(StyleRuleRegion* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSRegionRule(rule, sheet)); }
-
- virtual CSSRule::Type type() const OVERRIDE { return WEBKIT_REGION_RULE; }
- virtual String cssText() const OVERRIDE;
-
-private:
- CSSRegionRule(StyleRuleRegion*, CSSStyleSheet* parent);
-};
-
-DEFINE_CSS_RULE_TYPE_CASTS(CSSRegionRule, WEBKIT_REGION_RULE);
-
-}
-
-#endif // CSSRegionRule_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSRule.cpp
index 7673640a990..60aa695022e 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSRule.cpp
@@ -29,7 +29,7 @@
namespace WebCore {
-struct SameSizeAsCSSRule : public RefCounted<SameSizeAsCSSRule> {
+struct SameSizeAsCSSRule : public RefCountedWillBeGarbageCollectedFinalized<SameSizeAsCSSRule> {
virtual ~SameSizeAsCSSRule();
unsigned char bitfields;
void* pointerUnion;
@@ -37,8 +37,6 @@ struct SameSizeAsCSSRule : public RefCounted<SameSizeAsCSSRule> {
COMPILE_ASSERT(sizeof(CSSRule) == sizeof(SameSizeAsCSSRule), CSSRule_should_stay_small);
-COMPILE_ASSERT(StyleRuleBase::Region == static_cast<StyleRuleBase::Type>(CSSRule::WEBKIT_REGION_RULE), enums_should_match);
-
COMPILE_ASSERT(StyleRuleBase::Viewport == static_cast<StyleRuleBase::Type>(CSSRule::VIEWPORT_RULE), enums_should_match);
void CSSRule::setCSSText(const String&)
@@ -52,4 +50,15 @@ const CSSParserContext& CSSRule::parserContext() const
return styleSheet ? styleSheet->contents()->parserContext() : strictCSSParserContext();
}
+void CSSRule::trace(Visitor* visitor)
+{
+ // This makes the parent link strong, which is different from the
+ // pre-oilpan world, where the parent link is mysteriously zeroed under
+ // some circumstances.
+ if (m_parentIsRule)
+ visitor->trace(m_parentRule);
+ else
+ visitor->trace(m_parentStyleSheet);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRule.h b/chromium/third_party/WebKit/Source/core/css/CSSRule.h
index 9cd66086e23..b160a9e82da 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSRule.h
@@ -23,6 +23,7 @@
#ifndef CSSRule_h
#define CSSRule_h
+#include "platform/heap/Handle.h"
#include "wtf/RefCounted.h"
#include "wtf/text/WTFString.h"
@@ -32,7 +33,7 @@ class CSSParserContext;
class CSSStyleSheet;
class StyleRuleBase;
-class CSSRule : public RefCounted<CSSRule> {
+class CSSRule : public RefCountedWillBeGarbageCollectedFinalized<CSSRule> {
public:
virtual ~CSSRule() { }
@@ -53,7 +54,6 @@ public:
WEBKIT_KEYFRAME_RULE = KEYFRAME_RULE,
SUPPORTS_RULE = 12,
VIEWPORT_RULE = 15,
- WEBKIT_REGION_RULE = 16,
WEBKIT_FILTER_RULE = 17
};
@@ -73,6 +73,8 @@ public:
m_parentRule = rule;
}
+ virtual void trace(Visitor*);
+
CSSStyleSheet* parentStyleSheet() const
{
if (m_parentIsRule)
@@ -102,6 +104,7 @@ private:
mutable unsigned char m_hasCachedSelectorText : 1;
unsigned char m_parentIsRule : 1;
+ // These should be Members, but no Members in unions.
union {
CSSRule* m_parentRule;
CSSStyleSheet* m_parentStyleSheet;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRule.idl b/chromium/third_party/WebKit/Source/core/css/CSSRule.idl
index 9dadad92a10..a70bd3ec983 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSRule.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSRule.idl
@@ -22,6 +22,7 @@
[
Custom=Wrap,
DependentLifetime,
+ WillBeGarbageCollected,
] interface CSSRule {
// RuleType
@@ -38,7 +39,6 @@
const unsigned short WEBKIT_KEYFRAME_RULE = 8;
const unsigned short SUPPORTS_RULE = 12;
[RuntimeEnabled=CSSViewport] const unsigned short VIEWPORT_RULE = 15;
- [RuntimeEnabled=CSSRegions] const unsigned short WEBKIT_REGION_RULE = 16;
const unsigned short WEBKIT_FILTER_RULE = 17;
readonly attribute unsigned short type;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRuleList.cpp b/chromium/third_party/WebKit/Source/core/css/CSSRuleList.cpp
index 499518bde5d..bfdf30c8719 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSRuleList.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSRuleList.cpp
@@ -35,7 +35,9 @@ CSSRuleList::~CSSRuleList()
}
StaticCSSRuleList::StaticCSSRuleList()
+#if !ENABLE(OILPAN)
: m_refCount(1)
+#endif
{
}
@@ -43,11 +45,20 @@ StaticCSSRuleList::~StaticCSSRuleList()
{
}
+#if !ENABLE(OILPAN)
void StaticCSSRuleList::deref()
{
ASSERT(m_refCount);
if (!--m_refCount)
delete this;
}
+#endif
+
+void StaticCSSRuleList::trace(Visitor* visitor)
+{
+ visitor->trace(m_rules);
+ CSSRuleList::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRuleList.h b/chromium/third_party/WebKit/Source/core/css/CSSRuleList.h
index f65b3667a4f..81b0fcf9775 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSRuleList.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSRuleList.h
@@ -22,6 +22,7 @@
#ifndef CSSRuleList_h
#define CSSRuleList_h
+#include "platform/heap/Handle.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefPtr.h"
#include "wtf/Vector.h"
@@ -31,60 +32,86 @@ namespace WebCore {
class CSSRule;
class CSSStyleSheet;
-class CSSRuleList {
- WTF_MAKE_NONCOPYABLE(CSSRuleList); WTF_MAKE_FAST_ALLOCATED;
+class CSSRuleList : public NoBaseWillBeGarbageCollectedFinalized<CSSRuleList> {
+ WTF_MAKE_NONCOPYABLE(CSSRuleList);
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
virtual ~CSSRuleList();
+#if !ENABLE(OILPAN)
virtual void ref() = 0;
virtual void deref() = 0;
+#endif
virtual unsigned length() const = 0;
virtual CSSRule* item(unsigned index) const = 0;
virtual CSSStyleSheet* styleSheet() const = 0;
+ virtual void trace(Visitor*) { }
+
protected:
CSSRuleList();
};
-class StaticCSSRuleList : public CSSRuleList {
+class StaticCSSRuleList FINAL : public CSSRuleList {
public:
- static PassRefPtr<StaticCSSRuleList> create() { return adoptRef(new StaticCSSRuleList()); }
+ static PassRefPtrWillBeRawPtr<StaticCSSRuleList> create()
+ {
+ return adoptRefWillBeNoop(new StaticCSSRuleList());
+ }
+
+#if !ENABLE(OILPAN)
+ virtual void ref() OVERRIDE { ++m_refCount; }
+ virtual void deref() OVERRIDE;
+#endif
- virtual void ref() { ++m_refCount; }
- virtual void deref();
+ WillBeHeapVector<RefPtrWillBeMember<CSSRule> >& rules() { return m_rules; }
- Vector<RefPtr<CSSRule> >& rules() { return m_rules; }
+ virtual CSSStyleSheet* styleSheet() const OVERRIDE { return 0; }
- virtual CSSStyleSheet* styleSheet() const { return 0; }
+ virtual void trace(Visitor*) OVERRIDE;
private:
StaticCSSRuleList();
- ~StaticCSSRuleList();
+ virtual ~StaticCSSRuleList();
- virtual unsigned length() const { return m_rules.size(); }
- virtual CSSRule* item(unsigned index) const { return index < m_rules.size() ? m_rules[index].get() : 0; }
+ virtual unsigned length() const OVERRIDE { return m_rules.size(); }
+ virtual CSSRule* item(unsigned index) const OVERRIDE { return index < m_rules.size() ? m_rules[index].get() : 0; }
- Vector<RefPtr<CSSRule> > m_rules;
+ WillBeHeapVector<RefPtrWillBeMember<CSSRule> > m_rules;
+#if !ENABLE(OILPAN)
unsigned m_refCount;
+#endif
};
-// The rule owns the live list.
template <class Rule>
-class LiveCSSRuleList : public CSSRuleList {
+class LiveCSSRuleList FINAL : public CSSRuleList {
public:
- LiveCSSRuleList(Rule* rule) : m_rule(rule) { }
-
- virtual void ref() { m_rule->ref(); }
- virtual void deref() { m_rule->deref(); }
+ static PassOwnPtrWillBeRawPtr<LiveCSSRuleList> create(Rule* rule)
+ {
+ return adoptPtrWillBeNoop(new LiveCSSRuleList(rule));
+ }
+
+#if !ENABLE(OILPAN)
+ virtual void ref() OVERRIDE { m_rule->ref(); }
+ virtual void deref() OVERRIDE { m_rule->deref(); }
+#endif
+
+ virtual void trace(Visitor* visitor) OVERRIDE
+ {
+ visitor->trace(m_rule);
+ CSSRuleList::trace(visitor);
+ }
private:
- virtual unsigned length() const { return m_rule->length(); }
- virtual CSSRule* item(unsigned index) const { return m_rule->item(index); }
- virtual CSSStyleSheet* styleSheet() const { return m_rule->parentStyleSheet(); }
+ LiveCSSRuleList(Rule* rule) : m_rule(rule) { }
+
+ virtual unsigned length() const OVERRIDE { return m_rule->length(); }
+ virtual CSSRule* item(unsigned index) const OVERRIDE { return m_rule->item(index); }
+ virtual CSSStyleSheet* styleSheet() const OVERRIDE { return m_rule->parentStyleSheet(); }
- Rule* m_rule;
+ RawPtrWillBeMember<Rule> m_rule;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSRuleList.idl b/chromium/third_party/WebKit/Source/core/css/CSSRuleList.idl
index dd189108786..35fb40069fe 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSRuleList.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSRuleList.idl
@@ -25,7 +25,8 @@
// Introduced in DOM Level 2:
[
- DependentLifetime
+ DependentLifetime,
+ WillBeGarbageCollected,
] interface CSSRuleList {
readonly attribute unsigned long length;
getter CSSRule item(unsigned long index);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.cpp
index d0912d4263f..db01c5bbf62 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.cpp
@@ -26,8 +26,8 @@
#include "core/css/CSSSVGDocumentValue.h"
-#include "FetchInitiatorTypeNames.h"
-#include "core/css/CSSParser.h"
+#include "core/FetchInitiatorTypeNames.h"
+#include "core/css/CSSMarkup.h"
#include "core/dom/Document.h"
#include "core/fetch/FetchRequest.h"
#include "core/fetch/ResourceFetcher.h"
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.h b/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.h
index d2decc42d88..389b1797f60 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSVGDocumentValue.h
@@ -35,7 +35,10 @@ class ResourceFetcher;
class CSSSVGDocumentValue : public CSSValue {
public:
- static PassRefPtr<CSSSVGDocumentValue> create(const String& url) { return adoptRef(new CSSSVGDocumentValue(url)); }
+ static PassRefPtrWillBeRawPtr<CSSSVGDocumentValue> create(const String& url)
+ {
+ return adoptRefWillBeNoop(new CSSSVGDocumentValue(url));
+ }
~CSSSVGDocumentValue();
DocumentResource* cachedSVGDocument() const { return m_document.get(); }
@@ -46,6 +49,8 @@ public:
bool loadRequested() const { return m_loadRequested; }
bool equals(const CSSSVGDocumentValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSSVGDocumentValue(const String& url);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.cpp b/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.cpp
index eaa1223b132..edb36fa9809 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.cpp
@@ -26,8 +26,9 @@
#include "config.h"
#include "core/css/CSSSegmentedFontFace.h"
-#include "RuntimeEnabledFeatures.h"
#include "core/css/CSSFontFace.h"
+#include "core/css/CSSFontSelector.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/fonts/FontCache.h"
#include "platform/fonts/FontDescription.h"
#include "platform/fonts/SegmentedFontData.h"
@@ -35,18 +36,20 @@
namespace WebCore {
-CSSSegmentedFontFace::CSSSegmentedFontFace(CSSFontSelector* fontSelector, FontTraitsMask traitsMask)
+CSSSegmentedFontFace::CSSSegmentedFontFace(CSSFontSelector* fontSelector, FontTraits traits)
: m_fontSelector(fontSelector)
- , m_traitsMask(traitsMask)
+ , m_traits(traits)
+ , m_firstNonCssConnectedFace(m_fontFaces.end())
{
}
CSSSegmentedFontFace::~CSSSegmentedFontFace()
{
pruneTable();
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++)
- m_fontFaces[i]->clearSegmentedFontFace();
+#if !ENABLE(OILPAN)
+ for (FontFaceList::iterator it = m_fontFaces.begin(); it != m_fontFaces.end(); ++it)
+ (*it)->cssFontFace()->clearSegmentedFontFace();
+#endif
}
void CSSSegmentedFontFace::pruneTable()
@@ -61,9 +64,8 @@ void CSSSegmentedFontFace::pruneTable()
bool CSSSegmentedFontFace::isValid() const
{
// Valid if at least one font face is valid.
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++) {
- if (m_fontFaces[i]->isValid())
+ for (FontFaceList::const_iterator it = m_fontFaces.begin(); it != m_fontFaces.end(); ++it) {
+ if ((*it)->cssFontFace()->isValid())
return true;
}
return false;
@@ -72,36 +74,43 @@ bool CSSSegmentedFontFace::isValid() const
void CSSSegmentedFontFace::fontLoaded(CSSFontFace*)
{
pruneTable();
-
- if (RuntimeEnabledFeatures::fontLoadEventsEnabled() && !isLoading()) {
- Vector<RefPtr<LoadFontCallback> > callbacks;
- m_callbacks.swap(callbacks);
- for (size_t index = 0; index < callbacks.size(); ++index) {
- if (isLoaded())
- callbacks[index]->notifyLoaded(this);
- else
- callbacks[index]->notifyError(this);
- }
- }
}
-void CSSSegmentedFontFace::appendFontFace(PassRefPtr<CSSFontFace> fontFace)
+void CSSSegmentedFontFace::fontLoadWaitLimitExceeded(CSSFontFace*)
{
pruneTable();
- fontFace->setSegmentedFontFace(this);
- m_fontFaces.append(fontFace);
}
-void CSSSegmentedFontFace::removeFontFace(PassRefPtr<CSSFontFace> fontFace)
+void CSSSegmentedFontFace::addFontFace(PassRefPtrWillBeRawPtr<FontFace> prpFontFace, bool cssConnected)
{
- size_t index = m_fontFaces.find(fontFace);
- if (index != kNotFound) {
- pruneTable();
- m_fontFaces.remove(index);
- fontFace->clearSegmentedFontFace();
+ RefPtrWillBeRawPtr<FontFace> fontFace = prpFontFace;
+ pruneTable();
+ fontFace->cssFontFace()->setSegmentedFontFace(this);
+ if (cssConnected) {
+ m_fontFaces.insertBefore(m_firstNonCssConnectedFace, fontFace);
+ } else {
+ // This is the only place in Blink that is using addReturnIterator.
+ FontFaceList::iterator iterator = m_fontFaces.addReturnIterator(fontFace);
+ if (m_firstNonCssConnectedFace == m_fontFaces.end())
+ m_firstNonCssConnectedFace = iterator;
}
}
+void CSSSegmentedFontFace::removeFontFace(PassRefPtrWillBeRawPtr<FontFace> prpFontFace)
+{
+ RefPtrWillBeRawPtr<FontFace> fontFace = prpFontFace;
+ FontFaceList::iterator it = m_fontFaces.find(fontFace);
+ if (it == m_fontFaces.end())
+ return;
+
+ if (it == m_firstNonCssConnectedFace)
+ ++m_firstNonCssConnectedFace;
+ m_fontFaces.remove(it);
+
+ pruneTable();
+ fontFace->cssFontFace()->clearSegmentedFontFace();
+}
+
static void appendFontData(SegmentedFontData* newFontData, PassRefPtr<SimpleFontData> prpFaceFontData, const CSSFontFace::UnicodeRangeSet& ranges)
{
RefPtr<SimpleFontData> faceFontData = prpFaceFontData;
@@ -118,13 +127,13 @@ static void appendFontData(SegmentedFontData* newFontData, PassRefPtr<SimpleFont
PassRefPtr<FontData> CSSSegmentedFontFace::getFontData(const FontDescription& fontDescription)
{
if (!isValid())
- return 0;
+ return nullptr;
- FontTraitsMask desiredTraitsMask = fontDescription.traitsMask();
+ FontTraits desiredTraits = fontDescription.traits();
AtomicString emptyFontFamily = "";
- FontCacheKey key = fontDescription.cacheKey(emptyFontFamily, desiredTraitsMask);
+ FontCacheKey key = fontDescription.cacheKey(emptyFontFamily, desiredTraits);
- RefPtr<SegmentedFontData>& fontData = m_fontDataTable.add(key.hash(), 0).iterator->value;
+ RefPtr<SegmentedFontData>& fontData = m_fontDataTable.add(key.hash(), nullptr).storedValue->value;
if (fontData && fontData->numRanges())
return fontData; // No release, we have a reference to an object in the cache which should retain the ref count it has.
@@ -132,35 +141,34 @@ PassRefPtr<FontData> CSSSegmentedFontFace::getFontData(const FontDescription& fo
fontData = SegmentedFontData::create();
FontDescription requestedFontDescription(fontDescription);
- requestedFontDescription.setTraitsMask(m_traitsMask);
- requestedFontDescription.setSyntheticBold(!(m_traitsMask & (FontWeight600Mask | FontWeight700Mask | FontWeight800Mask | FontWeight900Mask)) && (desiredTraitsMask & (FontWeight600Mask | FontWeight700Mask | FontWeight800Mask | FontWeight900Mask)));
- requestedFontDescription.setSyntheticItalic(!(m_traitsMask & FontStyleItalicMask) && (desiredTraitsMask & FontStyleItalicMask));
+ requestedFontDescription.setTraits(m_traits);
+ requestedFontDescription.setSyntheticBold(m_traits.weight() < FontWeight600 && desiredTraits.weight() >= FontWeight600);
+ requestedFontDescription.setSyntheticItalic(m_traits.style() == FontStyleNormal && desiredTraits.style() == FontStyleItalic);
- for (int i = m_fontFaces.size() - 1; i >= 0; --i) {
- if (!m_fontFaces[i]->isValid())
+ for (FontFaceList::reverse_iterator it = m_fontFaces.rbegin(); it != m_fontFaces.rend(); ++it) {
+ if (!(*it)->cssFontFace()->isValid())
continue;
- if (RefPtr<SimpleFontData> faceFontData = m_fontFaces[i]->getFontData(requestedFontDescription)) {
+ if (RefPtr<SimpleFontData> faceFontData = (*it)->cssFontFace()->getFontData(requestedFontDescription)) {
ASSERT(!faceFontData->isSegmented());
#if ENABLE(SVG_FONTS)
// For SVG Fonts that specify that they only support the "normal" variant, we will assume they are incapable
// of small-caps synthesis and just ignore the font face.
- if (faceFontData->isSVGFont() && (desiredTraitsMask & FontVariantSmallCapsMask) && !(m_traitsMask & FontVariantSmallCapsMask))
+ if (faceFontData->isSVGFont() && desiredTraits.variant() == FontVariantSmallCaps && m_traits.variant() == FontVariantNormal)
continue;
#endif
- appendFontData(fontData.get(), faceFontData.release(), m_fontFaces[i]->ranges());
+ appendFontData(fontData.get(), faceFontData.release(), (*it)->cssFontFace()->ranges());
}
}
if (fontData->numRanges())
return fontData; // No release, we have a reference to an object in the cache which should retain the ref count it has.
- return 0;
+ return nullptr;
}
bool CSSSegmentedFontFace::isLoading() const
{
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++) {
- if (m_fontFaces[i]->loadStatus() == FontFace::Loading)
+ for (FontFaceList::const_iterator it = m_fontFaces.begin(); it != m_fontFaces.end(); ++it) {
+ if ((*it)->loadStatus() == FontFace::Loading)
return true;
}
return false;
@@ -168,61 +176,44 @@ bool CSSSegmentedFontFace::isLoading() const
bool CSSSegmentedFontFace::isLoaded() const
{
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++) {
- if (m_fontFaces[i]->loadStatus() != FontFace::Loaded)
+ for (FontFaceList::const_iterator it = m_fontFaces.begin(); it != m_fontFaces.end(); ++it) {
+ if ((*it)->loadStatus() != FontFace::Loaded)
return false;
}
return true;
}
-void CSSSegmentedFontFace::willUseFontData(const FontDescription& fontDescription)
+void CSSSegmentedFontFace::willUseFontData(const FontDescription& fontDescription, UChar32 character)
{
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++)
- m_fontFaces[i]->willUseFontData(fontDescription);
+ for (FontFaceList::reverse_iterator it = m_fontFaces.rbegin(); it != m_fontFaces.rend(); ++it) {
+ if ((*it)->loadStatus() != FontFace::Unloaded)
+ break;
+ if ((*it)->cssFontFace()->maybeScheduleFontLoad(fontDescription, character))
+ break;
+ }
}
bool CSSSegmentedFontFace::checkFont(const String& text) const
{
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++) {
- if (m_fontFaces[i]->loadStatus() != FontFace::Loaded && m_fontFaces[i]->ranges().intersectsWith(text))
+ for (FontFaceList::const_iterator it = m_fontFaces.begin(); it != m_fontFaces.end(); ++it) {
+ if ((*it)->loadStatus() != FontFace::Loaded && (*it)->cssFontFace()->ranges().intersectsWith(text))
return false;
}
return true;
}
-void CSSSegmentedFontFace::loadFont(const FontDescription& fontDescription, const String& text, PassRefPtr<LoadFontCallback> callback)
+void CSSSegmentedFontFace::match(const String& text, WillBeHeapVector<RefPtrWillBeMember<FontFace> >& faces) const
{
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++) {
- if (m_fontFaces[i]->loadStatus() == FontFace::Unloaded && m_fontFaces[i]->ranges().intersectsWith(text)) {
- RefPtr<SimpleFontData> fontData = m_fontFaces[i]->getFontData(fontDescription);
- if (fontData->customFontData())
- fontData->customFontData()->beginLoadIfNeeded();
- }
- }
-
- if (callback) {
- if (isLoading())
- m_callbacks.append(callback);
- else if (isLoaded())
- callback->notifyLoaded(this);
- else
- callback->notifyError(this);
+ for (FontFaceList::const_iterator it = m_fontFaces.begin(); it != m_fontFaces.end(); ++it) {
+ if ((*it)->cssFontFace()->ranges().intersectsWith(text))
+ faces.append(*it);
}
}
-Vector<RefPtr<FontFace> > CSSSegmentedFontFace::fontFaces(const String& text) const
+void CSSSegmentedFontFace::trace(Visitor* visitor)
{
- Vector<RefPtr<FontFace> > fontFaces;
- unsigned size = m_fontFaces.size();
- for (unsigned i = 0; i < size; i++) {
- if (m_fontFaces[i]->ranges().intersectsWith(text))
- fontFaces.append(m_fontFaces[i]->fontFace());
- }
- return fontFaces;
+ visitor->trace(m_fontSelector);
+ visitor->trace(m_fontFaces);
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.h b/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.h
index 26c5bb1e0b0..a3630e38aa7 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFace.h
@@ -26,8 +26,10 @@
#ifndef CSSSegmentedFontFace_h
#define CSSSegmentedFontFace_h
-#include "platform/fonts/FontTraitsMask.h"
+#include "platform/fonts/FontTraits.h"
+#include "platform/heap/Handle.h"
#include "wtf/HashMap.h"
+#include "wtf/ListHashSet.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefCounted.h"
#include "wtf/Vector.h"
@@ -42,47 +44,48 @@ class FontDescription;
class FontFace;
class SegmentedFontData;
-class CSSSegmentedFontFace : public RefCounted<CSSSegmentedFontFace> {
+class CSSSegmentedFontFace FINAL : public RefCountedWillBeGarbageCollectedFinalized<CSSSegmentedFontFace> {
public:
- static PassRefPtr<CSSSegmentedFontFace> create(CSSFontSelector* selector, FontTraitsMask traitsMask) { return adoptRef(new CSSSegmentedFontFace(selector, traitsMask)); }
+ static PassRefPtrWillBeRawPtr<CSSSegmentedFontFace> create(CSSFontSelector* selector, FontTraits traits)
+ {
+ return adoptRefWillBeNoop(new CSSSegmentedFontFace(selector, traits));
+ }
~CSSSegmentedFontFace();
CSSFontSelector* fontSelector() const { return m_fontSelector; }
- FontTraitsMask traitsMask() const { return m_traitsMask; }
+ FontTraits traits() const { return m_traits; }
void fontLoaded(CSSFontFace*);
+ void fontLoadWaitLimitExceeded(CSSFontFace*);
- void appendFontFace(PassRefPtr<CSSFontFace>);
- void removeFontFace(PassRefPtr<CSSFontFace>);
+ void addFontFace(PassRefPtrWillBeRawPtr<FontFace>, bool cssConnected);
+ void removeFontFace(PassRefPtrWillBeRawPtr<FontFace>);
bool isEmpty() const { return m_fontFaces.isEmpty(); }
PassRefPtr<FontData> getFontData(const FontDescription&);
- class LoadFontCallback : public RefCounted<LoadFontCallback> {
- public:
- virtual ~LoadFontCallback() { }
- virtual void notifyLoaded(CSSSegmentedFontFace*) = 0;
- virtual void notifyError(CSSSegmentedFontFace*) = 0;
- };
-
bool checkFont(const String&) const;
- void loadFont(const FontDescription&, const String&, PassRefPtr<LoadFontCallback>);
- Vector<RefPtr<FontFace> > fontFaces(const String& text) const;
- void willUseFontData(const FontDescription&);
+ void match(const String&, WillBeHeapVector<RefPtrWillBeMember<FontFace> >&) const;
+ void willUseFontData(const FontDescription&, UChar32);
+
+ void trace(Visitor*);
private:
- CSSSegmentedFontFace(CSSFontSelector*, FontTraitsMask);
+ CSSSegmentedFontFace(CSSFontSelector*, FontTraits);
void pruneTable();
bool isValid() const;
bool isLoading() const;
bool isLoaded() const;
- CSSFontSelector* m_fontSelector;
- FontTraitsMask m_traitsMask;
+ typedef WillBeHeapListHashSet<RefPtrWillBeMember<FontFace> > FontFaceList;
+
+ RawPtrWillBeMember<CSSFontSelector> m_fontSelector;
+ FontTraits m_traits;
HashMap<unsigned, RefPtr<SegmentedFontData> > m_fontDataTable;
- Vector<RefPtr<CSSFontFace>, 1> m_fontFaces;
- Vector<RefPtr<LoadFontCallback> > m_callbacks;
+ // All non-CSS-connected FontFaces are stored after the CSS-connected ones.
+ FontFaceList m_fontFaces;
+ FontFaceList::iterator m_firstNonCssConnectedFace;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.cpp b/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.cpp
deleted file mode 100644
index 17803d82821..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.cpp
+++ /dev/null
@@ -1,208 +0,0 @@
-/*
- * Copyright (C) 2007, 2008, 2011 Apple Inc. All rights reserved.
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
- * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
- * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-
-#include "config.h"
-#include "CSSSegmentedFontFaceCache.h"
-
-#include "FontFamilyNames.h"
-#include "core/css/CSSFontFace.h"
-#include "core/css/CSSFontFaceSource.h"
-#include "core/css/CSSFontSelector.h"
-#include "core/css/CSSSegmentedFontFace.h"
-#include "core/css/CSSValueList.h"
-#include "core/css/StyleRule.h"
-#include "core/fetch/FontResource.h"
-#include "core/fetch/ResourceFetcher.h"
-#include "platform/fonts/FontDescription.h"
-#include "wtf/text/AtomicString.h"
-
-namespace WebCore {
-
-CSSSegmentedFontFaceCache::CSSSegmentedFontFaceCache()
- : m_version(0)
-{
-}
-
-void CSSSegmentedFontFaceCache::add(CSSFontSelector* cssFontSelector, const StyleRuleFontFace* fontFaceRule, PassRefPtr<CSSFontFace> prpCssFontFace)
-{
- RefPtr<CSSFontFace> cssFontFace = prpCssFontFace;
-
- if (!m_styleRuleToFontFace.add(fontFaceRule, cssFontFace).isNewEntry)
- return;
-
- FontFace* fontFace = cssFontFace->fontFace();
-
- OwnPtr<TraitsMap>& familyFontFaces = m_fontFaces.add(fontFace->family(), nullptr).iterator->value;
- if (!familyFontFaces)
- familyFontFaces = adoptPtr(new TraitsMap);
-
- RefPtr<CSSSegmentedFontFace>& segmentedFontFace = familyFontFaces->add(fontFace->traitsMask(), 0).iterator->value;
- if (!segmentedFontFace)
- segmentedFontFace = CSSSegmentedFontFace::create(cssFontSelector, static_cast<FontTraitsMask>(fontFace->traitsMask()));
-
- segmentedFontFace->appendFontFace(cssFontFace);
-
- ++m_version;
-}
-
-void CSSSegmentedFontFaceCache::remove(const StyleRuleFontFace* fontFaceRule)
-{
- StyleRuleToFontFace::iterator styleRuleToFontFaceIter = m_styleRuleToFontFace.find(fontFaceRule);
- if (styleRuleToFontFaceIter == m_styleRuleToFontFace.end())
- return;
- RefPtr<CSSFontFace> cssFontFace = styleRuleToFontFaceIter->value;
-
- FamilyToTraitsMap::iterator fontFacesIter = m_fontFaces.find(cssFontFace->fontFace()->family());
- if (fontFacesIter == m_fontFaces.end())
- return;
- TraitsMap* familyFontFaces = fontFacesIter->value.get();
-
- TraitsMap::iterator familyFontFacesIter = familyFontFaces->find(cssFontFace->fontFace()->traitsMask());
- if (familyFontFacesIter == familyFontFaces->end())
- return;
- RefPtr<CSSSegmentedFontFace> segmentedFontFace = familyFontFacesIter->value;
-
- segmentedFontFace->removeFontFace(cssFontFace);
- if (segmentedFontFace->isEmpty()) {
- familyFontFaces->remove(familyFontFacesIter);
- if (familyFontFaces->isEmpty())
- m_fontFaces.remove(fontFacesIter);
- }
- m_styleRuleToFontFace.remove(styleRuleToFontFaceIter);
- m_fonts.clear();
- ++m_version;
-}
-
-static inline bool compareFontFaces(CSSSegmentedFontFace* first, CSSSegmentedFontFace* second, FontTraitsMask desiredTraitsMask)
-{
- FontTraitsMask firstTraitsMask = first->traitsMask();
- FontTraitsMask secondTraitsMask = second->traitsMask();
-
- bool firstHasDesiredVariant = firstTraitsMask & desiredTraitsMask & FontVariantMask;
- bool secondHasDesiredVariant = secondTraitsMask & desiredTraitsMask & FontVariantMask;
-
- if (firstHasDesiredVariant != secondHasDesiredVariant)
- return firstHasDesiredVariant;
-
- // We need to check font-variant css property for CSS2.1 compatibility.
- if (desiredTraitsMask & FontVariantSmallCapsMask) {
- // Prefer a font that has indicated that it can only support small-caps to a font that claims to support
- // all variants. The specialized font is more likely to be true small-caps and not require synthesis.
- bool firstRequiresSmallCaps = (firstTraitsMask & FontVariantSmallCapsMask) && !(firstTraitsMask & FontVariantNormalMask);
- bool secondRequiresSmallCaps = (secondTraitsMask & FontVariantSmallCapsMask) && !(secondTraitsMask & FontVariantNormalMask);
- if (firstRequiresSmallCaps != secondRequiresSmallCaps)
- return firstRequiresSmallCaps;
- }
-
- bool firstHasDesiredStyle = firstTraitsMask & desiredTraitsMask & FontStyleMask;
- bool secondHasDesiredStyle = secondTraitsMask & desiredTraitsMask & FontStyleMask;
-
- if (firstHasDesiredStyle != secondHasDesiredStyle)
- return firstHasDesiredStyle;
-
- if (desiredTraitsMask & FontStyleItalicMask) {
- // Prefer a font that has indicated that it can only support italics to a font that claims to support
- // all styles. The specialized font is more likely to be the one the author wants used.
- bool firstRequiresItalics = (firstTraitsMask & FontStyleItalicMask) && !(firstTraitsMask & FontStyleNormalMask);
- bool secondRequiresItalics = (secondTraitsMask & FontStyleItalicMask) && !(secondTraitsMask & FontStyleNormalMask);
- if (firstRequiresItalics != secondRequiresItalics)
- return firstRequiresItalics;
- }
-
- if (secondTraitsMask & desiredTraitsMask & FontWeightMask)
- return false;
- if (firstTraitsMask & desiredTraitsMask & FontWeightMask)
- return true;
-
- // http://www.w3.org/TR/2011/WD-css3-fonts-20111004/#font-matching-algorithm says :
- // - If the desired weight is less than 400, weights below the desired weight are checked in descending order followed by weights above the desired weight in ascending order until a match is found.
- // - If the desired weight is greater than 500, weights above the desired weight are checked in ascending order followed by weights below the desired weight in descending order until a match is found.
- // - If the desired weight is 400, 500 is checked first and then the rule for desired weights less than 400 is used.
- // - If the desired weight is 500, 400 is checked first and then the rule for desired weights less than 400 is used.
-
- static const unsigned fallbackRuleSets = 9;
- static const unsigned rulesPerSet = 8;
- static const FontTraitsMask weightFallbackRuleSets[fallbackRuleSets][rulesPerSet] = {
- { FontWeight200Mask, FontWeight300Mask, FontWeight400Mask, FontWeight500Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask },
- { FontWeight100Mask, FontWeight300Mask, FontWeight400Mask, FontWeight500Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask },
- { FontWeight200Mask, FontWeight100Mask, FontWeight400Mask, FontWeight500Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask },
- { FontWeight500Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask },
- { FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask, FontWeight600Mask, FontWeight700Mask, FontWeight800Mask, FontWeight900Mask },
- { FontWeight700Mask, FontWeight800Mask, FontWeight900Mask, FontWeight500Mask, FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask },
- { FontWeight800Mask, FontWeight900Mask, FontWeight600Mask, FontWeight500Mask, FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask },
- { FontWeight900Mask, FontWeight700Mask, FontWeight600Mask, FontWeight500Mask, FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask },
- { FontWeight800Mask, FontWeight700Mask, FontWeight600Mask, FontWeight500Mask, FontWeight400Mask, FontWeight300Mask, FontWeight200Mask, FontWeight100Mask }
- };
-
- unsigned ruleSetIndex = 0;
- unsigned w = FontWeight100Bit;
- while (!(desiredTraitsMask & (1 << w))) {
- w++;
- ruleSetIndex++;
- }
-
- ASSERT(ruleSetIndex < fallbackRuleSets);
- const FontTraitsMask* weightFallbackRule = weightFallbackRuleSets[ruleSetIndex];
- for (unsigned i = 0; i < rulesPerSet; ++i) {
- if (secondTraitsMask & weightFallbackRule[i])
- return false;
- if (firstTraitsMask & weightFallbackRule[i])
- return true;
- }
-
- return false;
-}
-
-CSSSegmentedFontFace* CSSSegmentedFontFaceCache::get(const FontDescription& fontDescription, const AtomicString& family)
-{
- TraitsMap* familyFontFaces = m_fontFaces.get(family);
- if (!familyFontFaces || familyFontFaces->isEmpty())
- return 0;
-
- OwnPtr<TraitsMap>& segmentedFontFaceCache = m_fonts.add(family, nullptr).iterator->value;
- if (!segmentedFontFaceCache)
- segmentedFontFaceCache = adoptPtr(new TraitsMap);
-
- FontTraitsMask traitsMask = fontDescription.traitsMask();
-
- RefPtr<CSSSegmentedFontFace>& face = segmentedFontFaceCache->add(traitsMask, 0).iterator->value;
- if (!face) {
- for (TraitsMap::const_iterator i = familyFontFaces->begin(); i != familyFontFaces->end(); ++i) {
- CSSSegmentedFontFace* candidate = i->value.get();
- unsigned candidateTraitsMask = candidate->traitsMask();
- if ((traitsMask & FontStyleNormalMask) && !(candidateTraitsMask & FontStyleNormalMask))
- continue;
- if ((traitsMask & FontVariantNormalMask) && !(candidateTraitsMask & FontVariantNormalMask))
- continue;
- if (!face || compareFontFaces(candidate, face.get(), traitsMask))
- face = candidate;
- }
- }
- return face.get();
-}
-
-}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSelector.cpp b/chromium/third_party/WebKit/Source/core/css/CSSSelector.cpp
index b744726355b..293cb2fd7f9 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSelector.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSelector.cpp
@@ -26,15 +26,18 @@
#include "config.h"
#include "core/css/CSSSelector.h"
-#include "HTMLNames.h"
-#include "RuntimeEnabledFeatures.h"
+#include "core/HTMLNames.h"
#include "core/css/CSSOMUtils.h"
#include "core/css/CSSSelectorList.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "wtf/Assertions.h"
#include "wtf/HashMap.h"
#include "wtf/StdLibExtras.h"
#include "wtf/text/StringBuilder.h"
-#include "wtf/text/StringHash.h"
+
+#ifndef NDEBUG
+#include <stdio.h>
+#endif
namespace WebCore {
@@ -52,8 +55,10 @@ void CSSSelector::createRareData()
ASSERT(m_match != Tag);
if (m_hasRareData)
return;
- // Move the value to the rare data stucture.
- m_data.m_rareData = RareData::create(adoptRef(m_data.m_value)).leakRef();
+ AtomicString value(m_data.m_value);
+ if (m_data.m_value)
+ m_data.m_value->deref();
+ m_data.m_rareData = RareData::create(value).leakRef();
m_hasRareData = true;
}
@@ -94,7 +99,7 @@ inline unsigned CSSSelector::specificityForOneSelector() const
case Id:
return 0x10000;
case PseudoClass:
- if (pseudoType() == PseudoHost)
+ if (pseudoType() == PseudoHost || pseudoType() == PseudoHostContext)
return 0;
// fall through.
case Exact:
@@ -183,12 +188,6 @@ PseudoId CSSSelector::pseudoId(PseudoType type)
return SCROLLBAR_TRACK_PIECE;
case PseudoResizer:
return RESIZER;
- case PseudoFullScreen:
- return FULL_SCREEN;
- case PseudoFullScreenDocument:
- return FULL_SCREEN_DOCUMENT;
- case PseudoFullScreenAncestor:
- return FULL_SCREEN_ANCESTOR;
case PseudoUnknown:
case PseudoEmpty:
case PseudoFirstChild:
@@ -250,11 +249,14 @@ PseudoId CSSSelector::pseudoId(PseudoType type)
case PseudoCue:
case PseudoFutureCue:
case PseudoPastCue:
- case PseudoSeamlessDocument:
- case PseudoDistributed:
case PseudoUnresolved:
case PseudoContent:
case PseudoHost:
+ case PseudoHostContext:
+ case PseudoShadow:
+ case PseudoFullScreen:
+ case PseudoFullScreenDocument:
+ case PseudoFullScreenAncestor:
return NOPSEUDO;
case PseudoNotParsed:
ASSERT_NOT_REACHED();
@@ -265,191 +267,168 @@ PseudoId CSSSelector::pseudoId(PseudoType type)
return NOPSEUDO;
}
-static HashMap<StringImpl*, CSSSelector::PseudoType>* nameToPseudoTypeMap()
+// Could be made smaller and faster by replacing pointer with an
+// offset into a string buffer and making the bit fields smaller but
+// that could not be maintained by hand.
+struct NameToPseudoStruct {
+ const char* string;
+ unsigned type:8;
+};
+
+// This table should be kept sorted.
+const static NameToPseudoStruct pseudoTypeMap[] = {
+{"-webkit-any(", CSSSelector::PseudoAny},
+{"-webkit-any-link", CSSSelector::PseudoAnyLink},
+{"-webkit-autofill", CSSSelector::PseudoAutofill},
+{"-webkit-drag", CSSSelector::PseudoDrag},
+{"-webkit-full-page-media", CSSSelector::PseudoFullPageMedia},
+{"-webkit-full-screen", CSSSelector::PseudoFullScreen},
+{"-webkit-full-screen-ancestor", CSSSelector::PseudoFullScreenAncestor},
+{"-webkit-full-screen-document", CSSSelector::PseudoFullScreenDocument},
+{"-webkit-resizer", CSSSelector::PseudoResizer},
+{"-webkit-scrollbar", CSSSelector::PseudoScrollbar},
+{"-webkit-scrollbar-button", CSSSelector::PseudoScrollbarButton},
+{"-webkit-scrollbar-corner", CSSSelector::PseudoScrollbarCorner},
+{"-webkit-scrollbar-thumb", CSSSelector::PseudoScrollbarThumb},
+{"-webkit-scrollbar-track", CSSSelector::PseudoScrollbarTrack},
+{"-webkit-scrollbar-track-piece", CSSSelector::PseudoScrollbarTrackPiece},
+{"active", CSSSelector::PseudoActive},
+{"after", CSSSelector::PseudoAfter},
+{"backdrop", CSSSelector::PseudoBackdrop},
+{"before", CSSSelector::PseudoBefore},
+{"checked", CSSSelector::PseudoChecked},
+{"content", CSSSelector::PseudoContent},
+{"corner-present", CSSSelector::PseudoCornerPresent},
+{"cue", CSSSelector::PseudoWebKitCustomElement},
+{"cue(", CSSSelector::PseudoCue},
+{"decrement", CSSSelector::PseudoDecrement},
+{"default", CSSSelector::PseudoDefault},
+{"disabled", CSSSelector::PseudoDisabled},
+{"double-button", CSSSelector::PseudoDoubleButton},
+{"empty", CSSSelector::PseudoEmpty},
+{"enabled", CSSSelector::PseudoEnabled},
+{"end", CSSSelector::PseudoEnd},
+{"first", CSSSelector::PseudoFirstPage},
+{"first-child", CSSSelector::PseudoFirstChild},
+{"first-letter", CSSSelector::PseudoFirstLetter},
+{"first-line", CSSSelector::PseudoFirstLine},
+{"first-of-type", CSSSelector::PseudoFirstOfType},
+{"focus", CSSSelector::PseudoFocus},
+{"future", CSSSelector::PseudoFutureCue},
+{"horizontal", CSSSelector::PseudoHorizontal},
+{"host", CSSSelector::PseudoHost},
+{"host(", CSSSelector::PseudoHost},
+{"host-context(", CSSSelector::PseudoHostContext},
+{"hover", CSSSelector::PseudoHover},
+{"in-range", CSSSelector::PseudoInRange},
+{"increment", CSSSelector::PseudoIncrement},
+{"indeterminate", CSSSelector::PseudoIndeterminate},
+{"invalid", CSSSelector::PseudoInvalid},
+{"lang(", CSSSelector::PseudoLang},
+{"last-child", CSSSelector::PseudoLastChild},
+{"last-of-type", CSSSelector::PseudoLastOfType},
+{"left", CSSSelector::PseudoLeftPage},
+{"link", CSSSelector::PseudoLink},
+{"no-button", CSSSelector::PseudoNoButton},
+{"not(", CSSSelector::PseudoNot},
+{"nth-child(", CSSSelector::PseudoNthChild},
+{"nth-last-child(", CSSSelector::PseudoNthLastChild},
+{"nth-last-of-type(", CSSSelector::PseudoNthLastOfType},
+{"nth-of-type(", CSSSelector::PseudoNthOfType},
+{"only-child", CSSSelector::PseudoOnlyChild},
+{"only-of-type", CSSSelector::PseudoOnlyOfType},
+{"optional", CSSSelector::PseudoOptional},
+{"out-of-range", CSSSelector::PseudoOutOfRange},
+{"past", CSSSelector::PseudoPastCue},
+{"read-only", CSSSelector::PseudoReadOnly},
+{"read-write", CSSSelector::PseudoReadWrite},
+{"required", CSSSelector::PseudoRequired},
+{"right", CSSSelector::PseudoRightPage},
+{"root", CSSSelector::PseudoRoot},
+{"scope", CSSSelector::PseudoScope},
+{"selection", CSSSelector::PseudoSelection},
+{"shadow", CSSSelector::PseudoShadow},
+{"single-button", CSSSelector::PseudoSingleButton},
+{"start", CSSSelector::PseudoStart},
+{"target", CSSSelector::PseudoTarget},
+{"unresolved", CSSSelector::PseudoUnresolved},
+{"valid", CSSSelector::PseudoValid},
+{"vertical", CSSSelector::PseudoVertical},
+{"visited", CSSSelector::PseudoVisited},
+{"window-inactive", CSSSelector::PseudoWindowInactive},
+};
+
+class NameToPseudoCompare {
+public:
+ NameToPseudoCompare(const AtomicString& key) : m_key(key) { ASSERT(m_key.is8Bit()); }
+
+ bool operator()(const NameToPseudoStruct& entry, const NameToPseudoStruct&)
+ {
+ ASSERT(entry.string);
+ const char* key = reinterpret_cast<const char*>(m_key.characters8());
+ // If strncmp returns 0, then either the keys are equal, or |m_key| sorts before |entry|.
+ return strncmp(entry.string, key, m_key.length()) < 0;
+ }
+
+private:
+ const AtomicString& m_key;
+};
+
+static CSSSelector::PseudoType nameToPseudoType(const AtomicString& name)
{
- DEFINE_STATIC_LOCAL(AtomicString, active, ("active", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, after, ("after", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, any, ("-webkit-any(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, anyLink, ("-webkit-any-link", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, autofill, ("-webkit-autofill", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, backdrop, ("backdrop", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, before, ("before", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, checked, ("checked", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, defaultString, ("default", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, disabled, ("disabled", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, readOnly, ("read-only", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, readWrite, ("read-write", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, valid, ("valid", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, invalid, ("invalid", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, drag, ("-webkit-drag", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, empty, ("empty", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, enabled, ("enabled", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, firstChild, ("first-child", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, firstLetter, ("first-letter", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, firstLine, ("first-line", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, firstOfType, ("first-of-type", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, fullPageMedia, ("-webkit-full-page-media", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, nthChild, ("nth-child(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, nthOfType, ("nth-of-type(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, nthLastChild, ("nth-last-child(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, nthLastOfType, ("nth-last-of-type(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, focus, ("focus", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, hover, ("hover", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, indeterminate, ("indeterminate", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, lastChild, ("last-child", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, lastOfType, ("last-of-type", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, link, ("link", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, lang, ("lang(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, notStr, ("not(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, onlyChild, ("only-child", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, onlyOfType, ("only-of-type", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, optional, ("optional", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, required, ("required", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, resizer, ("-webkit-resizer", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, root, ("root", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scrollbar, ("-webkit-scrollbar", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scrollbarButton, ("-webkit-scrollbar-button", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scrollbarCorner, ("-webkit-scrollbar-corner", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scrollbarThumb, ("-webkit-scrollbar-thumb", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scrollbarTrack, ("-webkit-scrollbar-track", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scrollbarTrackPiece, ("-webkit-scrollbar-track-piece", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, selection, ("selection", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, target, ("target", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, visited, ("visited", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, windowInactive, ("window-inactive", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, decrement, ("decrement", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, increment, ("increment", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, start, ("start", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, end, ("end", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, horizontal, ("horizontal", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, vertical, ("vertical", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, doubleButton, ("double-button", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, singleButton, ("single-button", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, noButton, ("no-button", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, cornerPresent, ("corner-present", AtomicString::ConstructFromLiteral));
- // Paged Media pseudo-classes
- DEFINE_STATIC_LOCAL(AtomicString, firstPage, ("first", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, leftPage, ("left", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, rightPage, ("right", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, fullScreen, ("-webkit-full-screen", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, fullScreenDocument, ("-webkit-full-screen-document", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, fullScreenAncestor, ("-webkit-full-screen-ancestor", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, cue, ("cue(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, cueWithoutParen, ("cue", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, futureCue, ("future", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, pastCue, ("past", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, seamlessDocument, ("-webkit-seamless-document", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, distributed, ("-webkit-distributed(", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, inRange, ("in-range", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, outOfRange, ("out-of-range", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, scope, ("scope", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, unresolved, ("unresolved", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, content, ("content", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, host, ("host", AtomicString::ConstructFromLiteral));
- DEFINE_STATIC_LOCAL(AtomicString, hostWithParams, ("host(", AtomicString::ConstructFromLiteral));
-
- static HashMap<StringImpl*, CSSSelector::PseudoType>* nameToPseudoType = 0;
- if (!nameToPseudoType) {
- nameToPseudoType = new HashMap<StringImpl*, CSSSelector::PseudoType>;
- nameToPseudoType->set(active.impl(), CSSSelector::PseudoActive);
- nameToPseudoType->set(after.impl(), CSSSelector::PseudoAfter);
- nameToPseudoType->set(anyLink.impl(), CSSSelector::PseudoAnyLink);
- nameToPseudoType->set(any.impl(), CSSSelector::PseudoAny);
- nameToPseudoType->set(autofill.impl(), CSSSelector::PseudoAutofill);
- nameToPseudoType->set(backdrop.impl(), CSSSelector::PseudoBackdrop);
- nameToPseudoType->set(before.impl(), CSSSelector::PseudoBefore);
- nameToPseudoType->set(checked.impl(), CSSSelector::PseudoChecked);
- nameToPseudoType->set(defaultString.impl(), CSSSelector::PseudoDefault);
- nameToPseudoType->set(disabled.impl(), CSSSelector::PseudoDisabled);
- nameToPseudoType->set(readOnly.impl(), CSSSelector::PseudoReadOnly);
- nameToPseudoType->set(readWrite.impl(), CSSSelector::PseudoReadWrite);
- nameToPseudoType->set(valid.impl(), CSSSelector::PseudoValid);
- nameToPseudoType->set(invalid.impl(), CSSSelector::PseudoInvalid);
- nameToPseudoType->set(drag.impl(), CSSSelector::PseudoDrag);
- nameToPseudoType->set(enabled.impl(), CSSSelector::PseudoEnabled);
- nameToPseudoType->set(empty.impl(), CSSSelector::PseudoEmpty);
- nameToPseudoType->set(firstChild.impl(), CSSSelector::PseudoFirstChild);
- nameToPseudoType->set(fullPageMedia.impl(), CSSSelector::PseudoFullPageMedia);
- nameToPseudoType->set(lastChild.impl(), CSSSelector::PseudoLastChild);
- nameToPseudoType->set(lastOfType.impl(), CSSSelector::PseudoLastOfType);
- nameToPseudoType->set(onlyChild.impl(), CSSSelector::PseudoOnlyChild);
- nameToPseudoType->set(onlyOfType.impl(), CSSSelector::PseudoOnlyOfType);
- nameToPseudoType->set(firstLetter.impl(), CSSSelector::PseudoFirstLetter);
- nameToPseudoType->set(firstLine.impl(), CSSSelector::PseudoFirstLine);
- nameToPseudoType->set(firstOfType.impl(), CSSSelector::PseudoFirstOfType);
- nameToPseudoType->set(focus.impl(), CSSSelector::PseudoFocus);
- nameToPseudoType->set(hover.impl(), CSSSelector::PseudoHover);
- nameToPseudoType->set(indeterminate.impl(), CSSSelector::PseudoIndeterminate);
- nameToPseudoType->set(link.impl(), CSSSelector::PseudoLink);
- nameToPseudoType->set(lang.impl(), CSSSelector::PseudoLang);
- nameToPseudoType->set(notStr.impl(), CSSSelector::PseudoNot);
- nameToPseudoType->set(nthChild.impl(), CSSSelector::PseudoNthChild);
- nameToPseudoType->set(nthOfType.impl(), CSSSelector::PseudoNthOfType);
- nameToPseudoType->set(nthLastChild.impl(), CSSSelector::PseudoNthLastChild);
- nameToPseudoType->set(nthLastOfType.impl(), CSSSelector::PseudoNthLastOfType);
- nameToPseudoType->set(root.impl(), CSSSelector::PseudoRoot);
- nameToPseudoType->set(windowInactive.impl(), CSSSelector::PseudoWindowInactive);
- nameToPseudoType->set(decrement.impl(), CSSSelector::PseudoDecrement);
- nameToPseudoType->set(increment.impl(), CSSSelector::PseudoIncrement);
- nameToPseudoType->set(start.impl(), CSSSelector::PseudoStart);
- nameToPseudoType->set(end.impl(), CSSSelector::PseudoEnd);
- nameToPseudoType->set(horizontal.impl(), CSSSelector::PseudoHorizontal);
- nameToPseudoType->set(vertical.impl(), CSSSelector::PseudoVertical);
- nameToPseudoType->set(doubleButton.impl(), CSSSelector::PseudoDoubleButton);
- nameToPseudoType->set(singleButton.impl(), CSSSelector::PseudoSingleButton);
- nameToPseudoType->set(noButton.impl(), CSSSelector::PseudoNoButton);
- nameToPseudoType->set(optional.impl(), CSSSelector::PseudoOptional);
- nameToPseudoType->set(required.impl(), CSSSelector::PseudoRequired);
- nameToPseudoType->set(resizer.impl(), CSSSelector::PseudoResizer);
- nameToPseudoType->set(scope.impl(), CSSSelector::PseudoScope);
- nameToPseudoType->set(scrollbar.impl(), CSSSelector::PseudoScrollbar);
- nameToPseudoType->set(scrollbarButton.impl(), CSSSelector::PseudoScrollbarButton);
- nameToPseudoType->set(scrollbarCorner.impl(), CSSSelector::PseudoScrollbarCorner);
- nameToPseudoType->set(scrollbarThumb.impl(), CSSSelector::PseudoScrollbarThumb);
- nameToPseudoType->set(scrollbarTrack.impl(), CSSSelector::PseudoScrollbarTrack);
- nameToPseudoType->set(scrollbarTrackPiece.impl(), CSSSelector::PseudoScrollbarTrackPiece);
- nameToPseudoType->set(cornerPresent.impl(), CSSSelector::PseudoCornerPresent);
- nameToPseudoType->set(selection.impl(), CSSSelector::PseudoSelection);
- nameToPseudoType->set(target.impl(), CSSSelector::PseudoTarget);
- nameToPseudoType->set(visited.impl(), CSSSelector::PseudoVisited);
- nameToPseudoType->set(firstPage.impl(), CSSSelector::PseudoFirstPage);
- nameToPseudoType->set(leftPage.impl(), CSSSelector::PseudoLeftPage);
- nameToPseudoType->set(rightPage.impl(), CSSSelector::PseudoRightPage);
- nameToPseudoType->set(fullScreen.impl(), CSSSelector::PseudoFullScreen);
- nameToPseudoType->set(fullScreenDocument.impl(), CSSSelector::PseudoFullScreenDocument);
- nameToPseudoType->set(fullScreenAncestor.impl(), CSSSelector::PseudoFullScreenAncestor);
- nameToPseudoType->set(cue.impl(), CSSSelector::PseudoCue);
- nameToPseudoType->set(cueWithoutParen.impl(), CSSSelector::PseudoWebKitCustomElement);
- nameToPseudoType->set(futureCue.impl(), CSSSelector::PseudoFutureCue);
- nameToPseudoType->set(pastCue.impl(), CSSSelector::PseudoPastCue);
- nameToPseudoType->set(seamlessDocument.impl(), CSSSelector::PseudoSeamlessDocument);
- nameToPseudoType->set(distributed.impl(), CSSSelector::PseudoDistributed);
- nameToPseudoType->set(inRange.impl(), CSSSelector::PseudoInRange);
- nameToPseudoType->set(outOfRange.impl(), CSSSelector::PseudoOutOfRange);
- if (RuntimeEnabledFeatures::shadowDOMEnabled()) {
- nameToPseudoType->set(host.impl(), CSSSelector::PseudoHost);
- nameToPseudoType->set(hostWithParams.impl(), CSSSelector::PseudoHost);
- nameToPseudoType->set(content.impl(), CSSSelector::PseudoContent);
- }
- if (RuntimeEnabledFeatures::customElementsEnabled())
- nameToPseudoType->set(unresolved.impl(), CSSSelector::PseudoUnresolved);
+ if (name.isNull() || !name.is8Bit())
+ return CSSSelector::PseudoUnknown;
+
+ const NameToPseudoStruct* pseudoTypeMapEnd = pseudoTypeMap + WTF_ARRAY_LENGTH(pseudoTypeMap);
+ NameToPseudoStruct dummyKey = { 0, CSSSelector::PseudoUnknown };
+ const NameToPseudoStruct* match = std::lower_bound(pseudoTypeMap, pseudoTypeMapEnd, dummyKey, NameToPseudoCompare(name));
+ if (match == pseudoTypeMapEnd || match->string != name.string())
+ return CSSSelector::PseudoUnknown;
+
+ return static_cast<CSSSelector::PseudoType>(match->type);
+}
+
+#ifndef NDEBUG
+void CSSSelector::show(int indent) const
+{
+ printf("%*sselectorText(): %s\n", indent, "", selectorText().ascii().data());
+ printf("%*sm_match: %d\n", indent, "", m_match);
+ printf("%*sisCustomPseudoElement(): %d\n", indent, "", isCustomPseudoElement());
+ if (m_match != Tag)
+ printf("%*svalue(): %s\n", indent, "", value().ascii().data());
+ printf("%*spseudoType(): %d\n", indent, "", pseudoType());
+ if (m_match == Tag)
+ printf("%*stagQName().localName: %s\n", indent, "", tagQName().localName().ascii().data());
+ printf("%*sisAttributeSelector(): %d\n", indent, "", isAttributeSelector());
+ if (isAttributeSelector())
+ printf("%*sattribute(): %s\n", indent, "", attribute().localName().ascii().data());
+ printf("%*sargument(): %s\n", indent, "", argument().ascii().data());
+ printf("%*sspecificity(): %u\n", indent, "", specificity());
+ if (tagHistory()) {
+ printf("\n%*s--> (relation == %d)\n", indent, "", relation());
+ tagHistory()->show(indent + 2);
+ } else {
+ printf("\n%*s--> (relation == %d)\n", indent, "", relation());
}
- return nameToPseudoType;
}
-CSSSelector::PseudoType CSSSelector::parsePseudoType(const AtomicString& name)
+void CSSSelector::show() const
{
- if (name.isNull())
- return PseudoUnknown;
- HashMap<StringImpl*, CSSSelector::PseudoType>* nameToPseudoType = nameToPseudoTypeMap();
- HashMap<StringImpl*, CSSSelector::PseudoType>::iterator slot = nameToPseudoType->find(name.impl());
+ printf("\n******* CSSSelector::show(\"%s\") *******\n", selectorText().ascii().data());
+ show(2);
+ printf("******* end *******\n");
+}
+#endif
- if (slot != nameToPseudoType->end())
- return slot->value;
+CSSSelector::PseudoType CSSSelector::parsePseudoType(const AtomicString& name)
+{
+ CSSSelector::PseudoType pseudoType = nameToPseudoType(name);
+ if (pseudoType != PseudoUnknown)
+ return pseudoType;
if (name.startsWith("-webkit-"))
return PseudoWebKitCustomElement;
- if (name.startsWith("x-") || name.startsWith("cue"))
+ if (name.startsWith("cue"))
return PseudoUserAgentCustomElement;
return PseudoUnknown;
@@ -474,7 +453,6 @@ void CSSSelector::extractPseudoType() const
case PseudoFirstLine:
compat = true;
case PseudoBackdrop:
- case PseudoDistributed:
case PseudoResizer:
case PseudoScrollbar:
case PseudoScrollbarCorner:
@@ -486,6 +464,7 @@ void CSSSelector::extractPseudoType() const
case PseudoUserAgentCustomElement:
case PseudoWebKitCustomElement:
case PseudoContent:
+ case PseudoShadow:
element = true;
break;
case PseudoUnknown:
@@ -543,12 +522,12 @@ void CSSSelector::extractPseudoType() const
case PseudoFullScreen:
case PseudoFullScreenDocument:
case PseudoFullScreenAncestor:
- case PseudoSeamlessDocument:
case PseudoInRange:
case PseudoOutOfRange:
case PseudoFutureCue:
case PseudoPastCue:
case PseudoHost:
+ case PseudoHostContext:
case PseudoUnresolved:
break;
case PseudoFirstPage:
@@ -640,7 +619,7 @@ String CSSSelector::selectorText(const String& rightSide) const
break;
case PseudoAny: {
const CSSSelector* firstSubSelector = cs->selectorList()->first();
- for (const CSSSelector* subSelector = firstSubSelector; subSelector; subSelector = CSSSelectorList::next(subSelector)) {
+ for (const CSSSelector* subSelector = firstSubSelector; subSelector; subSelector = CSSSelectorList::next(*subSelector)) {
if (subSelector != firstSubSelector)
str.append(',');
str.append(subSelector->selectorText());
@@ -648,10 +627,11 @@ String CSSSelector::selectorText(const String& rightSide) const
str.append(')');
break;
}
- case PseudoHost: {
+ case PseudoHost:
+ case PseudoHostContext: {
if (cs->selectorList()) {
const CSSSelector* firstSubSelector = cs->selectorList()->first();
- for (const CSSSelector* subSelector = firstSubSelector; subSelector; subSelector = CSSSelectorList::next(subSelector)) {
+ for (const CSSSelector* subSelector = firstSubSelector; subSelector; subSelector = CSSSelectorList::next(*subSelector)) {
if (subSelector != firstSubSelector)
str.append(',');
str.append(subSelector->selectorText());
@@ -718,17 +698,11 @@ String CSSSelector::selectorText(const String& rightSide) const
if (const CSSSelector* tagHistory = cs->tagHistory()) {
switch (cs->relation()) {
case CSSSelector::Descendant:
- if (cs->relationIsAffectedByPseudoContent() && tagHistory->pseudoType() != CSSSelector::PseudoContent)
- return tagHistory->selectorText("::-webkit-distributed(" + str.toString() + rightSide + ")");
return tagHistory->selectorText(" " + str.toString() + rightSide);
case CSSSelector::Child:
- if (cs->relationIsAffectedByPseudoContent() && tagHistory->pseudoType() != CSSSelector::PseudoContent)
- return tagHistory->selectorText("::-webkit-distributed(> " + str.toString() + rightSide + ")");
return tagHistory->selectorText(" > " + str.toString() + rightSide);
- case CSSSelector::ChildTree:
- return tagHistory->selectorText(" ^ " + str.toString() + rightSide);
- case CSSSelector::DescendantTree:
- return tagHistory->selectorText(" ^^ " + str.toString() + rightSide);
+ case CSSSelector::ShadowDeep:
+ return tagHistory->selectorText(" /deep/ " + str.toString() + rightSide);
case CSSSelector::DirectAdjacent:
return tagHistory->selectorText(" + " + str.toString() + rightSide);
case CSSSelector::IndirectAdjacent:
@@ -762,7 +736,7 @@ void CSSSelector::setSelectorList(PassOwnPtr<CSSSelectorList> selectorList)
static bool validateSubSelector(const CSSSelector* selector)
{
- switch (selector->m_match) {
+ switch (selector->match()) {
case CSSSelector::Tag:
case CSSSelector::Id:
case CSSSelector::Class:
@@ -775,6 +749,7 @@ static bool validateSubSelector(const CSSSelector* selector)
case CSSSelector::End:
return true;
case CSSSelector::PseudoElement:
+ case CSSSelector::Unknown:
return false;
case CSSSelector::PagePseudoClass:
case CSSSelector::PseudoClass:
@@ -800,6 +775,8 @@ static bool validateSubSelector(const CSSSelector* selector)
case CSSSelector::PseudoLastOfType:
case CSSSelector::PseudoOnlyOfType:
case CSSSelector::PseudoHost:
+ case CSSSelector::PseudoHostContext:
+ case CSSSelector::PseudoNot:
return true;
default:
return false;
@@ -843,8 +820,8 @@ bool CSSSelector::matchNth(int count) const
return m_data.m_rareData->matchNth(count);
}
-CSSSelector::RareData::RareData(PassRefPtr<StringImpl> value)
- : m_value(value.leakRef())
+CSSSelector::RareData::RareData(const AtomicString& value)
+ : m_value(value)
, m_a(0)
, m_b(0)
, m_attribute(anyQName())
@@ -854,8 +831,6 @@ CSSSelector::RareData::RareData(PassRefPtr<StringImpl> value)
CSSSelector::RareData::~RareData()
{
- if (m_value)
- m_value->deref();
}
// a helper function for parsing nth-arguments
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSelector.h b/chromium/third_party/WebKit/Source/core/css/CSSSelector.h
index b0094687fb6..254ae9c5bb7 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSelector.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSelector.h
@@ -30,7 +30,57 @@
namespace WebCore {
class CSSSelectorList;
- // this class represents a selector for a StyleRule
+ // This class represents a selector for a StyleRule.
+
+ // CSS selector representation is somewhat complicated and subtle. A representative list of selectors is
+ // in CSSSelectorTest; run it in a debug build to see useful debugging output.
+ //
+ // ** tagHistory() and relation():
+ //
+ // Selectors are represented as a linked list of simple selectors (defined more or less according to
+ // http://www.w3.org/TR/css3-selectors/#simple-selectors-dfn). The tagHistory() method returns the next
+ // simple selector in the list. The relation() method returns the relationship of the current simple selector to
+ // the one in tagHistory(). For example, the CSS selector .a.b #c is represented as:
+ //
+ // selectorText(): .a.b #c
+ // --> (relation == Descendant)
+ // selectorText(): .a.b
+ // --> (relation == SubSelector)
+ // selectorText(): .b
+ //
+ // Note that currently a bare selector such as ".a" has a relation() of Descendant. This is a bug - instead the relation should be
+ // "None".
+ //
+ // The order of tagHistory() varies depending on the situation.
+ // * Relations using combinators (http://www.w3.org/TR/css3-selectors/#combinators), such as descendant, sibling, etc., are parsed
+ // right-to-left (in the example above, this is why .c is earlier in the tagHistory() chain than .a.b).
+ // * SubSelector relations are parsed left-to-right in most cases (such as the .a.b example above); a counter-example is the
+ // ::content pseudo-element. Most (all?) other pseudo elements and pseudo classes are parsed left-to-right.
+ // * ShadowPseudo relations are parsed right-to-left. Example: summary::-webkit-details-marker is parsed as:
+ // selectorText(): summary::-webkit-details-marker
+ // --> (relation == ShadowPseudo)
+ // selectorText(): summary
+ //
+ // ** match():
+ //
+ // The match of the current simple selector tells us the type of selector, such as class, id, tagname, or pseudo-class.
+ // Inline comments in the Match enum give examples of when each type would occur.
+ //
+ // ** value(), attribute():
+ //
+ // value() tells you the value of the simple selector. For example, for class selectors, value() will tell you the class string,
+ // and for id selectors it will tell you the id(). See below for the special case of attribute selectors.
+ //
+ // ** Attribute selectors.
+ //
+ // Attribute selectors return the attribute name in the attribute() method. The value() method returns the value matched against
+ // in case of selectors like [attr="value"].
+ //
+ // ** isCustomPseudoElement():
+ //
+ // It appears this is used only for pseudo elements that appear in user-agent shadow DOM. They are not exposed to author-created
+ // shadow DOM.
+
class CSSSelector {
WTF_MAKE_FAST_ALLOCATED;
public:
@@ -50,36 +100,37 @@ namespace WebCore {
// tag == -1 means apply to all elements (Selector = *)
+ // http://www.w3.org/TR/css3-selectors/#specificity
+ // We use 256 as the base of the specificity number system.
unsigned specificity() const;
/* how the attribute value has to match.... Default is Exact */
enum Match {
Unknown = 0,
- Tag,
- Id,
- Class,
- Exact,
- Set,
- List,
- Hyphen,
- PseudoClass,
- PseudoElement,
+ Tag, // Example: div
+ Id, // Example: #id
+ Class, // example: .class
+ PseudoClass, // Example: :nth-child(2)
+ PseudoElement, // Example: ::first-line
+ PagePseudoClass, // ??
+ Exact, // Example: E[foo="bar"]
+ Set, // Example: E[foo]
+ Hyphen, // Example: E[foo|="bar"]
+ List, // Example: E[foo~="bar"]
Contain, // css3: E[foo*="bar"]
Begin, // css3: E[foo^="bar"]
End, // css3: E[foo$="bar"]
- PagePseudoClass
+ FirstAttributeSelectorMatch = Exact,
};
enum Relation {
- Descendant = 0,
- Child,
- DirectAdjacent,
- IndirectAdjacent,
- SubSelector,
- ShadowPseudo,
- // FIXME: rename ChildTree and DescendantTree when the spec for this is written down.
- ChildTree,
- DescendantTree
+ Descendant = 0, // "Space" combinator
+ Child, // > combinator
+ DirectAdjacent, // + combinator
+ IndirectAdjacent, // ~ combinator
+ SubSelector, // "No space" combinator
+ ShadowPseudo, // Special case of shadow DOM pseudo elements / shadow pseudo element
+ ShadowDeep // /deep/ combinator
};
enum PseudoType {
@@ -161,11 +212,11 @@ namespace WebCore {
PseudoCue,
PseudoFutureCue,
PseudoPastCue,
- PseudoSeamlessDocument,
- PseudoDistributed,
PseudoUnresolved,
PseudoContent,
- PseudoHost
+ PseudoHost,
+ PseudoHostContext,
+ PseudoShadow
};
enum MarginBoxType {
@@ -210,9 +261,15 @@ namespace WebCore {
// how you use the returned QualifiedName.
// http://www.w3.org/TR/css3-selectors/#attrnmsp
const QualifiedName& attribute() const;
+ // Returns the argument of a parameterized selector. For example, nth-child(2) would have an argument of 2.
const AtomicString& argument() const { return m_hasRareData ? m_data.m_rareData->m_argument : nullAtom; }
const CSSSelectorList* selectorList() const { return m_hasRareData ? m_data.m_rareData->m_selectorList.get() : 0; }
+#ifndef NDEBUG
+ void show() const;
+ void show(int indent) const;
+#endif
+
void setValue(const AtomicString&);
void setAttribute(const QualifiedName&);
void setArgument(const AtomicString&);
@@ -228,11 +285,25 @@ namespace WebCore {
bool isDirectAdjacentSelector() const { return m_relation == DirectAdjacent; }
bool isSiblingSelector() const;
bool isAttributeSelector() const;
- bool isDistributedPseudoElement() const;
bool isContentPseudoElement() const;
+ bool isShadowPseudoElement() const;
bool isHostPseudoClass() const;
+ // FIXME: selectors with no tagHistory() get a relation() of Descendant (and sometimes even SubSelector). It should instead be
+ // None.
Relation relation() const { return static_cast<Relation>(m_relation); }
+ void setRelation(Relation relation)
+ {
+ m_relation = relation;
+ ASSERT(static_cast<Relation>(m_relation) == relation); // using a bitfield.
+ }
+
+ Match match() const { return static_cast<Match>(m_match); }
+ void setMatch(Match match)
+ {
+ m_match = match;
+ ASSERT(static_cast<Match>(m_match) == match); // using a bitfield.
+ }
bool isLastInSelectorList() const { return m_isLastInSelectorList; }
void setLastInSelectorList() { m_isLastInSelectorList = true; }
@@ -248,11 +319,10 @@ namespace WebCore {
bool relationIsAffectedByPseudoContent() const { return m_relationIsAffectedByPseudoContent; }
void setRelationIsAffectedByPseudoContent() { m_relationIsAffectedByPseudoContent = true; }
+ private:
unsigned m_relation : 3; // enum Relation
mutable unsigned m_match : 4; // enum Match
mutable unsigned m_pseudoType : 8; // PseudoType
-
- private:
mutable unsigned m_parsedNth : 1; // Used for :nth-*
unsigned m_isLastInSelectorList : 1;
unsigned m_isLastInTagHistory : 1;
@@ -269,13 +339,13 @@ namespace WebCore {
CSSSelector& operator=(const CSSSelector&);
struct RareData : public RefCounted<RareData> {
- static PassRefPtr<RareData> create(PassRefPtr<StringImpl> value) { return adoptRef(new RareData(value)); }
+ static PassRefPtr<RareData> create(const AtomicString& value) { return adoptRef(new RareData(value)); }
~RareData();
bool parseNth();
bool matchNth(int count);
- StringImpl* m_value; // Plain pointer to keep things uniform with the union.
+ AtomicString m_value;
int m_a; // Used for :nth-*
int m_b; // Used for :nth-*
QualifiedName m_attribute; // used for attribute selector
@@ -283,7 +353,7 @@ namespace WebCore {
OwnPtr<CSSSelectorList> m_selectorList; // Used for :-webkit-any and :not
private:
- RareData(PassRefPtr<StringImpl> value);
+ RareData(const AtomicString& value);
};
void createRareData();
@@ -321,7 +391,7 @@ inline bool CSSSelector::isCustomPseudoElement() const
inline bool CSSSelector::isHostPseudoClass() const
{
- return m_match == PseudoClass && m_pseudoType == PseudoHost;
+ return m_match == PseudoClass && (m_pseudoType == PseudoHost || m_pseudoType == PseudoHostContext);
}
inline bool CSSSelector::isSiblingSelector() const
@@ -344,23 +414,17 @@ inline bool CSSSelector::isSiblingSelector() const
inline bool CSSSelector::isAttributeSelector() const
{
- return m_match == CSSSelector::Exact
- || m_match == CSSSelector::Set
- || m_match == CSSSelector::List
- || m_match == CSSSelector::Hyphen
- || m_match == CSSSelector::Contain
- || m_match == CSSSelector::Begin
- || m_match == CSSSelector::End;
+ return m_match >= FirstAttributeSelectorMatch;
}
-inline bool CSSSelector::isDistributedPseudoElement() const
+inline bool CSSSelector::isContentPseudoElement() const
{
- return m_match == PseudoElement && pseudoType() == PseudoDistributed;
+ return m_match == PseudoElement && pseudoType() == PseudoContent;
}
-inline bool CSSSelector::isContentPseudoElement() const
+inline bool CSSSelector::isShadowPseudoElement() const
{
- return m_match == PseudoElement && pseudoType() == PseudoContent;
+ return m_match == PseudoElement && pseudoType() == PseudoShadow;
}
inline void CSSSelector::setValue(const AtomicString& value)
@@ -369,10 +433,7 @@ inline void CSSSelector::setValue(const AtomicString& value)
ASSERT(m_pseudoType == PseudoNotParsed);
// Need to do ref counting manually for the union.
if (m_hasRareData) {
- if (m_data.m_rareData->m_value)
- m_data.m_rareData->m_value->deref();
- m_data.m_rareData->m_value = value.impl();
- m_data.m_rareData->m_value->ref();
+ m_data.m_rareData->m_value = value;
return;
}
if (m_data.m_value)
@@ -454,12 +515,13 @@ inline const QualifiedName& CSSSelector::tagQName() const
inline const AtomicString& CSSSelector::value() const
{
ASSERT(m_match != Tag);
+ if (m_hasRareData)
+ return m_data.m_rareData->m_value;
// AtomicString is really just a StringImpl* so the cast below is safe.
// FIXME: Perhaps call sites could be changed to accept StringImpl?
- return *reinterpret_cast<const AtomicString*>(m_hasRareData ? &m_data.m_rareData->m_value : &m_data.m_value);
+ return *reinterpret_cast<const AtomicString*>(&m_data.m_value);
}
-
} // namespace WebCore
#endif // CSSSelector_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.cpp b/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.cpp
index a3b8bdc7c12..2710a0f2e42 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.cpp
@@ -112,7 +112,7 @@ String CSSSelectorList::selectorsText() const
{
StringBuilder result;
- for (const CSSSelector* s = first(); s; s = next(s)) {
+ for (const CSSSelector* s = first(); s; s = next(*s)) {
if (s != first())
result.append(", ");
result.append(s->selectorText());
@@ -122,20 +122,19 @@ String CSSSelectorList::selectorsText() const
}
template <typename Functor>
-static bool forEachTagSelector(Functor& functor, const CSSSelector* selector)
+static bool forEachTagSelector(Functor& functor, const CSSSelector& selector)
{
- ASSERT(selector);
-
+ const CSSSelector* current = &selector;
do {
- if (functor(selector))
+ if (functor(*current))
return true;
- if (const CSSSelectorList* selectorList = selector->selectorList()) {
- for (const CSSSelector* subSelector = selectorList->first(); subSelector; subSelector = CSSSelectorList::next(subSelector)) {
- if (forEachTagSelector(functor, subSelector))
+ if (const CSSSelectorList* selectorList = current->selectorList()) {
+ for (const CSSSelector* subSelector = selectorList->first(); subSelector; subSelector = CSSSelectorList::next(*subSelector)) {
+ if (forEachTagSelector(functor, *subSelector))
return true;
}
}
- } while ((selector = selector->tagHistory()));
+ } while ((current = current->tagHistory()));
return false;
}
@@ -143,8 +142,8 @@ static bool forEachTagSelector(Functor& functor, const CSSSelector* selector)
template <typename Functor>
static bool forEachSelector(Functor& functor, const CSSSelectorList* selectorList)
{
- for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(selector)) {
- if (forEachTagSelector(functor, selector))
+ for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(*selector)) {
+ if (forEachTagSelector(functor, *selector))
return true;
}
@@ -153,11 +152,11 @@ static bool forEachSelector(Functor& functor, const CSSSelectorList* selectorLis
class SelectorNeedsNamespaceResolutionFunctor {
public:
- bool operator()(const CSSSelector* selector)
+ bool operator()(const CSSSelector& selector)
{
- if (selector->m_match == CSSSelector::Tag && selector->tagQName().prefix() != nullAtom && selector->tagQName().prefix() != starAtom)
+ if (selector.match() == CSSSelector::Tag && selector.tagQName().prefix() != nullAtom && selector.tagQName().prefix() != starAtom)
return true;
- if (selector->isAttributeSelector() && selector->attribute().prefix() != nullAtom && selector->attribute().prefix() != starAtom)
+ if (selector.isAttributeSelector() && selector.attribute().prefix() != nullAtom && selector.attribute().prefix() != starAtom)
return true;
return false;
}
@@ -171,9 +170,9 @@ bool CSSSelectorList::selectorsNeedNamespaceResolution()
class SelectorHasShadowDistributed {
public:
- bool operator()(const CSSSelector* selector)
+ bool operator()(const CSSSelector& selector)
{
- return selector->relationIsAffectedByPseudoContent();
+ return selector.relationIsAffectedByPseudoContent();
}
};
@@ -183,17 +182,17 @@ bool CSSSelectorList::hasShadowDistributedAt(size_t index) const
return forEachTagSelector(functor, selectorAt(index));
}
-class SelectorHasCombinatorCrossingTreeBoundary {
+class SelectorCrossesTreeScopes {
public:
- bool operator()(const CSSSelector* selector)
+ bool operator()(const CSSSelector& selector)
{
- return selector->relation() == CSSSelector::ChildTree || selector->relation() == CSSSelector::DescendantTree;
+ return selector.relation() == CSSSelector::ShadowDeep || selector.isShadowPseudoElement();
}
};
-bool CSSSelectorList::hasCombinatorCrossingTreeBoundaryAt(size_t index) const
+bool CSSSelectorList::selectorCrossesTreeScopes(size_t index) const
{
- SelectorHasCombinatorCrossingTreeBoundary functor;
+ SelectorCrossesTreeScopes functor;
return forEachTagSelector(functor, selectorAt(index));
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.h b/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.h
index 320de3b4175..e8932fec6fc 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSelectorList.h
@@ -45,23 +45,23 @@ public:
bool isValid() const { return !!m_selectorArray; }
const CSSSelector* first() const { return m_selectorArray; }
- static const CSSSelector* next(const CSSSelector*);
- bool hasOneSelector() const { return m_selectorArray && !next(m_selectorArray); }
- const CSSSelector* selectorAt(size_t index) const { return &m_selectorArray[index]; }
+ static const CSSSelector* next(const CSSSelector&);
+ bool hasOneSelector() const { return m_selectorArray && !next(*m_selectorArray); }
+ const CSSSelector& selectorAt(size_t index) const { return m_selectorArray[index]; }
size_t indexOfNextSelectorAfter(size_t index) const
{
- const CSSSelector* current = selectorAt(index);
- current = next(current);
- if (!current)
+ const CSSSelector& current = selectorAt(index);
+ const CSSSelector* next = this->next(current);
+ if (!next)
return kNotFound;
- return current - m_selectorArray;
+ return next - m_selectorArray;
}
bool selectorsNeedNamespaceResolution();
bool hasShadowDistributedAt(size_t index) const;
- bool hasCombinatorCrossingTreeBoundaryAt(size_t index) const;
+ bool selectorCrossesTreeScopes(size_t index) const;
String selectorsText() const;
@@ -77,12 +77,13 @@ private:
CSSSelector* m_selectorArray;
};
-inline const CSSSelector* CSSSelectorList::next(const CSSSelector* current)
+inline const CSSSelector* CSSSelectorList::next(const CSSSelector& current)
{
// Skip subparts of compound selectors.
- while (!current->isLastInTagHistory())
- current++;
- return current->isLastInSelectorList() ? 0 : current + 1;
+ const CSSSelector* last = &current;
+ while (!last->isLastInTagHistory())
+ last++;
+ return last->isLastInSelectorList() ? 0 : last + 1;
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSelectorTest.cpp b/chromium/third_party/WebKit/Source/core/css/CSSSelectorTest.cpp
new file mode 100644
index 00000000000..baf04659d65
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSelectorTest.cpp
@@ -0,0 +1,58 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/CSSTestHelper.h"
+#include "core/css/RuleSet.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+TEST(CSSSelector, Representations)
+{
+ CSSTestHelper helper;
+
+ const char* cssRules =
+ "summary::-webkit-details-marker { }"
+ "* {}"
+ "div {}"
+ "#id {}"
+ ".class {}"
+ "[attr] {}"
+ "div:hover {}"
+ "div:nth-child(2){}"
+ ".class#id { }"
+ "#id.class { }"
+ "[attr]#id { }"
+ "div[attr]#id { }"
+ "div::content { }"
+ "div::first-line { }"
+ ".a.b.c { }"
+ "div:not(.a) { }" // without class a
+ "div:not(:visited) { }" // without the visited pseudo class
+
+ "[attr=\"value\"] { }" // Exact equality
+ "[attr~=\"value\"] { }" // One of a space-separated list
+ "[attr^=\"value\"] { }" // Begins with
+ "[attr$=\"value\"] { }" // Ends with
+ "[attr*=\"value\"] { }" // Substring equal to
+ "[attr|=\"value\"] { }" // One of a hyphen-separated list
+
+ ".a .b { }" // .b is a descendant of .a
+ ".a > .b { }" // .b is a direct descendant of .a
+ ".a ~ .b { }" // .a precedes .b in sibling order
+ ".a + .b { }" // .a element immediately precedes .b in sibling order
+ ".a, .b { }" // matches .a or .b
+
+ ".a.b .c {}";
+
+ helper.addCSSRules(cssRules);
+ EXPECT_EQ(30u, helper.ruleSet().ruleCount()); // .a, .b counts as two rules.
+#ifndef NDEBUG
+ helper.ruleSet().show();
+#endif
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSShaderValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSShaderValue.cpp
deleted file mode 100644
index 1fafe3008f1..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSShaderValue.cpp
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER “AS IS” AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-#include "config.h"
-
-#include "core/css/CSSShaderValue.h"
-
-#include "FetchInitiatorTypeNames.h"
-#include "core/css/CSSParser.h"
-#include "core/dom/Document.h"
-#include "core/fetch/FetchRequest.h"
-#include "core/fetch/ResourceFetcher.h"
-#include "core/rendering/style/StyleFetchedShader.h"
-#include "core/rendering/style/StylePendingShader.h"
-#include "wtf/text/StringBuilder.h"
-
-namespace WebCore {
-
-CSSShaderValue::CSSShaderValue(const String& url)
- : CSSValue(CSSShaderClass)
- , m_url(url)
- , m_accessedShader(false)
-{
-}
-
-CSSShaderValue::~CSSShaderValue()
-{
-}
-
-KURL CSSShaderValue::completeURL(ResourceFetcher* loader) const
-{
- return loader->document()->completeURL(m_url);
-}
-
-StyleFetchedShader* CSSShaderValue::resource(ResourceFetcher* loader)
-{
- ASSERT(loader);
-
- if (!m_accessedShader) {
- m_accessedShader = true;
-
- FetchRequest request(ResourceRequest(completeURL(loader)), FetchInitiatorTypeNames::css);
- if (ResourcePtr<ShaderResource> resource = loader->fetchShader(request))
- m_shader = StyleFetchedShader::create(resource.get());
- }
-
- return (m_shader && m_shader->isShaderResource()) ? static_cast<StyleFetchedShader*>(m_shader.get()) : 0;
-}
-
-StyleShader* CSSShaderValue::cachedOrPendingShader()
-{
- if (!m_shader)
- m_shader = StylePendingShader::create(this);
-
- return m_shader.get();
-}
-
-String CSSShaderValue::customCSSText() const
-{
- StringBuilder result;
- result.appendLiteral("url(");
- result.append(quoteCSSURLIfNeeded(m_url));
- result.append(')');
- if (!m_format.isEmpty()) {
- result.appendLiteral(" format('");
- result.append(m_format);
- result.appendLiteral("')");
- }
- return result.toString();
-}
-
-bool CSSShaderValue::equals(const CSSShaderValue& other) const
-{
- return m_url == other.m_url;
-}
-
-} // namespace WebCore
-
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSShaderValue.h b/chromium/third_party/WebKit/Source/core/css/CSSShaderValue.h
deleted file mode 100644
index 9c736262402..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSShaderValue.h
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER “AS IS” AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-#ifndef CSSShaderValue_h
-#define CSSShaderValue_h
-
-#include "core/css/CSSValue.h"
-
-namespace WebCore {
-
-class ResourceFetcher;
-class KURL;
-class StyleFetchedShader;
-class StyleShader;
-
-class CSSShaderValue : public CSSValue {
-public:
- static PassRefPtr<CSSShaderValue> create(const String& url) { return adoptRef(new CSSShaderValue(url)); }
- ~CSSShaderValue();
-
- const String& format() const { return m_format; }
- void setFormat(const String& format) { m_format = format; }
-
- KURL completeURL(ResourceFetcher*) const;
- StyleFetchedShader* resource(ResourceFetcher*);
- StyleShader* cachedOrPendingShader();
-
- String customCSSText() const;
-
- bool equals(const CSSShaderValue&) const;
-
-private:
- CSSShaderValue(const String& url);
-
- String m_url;
- String m_format;
- RefPtr<StyleShader> m_shader;
- bool m_accessedShader;
-};
-
-DEFINE_CSS_VALUE_TYPE_CASTS(CSSShaderValue, isShaderValue());
-
-} // namespace WebCore
-
-
-#endif // CSSShaderValue_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.cpp
index 35ecefb8cf9..4bdecf5ec10 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.cpp
@@ -27,12 +27,12 @@
namespace WebCore {
// Used for text-shadow and box-shadow
-CSSShadowValue::CSSShadowValue(PassRefPtr<CSSPrimitiveValue> x,
- PassRefPtr<CSSPrimitiveValue> y,
- PassRefPtr<CSSPrimitiveValue> blur,
- PassRefPtr<CSSPrimitiveValue> spread,
- PassRefPtr<CSSPrimitiveValue> style,
- PassRefPtr<CSSPrimitiveValue> color)
+CSSShadowValue::CSSShadowValue(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> x,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> y,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> blur,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> spread,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> style,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> color)
: CSSValue(ShadowClass)
, x(x)
, y(y)
@@ -88,4 +88,15 @@ bool CSSShadowValue::equals(const CSSShadowValue& other) const
&& compareCSSValuePtr(style, other.style);
}
+void CSSShadowValue::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(x);
+ visitor->trace(y);
+ visitor->trace(blur);
+ visitor->trace(spread);
+ visitor->trace(style);
+ visitor->trace(color);
+ CSSValue::traceAfterDispatch(visitor);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.h b/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.h
index 79fe736c6f5..ddd32ddab2c 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSShadowValue.h
@@ -32,34 +32,36 @@ class CSSPrimitiveValue;
// Used for text-shadow and box-shadow
class CSSShadowValue : public CSSValue {
public:
- static PassRefPtr<CSSShadowValue> create(PassRefPtr<CSSPrimitiveValue> x,
- PassRefPtr<CSSPrimitiveValue> y,
- PassRefPtr<CSSPrimitiveValue> blur,
- PassRefPtr<CSSPrimitiveValue> spread,
- PassRefPtr<CSSPrimitiveValue> style,
- PassRefPtr<CSSPrimitiveValue> color)
+ static PassRefPtrWillBeRawPtr<CSSShadowValue> create(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> x,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> y,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> blur,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> spread,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> style,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> color)
{
- return adoptRef(new CSSShadowValue(x, y, blur, spread, style, color));
+ return adoptRefWillBeNoop(new CSSShadowValue(x, y, blur, spread, style, color));
}
String customCSSText() const;
bool equals(const CSSShadowValue&) const;
- RefPtr<CSSPrimitiveValue> x;
- RefPtr<CSSPrimitiveValue> y;
- RefPtr<CSSPrimitiveValue> blur;
- RefPtr<CSSPrimitiveValue> spread;
- RefPtr<CSSPrimitiveValue> style;
- RefPtr<CSSPrimitiveValue> color;
+ RefPtrWillBeMember<CSSPrimitiveValue> x;
+ RefPtrWillBeMember<CSSPrimitiveValue> y;
+ RefPtrWillBeMember<CSSPrimitiveValue> blur;
+ RefPtrWillBeMember<CSSPrimitiveValue> spread;
+ RefPtrWillBeMember<CSSPrimitiveValue> style;
+ RefPtrWillBeMember<CSSPrimitiveValue> color;
+
+ void traceAfterDispatch(Visitor*);
private:
- CSSShadowValue(PassRefPtr<CSSPrimitiveValue> x,
- PassRefPtr<CSSPrimitiveValue> y,
- PassRefPtr<CSSPrimitiveValue> blur,
- PassRefPtr<CSSPrimitiveValue> spread,
- PassRefPtr<CSSPrimitiveValue> style,
- PassRefPtr<CSSPrimitiveValue> color);
+ CSSShadowValue(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> x,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> y,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> blur,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> spread,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> style,
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> color);
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSShadowValue, isShadowValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSShorthands.in b/chromium/third_party/WebKit/Source/core/css/CSSShorthands.in
index f66d64994df..9495b43504e 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSShorthands.in
+++ b/chromium/third_party/WebKit/Source/core/css/CSSShorthands.in
@@ -21,6 +21,8 @@ border-width longhands=border-top-width;border-right-width;border-bottom-width;b
flex longhands=flex-grow;flex-shrink;flex-basis
flex-flow longhands=flex-direction;flex-wrap
font longhands=font-family;font-size;font-style;font-variant;font-weight;line-height
+grid longhands=grid-template;grid-auto-flow;grid-auto-columns;grid-auto-rows
+grid-template longhands=grid-template-columns;grid-template-rows;grid-template-areas
grid-area longhands=grid-row-start;grid-column-start;grid-row-end;grid-column-end
grid-column longhands=grid-column-start;grid-column-end
grid-row longhands=grid-row-start;grid-row-end
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.cpp b/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.cpp
deleted file mode 100644
index 1347f99c5c0..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.cpp
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
- * its contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
- * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "core/css/CSSStyleDeclaration.h"
-
-
-namespace WebCore {
-
-PassRefPtr<CSSVariablesMap> CSSStyleDeclaration::var()
-{
- if (!m_variablesMap)
- m_variablesMap = CSSVariablesMap::create(this);
- return m_variablesMap;
-}
-
-CSSStyleDeclaration::~CSSStyleDeclaration()
-{
- if (m_variablesMap)
- m_variablesMap->clearStyleDeclaration();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.h b/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.h
index 5c2445af31a..3aa549510f4 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.h
@@ -21,10 +21,8 @@
#ifndef CSSStyleDeclaration_h
#define CSSStyleDeclaration_h
-#include "CSSPropertyNames.h"
#include "bindings/v8/ScriptWrappable.h"
-#include "core/css/CSSVariablesIterator.h"
-#include "core/css/CSSVariablesMap.h"
+#include "core/CSSPropertyNames.h"
#include "wtf/Forward.h"
#include "wtf/Noncopyable.h"
@@ -36,22 +34,23 @@ class CSSStyleSheet;
class CSSValue;
class ExceptionState;
class MutableStylePropertySet;
-class VariablesIterator;
-class CSSStyleDeclaration : public ScriptWrappable {
- WTF_MAKE_NONCOPYABLE(CSSStyleDeclaration); WTF_MAKE_FAST_ALLOCATED;
+class CSSStyleDeclaration : public NoBaseWillBeGarbageCollectedFinalized<CSSStyleDeclaration>, public ScriptWrappable {
+ WTF_MAKE_NONCOPYABLE(CSSStyleDeclaration); WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- virtual ~CSSStyleDeclaration();
+ virtual ~CSSStyleDeclaration() { }
+#if !ENABLE(OILPAN)
virtual void ref() = 0;
virtual void deref() = 0;
+#endif
virtual CSSRule* parentRule() const = 0;
virtual String cssText() const = 0;
virtual void setCSSText(const String&, ExceptionState&) = 0;
virtual unsigned length() const = 0;
virtual String item(unsigned index) const = 0;
- virtual PassRefPtr<CSSValue> getPropertyCSSValue(const String& propertyName) = 0;
+ virtual PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValue(const String& propertyName) = 0;
virtual String getPropertyValue(const String& propertyName) = 0;
virtual String getPropertyPriority(const String& propertyName) = 0;
virtual String getPropertyShorthand(const String& propertyName) = 0;
@@ -59,32 +58,25 @@ public:
virtual void setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState&) = 0;
virtual String removeProperty(const String& propertyName, ExceptionState&) = 0;
- PassRefPtr<CSSVariablesMap> var();
- virtual unsigned variableCount() const = 0;
- virtual String variableValue(const AtomicString& name) const = 0;
- virtual bool setVariableValue(const AtomicString& name, const String& value, ExceptionState&) = 0; // Return value indicates whether variable was added.
- virtual bool removeVariable(const AtomicString& name) = 0;
- virtual bool clearVariables(ExceptionState&) = 0;
- virtual PassRefPtr<CSSVariablesIterator> variablesIterator() const = 0;
-
// CSSPropertyID versions of the CSSOM functions to support bindings and editing.
// Use the non-virtual methods in the concrete subclasses when possible.
// The CSSValue returned by this function should not be exposed to the web as it may be used by multiple documents at the same time.
- virtual PassRefPtr<CSSValue> getPropertyCSSValueInternal(CSSPropertyID) = 0;
+ virtual PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValueInternal(CSSPropertyID) = 0;
virtual String getPropertyValueInternal(CSSPropertyID) = 0;
virtual void setPropertyInternal(CSSPropertyID, const String& value, bool important, ExceptionState&) = 0;
- virtual PassRefPtr<MutableStylePropertySet> copyProperties() const = 0;
+ virtual PassRefPtrWillBeRawPtr<MutableStylePropertySet> copyProperties() const = 0;
virtual bool cssPropertyMatches(CSSPropertyID, const CSSValue*) const = 0;
virtual CSSStyleSheet* parentStyleSheet() const { return 0; }
+ virtual void trace(Visitor*) { }
+
protected:
CSSStyleDeclaration()
{
ScriptWrappable::init(this);
}
- RefPtr<CSSVariablesMap> m_variablesMap;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.idl b/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.idl
index f552573a8eb..1fc7e9c6abf 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleDeclaration.idl
@@ -20,23 +20,27 @@
// Introduced in DOM Level 2:
[
- DependentLifetime
+ DependentLifetime,
+ WillBeGarbageCollected
] interface CSSStyleDeclaration {
[TreatReturnedNullStringAs=Null, TreatNullAs=NullString, RaisesException=Setter] attribute DOMString cssText;
[TreatReturnedNullStringAs=Null] DOMString getPropertyValue([Default=Undefined] optional DOMString propertyName);
- CSSValue getPropertyCSSValue([Default=Undefined] optional DOMString propertyName);
[TreatReturnedNullStringAs=Null, RaisesException] DOMString removeProperty([Default=Undefined] optional DOMString propertyName);
[TreatReturnedNullStringAs=Null] DOMString getPropertyPriority([Default=Undefined] optional DOMString propertyName);
[RaisesException] void setProperty([Default=Undefined] optional DOMString propertyName,
[TreatNullAs=NullString,Default=Undefined] optional DOMString value,
- [Default=Undefined] optional DOMString priority);
+ [TreatNullAs=NullString] optional DOMString priority = null);
readonly attribute unsigned long length;
getter DOMString item([Default=Undefined] optional unsigned long index);
- [Custom, CustomEnumerateProperty] getter (DOMString or float) (DOMString name);
+ [Custom=PropertyGetter|PropertyEnumerator|PropertyQuery] getter (DOMString or float) (DOMString name);
[Custom] setter void (DOMString propertyName, [TreatNullAs=NullString] DOMString propertyValue);
readonly attribute CSSRule parentRule;
- [RuntimeEnabled=CSSVariables] readonly attribute CSSVariablesMap var;
+
+ // Deprecated as of 2003: http://lists.w3.org/Archives/Public/www-style/2003Oct/0347.html
+ // FIXME: This should be DeprecateAs=, but currently too many LayoutTests use
+ // this function and would need CONSOLE: message rebaselines!
+ [MeasureAs=CSSStyleDeclarationGetPropertyCSSValue] CSSValue getPropertyCSSValue([Default=Undefined] optional DOMString propertyName);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.cpp
index 1ab4c5203a4..775583f6464 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.cpp
@@ -22,7 +22,7 @@
#include "config.h"
#include "core/css/CSSStyleRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSStyleSheet.h"
#include "core/css/PropertySetCSSStyleDeclaration.h"
@@ -47,9 +47,10 @@ CSSStyleRule::CSSStyleRule(StyleRule* styleRule, CSSStyleSheet* parent)
CSSStyleRule::~CSSStyleRule()
{
+#if !ENABLE(OILPAN)
if (m_propertiesCSSOMWrapper)
m_propertiesCSSOMWrapper->clearParentRule();
-
+#endif
if (hasCachedSelectorText()) {
selectorTextCache().remove(this);
setHasCachedSelectorText(false);
@@ -67,7 +68,7 @@ CSSStyleDeclaration* CSSStyleRule::style() const
String CSSStyleRule::generateSelectorText() const
{
StringBuilder builder;
- for (const CSSSelector* selector = m_styleRule->selectorList().first(); selector; selector = CSSSelectorList::next(selector)) {
+ for (const CSSSelector* selector = m_styleRule->selectorList().first(); selector; selector = CSSSelectorList::next(*selector)) {
if (selector != m_styleRule->selectorList().first())
builder.append(", ");
builder.append(selector->selectorText());
@@ -91,7 +92,8 @@ String CSSStyleRule::selectorText() const
void CSSStyleRule::setSelectorText(const String& selectorText)
{
- CSSParser p(parserContext());
+ CSSParserContext context(parserContext(), 0);
+ BisonCSSParser p(context);
CSSSelectorList selectorList;
p.parseSelector(selectorText, selectorList);
if (!selectorList.isValid())
@@ -112,7 +114,7 @@ String CSSStyleRule::cssText() const
StringBuilder result;
result.append(selectorText());
result.appendLiteral(" { ");
- String decls = m_styleRule->properties()->asText();
+ String decls = m_styleRule->properties().asText();
result.append(decls);
if (!decls.isEmpty())
result.append(' ');
@@ -128,4 +130,11 @@ void CSSStyleRule::reattach(StyleRuleBase* rule)
m_propertiesCSSOMWrapper->reattach(m_styleRule->mutableProperties());
}
+void CSSStyleRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_styleRule);
+ visitor->trace(m_propertiesCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.h b/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.h
index 12b4562f039..e1258bf5bc7 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleRule.h
@@ -23,6 +23,7 @@
#define CSSStyleRule_h
#include "core/css/CSSRule.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -30,13 +31,16 @@ class CSSStyleDeclaration;
class StyleRuleCSSStyleDeclaration;
class StyleRule;
-class CSSStyleRule : public CSSRule {
+class CSSStyleRule FINAL : public CSSRule {
public:
- static PassRefPtr<CSSStyleRule> create(StyleRule* rule, CSSStyleSheet* sheet) { return adoptRef(new CSSStyleRule(rule, sheet)); }
+ static PassRefPtrWillBeRawPtr<CSSStyleRule> create(StyleRule* rule, CSSStyleSheet* sheet)
+ {
+ return adoptRefWillBeNoop(new CSSStyleRule(rule, sheet));
+ }
virtual ~CSSStyleRule();
- virtual CSSRule::Type type() const { return STYLE_RULE; }
+ virtual CSSRule::Type type() const OVERRIDE { return STYLE_RULE; }
virtual String cssText() const OVERRIDE;
virtual void reattach(StyleRuleBase*) OVERRIDE;
@@ -48,13 +52,15 @@ public:
// FIXME: Not CSSOM. Remove.
StyleRule* styleRule() const { return m_styleRule.get(); }
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSStyleRule(StyleRule*, CSSStyleSheet*);
String generateSelectorText() const;
- RefPtr<StyleRule> m_styleRule;
- mutable RefPtr<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
+ RefPtrWillBeMember<StyleRule> m_styleRule;
+ mutable RefPtrWillBeMember<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSStyleRule, STYLE_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.cpp b/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.cpp
index e7fe16ecd27..f3b536719c0 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.cpp
@@ -21,14 +21,15 @@
#include "config.h"
#include "core/css/CSSStyleSheet.h"
-#include "HTMLNames.h"
-#include "SVGNames.h"
#include "bindings/v8/ExceptionState.h"
+#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/V8PerIsolateData.h"
+#include "core/HTMLNames.h"
+#include "core/SVGNames.h"
#include "core/css/CSSCharsetRule.h"
#include "core/css/CSSImportRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSRuleList.h"
-#include "core/css/CSSStyleRule.h"
#include "core/css/MediaList.h"
#include "core/css/StyleRule.h"
#include "core/css/StyleSheetContents.h"
@@ -36,76 +37,103 @@
#include "core/dom/ExceptionCode.h"
#include "core/dom/Node.h"
#include "core/frame/UseCounter.h"
+#include "core/html/HTMLStyleElement.h"
#include "core/inspector/InspectorInstrumentation.h"
+#include "core/svg/SVGStyleElement.h"
#include "platform/weborigin/SecurityOrigin.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
-class StyleSheetCSSRuleList : public CSSRuleList {
+class StyleSheetCSSRuleList FINAL : public CSSRuleList {
public:
- StyleSheetCSSRuleList(CSSStyleSheet* sheet) : m_styleSheet(sheet) { }
+ static PassOwnPtrWillBeRawPtr<StyleSheetCSSRuleList> create(CSSStyleSheet* sheet)
+ {
+ return adoptPtrWillBeNoop(new StyleSheetCSSRuleList(sheet));
+ }
+
+ virtual void trace(Visitor* visitor) OVERRIDE
+ {
+ visitor->trace(m_styleSheet);
+ CSSRuleList::trace(visitor);
+ }
private:
- virtual void ref() { m_styleSheet->ref(); }
- virtual void deref() { m_styleSheet->deref(); }
+ StyleSheetCSSRuleList(CSSStyleSheet* sheet) : m_styleSheet(sheet) { }
- virtual unsigned length() const { return m_styleSheet->length(); }
- virtual CSSRule* item(unsigned index) const { return m_styleSheet->item(index); }
+#if !ENABLE(OILPAN)
+ virtual void ref() OVERRIDE { m_styleSheet->ref(); }
+ virtual void deref() OVERRIDE { m_styleSheet->deref(); }
+#endif
- virtual CSSStyleSheet* styleSheet() const { return m_styleSheet; }
+ virtual unsigned length() const OVERRIDE { return m_styleSheet->length(); }
+ virtual CSSRule* item(unsigned index) const OVERRIDE { return m_styleSheet->item(index); }
- CSSStyleSheet* m_styleSheet;
+ virtual CSSStyleSheet* styleSheet() const OVERRIDE { return m_styleSheet; }
+
+ RawPtrWillBeMember<CSSStyleSheet> m_styleSheet;
};
-#if !ASSERT_DISABLED
+#if ASSERT_ENABLED
static bool isAcceptableCSSStyleSheetParent(Node* parentNode)
{
- // Only these nodes can be parents of StyleSheets, and they need to call clearOwnerNode() when moved out of document.
+ // Only these nodes can be parents of StyleSheets, and they need to call
+ // clearOwnerNode() when moved out of document.
+ // Destruction of the style sheet counts as being "moved out of the
+ // document", but only in the non-oilpan version of blink. I.e. don't call
+ // clearOwnerNode() in the owner's destructor in oilpan.
return !parentNode
|| parentNode->isDocumentNode()
- || parentNode->hasTagName(HTMLNames::linkTag)
- || parentNode->hasTagName(HTMLNames::styleTag)
- || parentNode->hasTagName(SVGNames::styleTag)
+ || isHTMLLinkElement(*parentNode)
+ || isHTMLStyleElement(*parentNode)
+ || isSVGStyleElement(*parentNode)
|| parentNode->nodeType() == Node::PROCESSING_INSTRUCTION_NODE;
}
#endif
-PassRefPtr<CSSStyleSheet> CSSStyleSheet::create(PassRefPtr<StyleSheetContents> sheet, CSSImportRule* ownerRule)
+PassRefPtrWillBeRawPtr<CSSStyleSheet> CSSStyleSheet::create(PassRefPtrWillBeRawPtr<StyleSheetContents> sheet, CSSImportRule* ownerRule)
{
- return adoptRef(new CSSStyleSheet(sheet, ownerRule));
+ return adoptRefWillBeNoop(new CSSStyleSheet(sheet, ownerRule));
}
-PassRefPtr<CSSStyleSheet> CSSStyleSheet::create(PassRefPtr<StyleSheetContents> sheet, Node* ownerNode)
+PassRefPtrWillBeRawPtr<CSSStyleSheet> CSSStyleSheet::create(PassRefPtrWillBeRawPtr<StyleSheetContents> sheet, Node* ownerNode)
{
- return adoptRef(new CSSStyleSheet(sheet, ownerNode, false, TextPosition::minimumPosition()));
+ return adoptRefWillBeNoop(new CSSStyleSheet(sheet, ownerNode, false, TextPosition::minimumPosition()));
}
-PassRefPtr<CSSStyleSheet> CSSStyleSheet::createInline(Node* ownerNode, const KURL& baseURL, const TextPosition& startPosition, const String& encoding)
+PassRefPtrWillBeRawPtr<CSSStyleSheet> CSSStyleSheet::createInline(PassRefPtrWillBeRawPtr<StyleSheetContents> sheet, Node* ownerNode, const TextPosition& startPosition)
{
- CSSParserContext parserContext(ownerNode->document(), baseURL, encoding);
- RefPtr<StyleSheetContents> sheet = StyleSheetContents::create(baseURL.string(), parserContext);
- return adoptRef(new CSSStyleSheet(sheet.release(), ownerNode, true, startPosition));
+ ASSERT(sheet);
+ return adoptRefWillBeNoop(new CSSStyleSheet(sheet, ownerNode, true, startPosition));
}
-CSSStyleSheet::CSSStyleSheet(PassRefPtr<StyleSheetContents> contents, CSSImportRule* ownerRule)
+PassRefPtrWillBeRawPtr<CSSStyleSheet> CSSStyleSheet::createInline(Node* ownerNode, const KURL& baseURL, const TextPosition& startPosition, const String& encoding)
+{
+ CSSParserContext parserContext(ownerNode->document(), 0, baseURL, encoding);
+ RefPtrWillBeRawPtr<StyleSheetContents> sheet = StyleSheetContents::create(baseURL.string(), parserContext);
+ return adoptRefWillBeNoop(new CSSStyleSheet(sheet.release(), ownerNode, true, startPosition));
+}
+
+CSSStyleSheet::CSSStyleSheet(PassRefPtrWillBeRawPtr<StyleSheetContents> contents, CSSImportRule* ownerRule)
: m_contents(contents)
, m_isInlineStylesheet(false)
, m_isDisabled(false)
- , m_ownerNode(0)
+ , m_ownerNode(nullptr)
, m_ownerRule(ownerRule)
, m_startPosition(TextPosition::minimumPosition())
+ , m_loadCompleted(false)
{
m_contents->registerClient(this);
}
-CSSStyleSheet::CSSStyleSheet(PassRefPtr<StyleSheetContents> contents, Node* ownerNode, bool isInlineStylesheet, const TextPosition& startPosition)
+CSSStyleSheet::CSSStyleSheet(PassRefPtrWillBeRawPtr<StyleSheetContents> contents, Node* ownerNode, bool isInlineStylesheet, const TextPosition& startPosition)
: m_contents(contents)
, m_isInlineStylesheet(isInlineStylesheet)
, m_isDisabled(false)
, m_ownerNode(ownerNode)
- , m_ownerRule(0)
+ , m_ownerRule(nullptr)
, m_startPosition(startPosition)
+ , m_loadCompleted(false)
{
ASSERT(isAcceptableCSSStyleSheetParent(ownerNode));
m_contents->registerClient(this);
@@ -113,6 +141,11 @@ CSSStyleSheet::CSSStyleSheet(PassRefPtr<StyleSheetContents> contents, Node* owne
CSSStyleSheet::~CSSStyleSheet()
{
+ // With oilpan the parent style sheet pointer is strong and the sheet and
+ // its RuleCSSOMWrappers die together and we don't need to clear them here.
+ // Also with oilpan the StyleSheetContents client pointers are weak and
+ // therefore do not need to be cleared here.
+#if !ENABLE(OILPAN)
// For style rules outside the document, .parentStyleSheet can become null even if the style rule
// is still observable from JavaScript. This matches the behavior of .parentNode for nodes, but
// it's not ideal because it makes the CSSOM's behavior depend on the timing of garbage collection.
@@ -121,53 +154,28 @@ CSSStyleSheet::~CSSStyleSheet()
m_childRuleCSSOMWrappers[i]->setParentStyleSheet(0);
}
- for (unsigned i = 0; i < m_extraChildRuleCSSOMWrappers.size(); ++i)
- m_extraChildRuleCSSOMWrappers[i]->setParentStyleSheet(0);
-
if (m_mediaCSSOMWrapper)
m_mediaCSSOMWrapper->clearParentStyleSheet();
m_contents->unregisterClient(this);
-}
-
-void CSSStyleSheet::extraCSSOMWrapperIndices(Vector<unsigned>& indices)
-{
- indices.grow(m_extraChildRuleCSSOMWrappers.size());
-
- for (unsigned i = 0; i < m_extraChildRuleCSSOMWrappers.size(); ++i) {
- CSSRule* cssRule = m_extraChildRuleCSSOMWrappers[i].get();
- ASSERT(cssRule->type() == CSSRule::STYLE_RULE);
- StyleRule* styleRule = toCSSStyleRule(cssRule)->styleRule();
-
- bool didFindIndex = false;
- for (unsigned j = 0; j < m_contents->ruleCount(); ++j) {
- if (m_contents->ruleAt(j) == styleRule) {
- didFindIndex = true;
- indices[i] = j;
- break;
- }
- }
- ASSERT(didFindIndex);
- if (!didFindIndex)
- indices[i] = 0;
- }
+#endif
}
void CSSStyleSheet::willMutateRules()
{
InspectorInstrumentation::willMutateRules(this);
+
// If we are the only client it is safe to mutate.
- if (m_contents->hasOneClient() && !m_contents->isInMemoryCache()) {
+ if (m_contents->clientSize() <= 1 && !m_contents->isInMemoryCache()) {
m_contents->clearRuleSet();
+ if (Document* document = ownerDocument())
+ m_contents->removeSheetFromCache(document);
m_contents->setMutable();
return;
}
// Only cacheable stylesheets should have multiple clients.
ASSERT(m_contents->isCacheable());
- Vector<unsigned> indices;
- extraCSSOMWrapperIndices(indices);
-
// Copy-on-write.
m_contents->unregisterClient(this);
m_contents = m_contents->copy();
@@ -176,13 +184,13 @@ void CSSStyleSheet::willMutateRules()
m_contents->setMutable();
// Any existing CSSOM wrappers need to be connected to the copied child rules.
- reattachChildRuleCSSOMWrappers(indices);
+ reattachChildRuleCSSOMWrappers();
}
void CSSStyleSheet::didMutateRules()
{
ASSERT(m_contents->isMutable());
- ASSERT(m_contents->hasOneClient());
+ ASSERT(m_contents->clientSize() <= 1);
InspectorInstrumentation::didMutateRules(this);
didMutate(PartialRuleUpdate);
@@ -197,20 +205,11 @@ void CSSStyleSheet::didMutate(StyleSheetUpdateType updateType)
// Need FullStyleUpdate when insertRule or deleteRule,
// because StyleSheetCollection::analyzeStyleSheetChange cannot detect partial rule update.
StyleResolverUpdateMode updateMode = updateType != PartialRuleUpdate ? AnalyzedStyleUpdate : FullStyleUpdate;
- owner->modifiedStyleSheet(this, RecalcStyleDeferred, updateMode);
-}
-
-void CSSStyleSheet::registerExtraChildRuleCSSOMWrapper(PassRefPtr<CSSRule> rule)
-{
- m_extraChildRuleCSSOMWrappers.append(rule);
+ owner->modifiedStyleSheet(this, updateMode);
}
-void CSSStyleSheet::reattachChildRuleCSSOMWrappers(const Vector<unsigned>& extraCSSOMWrapperIndices)
+void CSSStyleSheet::reattachChildRuleCSSOMWrappers()
{
- ASSERT(extraCSSOMWrapperIndices.size() == m_extraChildRuleCSSOMWrappers.size());
- for (unsigned i = 0; i < extraCSSOMWrapperIndices.size(); ++i)
- m_extraChildRuleCSSOMWrappers[i]->reattach(m_contents->ruleAt(extraCSSOMWrapperIndices[i]));
-
for (unsigned i = 0; i < m_childRuleCSSOMWrappers.size(); ++i) {
if (!m_childRuleCSSOMWrappers[i])
continue;
@@ -227,7 +226,7 @@ void CSSStyleSheet::setDisabled(bool disabled)
didMutate();
}
-void CSSStyleSheet::setMediaQueries(PassRefPtr<MediaQuerySet> mediaQueries)
+void CSSStyleSheet::setMediaQueries(PassRefPtrWillBeRawPtr<MediaQuerySet> mediaQueries)
{
m_mediaQueries = mediaQueries;
if (m_mediaCSSOMWrapper && m_mediaQueries)
@@ -252,7 +251,7 @@ CSSRule* CSSStyleSheet::item(unsigned index)
m_childRuleCSSOMWrappers.grow(ruleCount);
ASSERT(m_childRuleCSSOMWrappers.size() == ruleCount);
- RefPtr<CSSRule>& cssRule = m_childRuleCSSOMWrappers[index];
+ RefPtrWillBeMember<CSSRule>& cssRule = m_childRuleCSSOMWrappers[index];
if (!cssRule) {
if (index == 0 && m_contents->hasCharsetRule()) {
ASSERT(!m_contents->ruleAt(0));
@@ -263,6 +262,14 @@ CSSRule* CSSStyleSheet::item(unsigned index)
return cssRule.get();
}
+void CSSStyleSheet::clearOwnerNode()
+{
+ didMutate(EntireStyleSheetUpdate);
+ if (m_ownerNode)
+ m_contents->unregisterClient(this);
+ m_ownerNode = nullptr;
+}
+
bool CSSStyleSheet::canAccessRules() const
{
if (m_isInlineStylesheet)
@@ -278,12 +285,12 @@ bool CSSStyleSheet::canAccessRules() const
return false;
}
-PassRefPtr<CSSRuleList> CSSStyleSheet::rules()
+PassRefPtrWillBeRawPtr<CSSRuleList> CSSStyleSheet::rules()
{
if (!canAccessRules())
- return 0;
+ return nullptr;
// IE behavior.
- RefPtr<StaticCSSRuleList> nonCharsetRules = StaticCSSRuleList::create();
+ RefPtrWillBeRawPtr<StaticCSSRuleList> nonCharsetRules(StaticCSSRuleList::create());
unsigned ruleCount = length();
for (unsigned i = 0; i < ruleCount; ++i) {
CSSRule* rule = item(i);
@@ -299,32 +306,33 @@ unsigned CSSStyleSheet::insertRule(const String& ruleString, unsigned index, Exc
ASSERT(m_childRuleCSSOMWrappers.isEmpty() || m_childRuleCSSOMWrappers.size() == m_contents->ruleCount());
if (index > length()) {
- exceptionState.throwUninformativeAndGenericDOMException(IndexSizeError);
+ exceptionState.throwDOMException(IndexSizeError, "The index provided (" + String::number(index) + ") is larger than the maximum index (" + String::number(length()) + ").");
return 0;
}
- CSSParser p(m_contents->parserContext(), UseCounter::getFrom(this));
- RefPtr<StyleRuleBase> rule = p.parseRule(m_contents.get(), ruleString);
+ CSSParserContext context(m_contents->parserContext(), UseCounter::getFrom(this));
+ BisonCSSParser p(context);
+ RefPtrWillBeRawPtr<StyleRuleBase> rule = p.parseRule(m_contents.get(), ruleString);
if (!rule) {
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
+ exceptionState.throwDOMException(SyntaxError, "Failed to parse the rule '" + ruleString + "'.");
return 0;
}
RuleMutationScope mutationScope(this);
bool success = m_contents->wrapperInsertRule(rule, index);
if (!success) {
- exceptionState.throwUninformativeAndGenericDOMException(HierarchyRequestError);
+ exceptionState.throwDOMException(HierarchyRequestError, "Failed to insert the rule.");
return 0;
}
if (!m_childRuleCSSOMWrappers.isEmpty())
- m_childRuleCSSOMWrappers.insert(index, RefPtr<CSSRule>());
+ m_childRuleCSSOMWrappers.insert(index, RefPtrWillBeMember<CSSRule>(nullptr));
return index;
}
unsigned CSSStyleSheet::insertRule(const String& rule, ExceptionState& exceptionState)
{
- UseCounter::countDeprecation(activeExecutionContext(), UseCounter::CSSStyleSheetInsertRuleOptionalArg);
+ UseCounter::countDeprecation(callingExecutionContext(V8PerIsolateData::mainThreadIsolate()), UseCounter::CSSStyleSheetInsertRuleOptionalArg);
return insertRule(rule, 0, exceptionState);
}
@@ -333,7 +341,7 @@ void CSSStyleSheet::deleteRule(unsigned index, ExceptionState& exceptionState)
ASSERT(m_childRuleCSSOMWrappers.isEmpty() || m_childRuleCSSOMWrappers.size() == m_contents->ruleCount());
if (index >= length()) {
- exceptionState.throwUninformativeAndGenericDOMException(IndexSizeError);
+ exceptionState.throwDOMException(IndexSizeError, "The index provided (" + String::number(index) + ") is larger than the maximum index (" + String::number(length() - 1) + ").");
return;
}
RuleMutationScope mutationScope(this);
@@ -368,12 +376,12 @@ int CSSStyleSheet::addRule(const String& selector, const String& style, Exceptio
}
-PassRefPtr<CSSRuleList> CSSStyleSheet::cssRules()
+PassRefPtrWillBeRawPtr<CSSRuleList> CSSStyleSheet::cssRules()
{
if (!canAccessRules())
- return 0;
+ return nullptr;
if (!m_ruleListCSSOMWrapper)
- m_ruleListCSSOMWrapper = adoptPtr(new StyleSheetCSSRuleList(this));
+ m_ruleListCSSOMWrapper = StyleSheetCSSRuleList::create(this);
return m_ruleListCSSOMWrapper.get();
}
@@ -420,4 +428,42 @@ void CSSStyleSheet::clearChildRuleCSSOMWrappers()
m_childRuleCSSOMWrappers.clear();
}
+bool CSSStyleSheet::sheetLoaded()
+{
+ ASSERT(m_ownerNode);
+ setLoadCompleted(m_ownerNode->sheetLoaded());
+ return m_loadCompleted;
+}
+
+void CSSStyleSheet::startLoadingDynamicSheet()
+{
+ setLoadCompleted(false);
+ m_ownerNode->startLoadingDynamicSheet();
+}
+
+void CSSStyleSheet::setLoadCompleted(bool completed)
+{
+ if (completed == m_loadCompleted)
+ return;
+
+ m_loadCompleted = completed;
+
+ if (completed)
+ m_contents->clientLoadCompleted(this);
+ else
+ m_contents->clientLoadStarted(this);
+}
+
+void CSSStyleSheet::trace(Visitor* visitor)
+{
+ visitor->trace(m_contents);
+ visitor->trace(m_mediaQueries);
+ visitor->trace(m_ownerNode);
+ visitor->trace(m_ownerRule);
+ visitor->trace(m_mediaCSSOMWrapper);
+ visitor->trace(m_childRuleCSSOMWrappers);
+ visitor->trace(m_ruleListCSSOMWrapper);
+ StyleSheet::trace(visitor);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.h b/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.h
index 3c02c230c9f..18d68d5716c 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.h
@@ -23,6 +23,7 @@
#include "core/css/CSSRule.h"
#include "core/css/StyleSheet.h"
+#include "platform/heap/Handle.h"
#include "wtf/Noncopyable.h"
#include "wtf/text/TextPosition.h"
@@ -30,7 +31,7 @@ namespace WebCore {
class CSSCharsetRule;
class CSSImportRule;
-class CSSParser;
+class BisonCSSParser;
class CSSRule;
class CSSRuleList;
class CSSStyleSheet;
@@ -46,11 +47,12 @@ enum StyleSheetUpdateType {
EntireStyleSheetUpdate
};
-class CSSStyleSheet : public StyleSheet {
+class CSSStyleSheet FINAL : public StyleSheet {
public:
- static PassRefPtr<CSSStyleSheet> create(PassRefPtr<StyleSheetContents>, CSSImportRule* ownerRule = 0);
- static PassRefPtr<CSSStyleSheet> create(PassRefPtr<StyleSheetContents>, Node* ownerNode);
- static PassRefPtr<CSSStyleSheet> createInline(Node*, const KURL&, const TextPosition& startPosition = TextPosition::minimumPosition(), const String& encoding = String());
+ static PassRefPtrWillBeRawPtr<CSSStyleSheet> create(PassRefPtrWillBeRawPtr<StyleSheetContents>, CSSImportRule* ownerRule = 0);
+ static PassRefPtrWillBeRawPtr<CSSStyleSheet> create(PassRefPtrWillBeRawPtr<StyleSheetContents>, Node* ownerNode);
+ static PassRefPtrWillBeRawPtr<CSSStyleSheet> createInline(Node*, const KURL&, const TextPosition& startPosition = TextPosition::minimumPosition(), const String& encoding = String());
+ static PassRefPtrWillBeRawPtr<CSSStyleSheet> createInline(PassRefPtrWillBeRawPtr<StyleSheetContents>, Node* ownerNode, const TextPosition& startPosition = TextPosition::minimumPosition());
virtual ~CSSStyleSheet();
@@ -62,13 +64,13 @@ public:
virtual bool disabled() const OVERRIDE { return m_isDisabled; }
virtual void setDisabled(bool) OVERRIDE;
- PassRefPtr<CSSRuleList> cssRules();
+ PassRefPtrWillBeRawPtr<CSSRuleList> cssRules();
unsigned insertRule(const String& rule, unsigned index, ExceptionState&);
unsigned insertRule(const String& rule, ExceptionState&); // Deprecated.
void deleteRule(unsigned index, ExceptionState&);
// IE Extensions
- PassRefPtr<CSSRuleList> rules();
+ PassRefPtrWillBeRawPtr<CSSRuleList> rules();
int addRule(const String& selector, const String& style, int index, ExceptionState&);
int addRule(const String& selector, const String& style, ExceptionState&);
void removeRule(unsigned index, ExceptionState& exceptionState) { deleteRule(index, exceptionState); }
@@ -77,26 +79,28 @@ public:
unsigned length() const;
CSSRule* item(unsigned index);
- virtual void clearOwnerNode() OVERRIDE { didMutate(EntireStyleSheetUpdate); m_ownerNode = 0; }
+ virtual void clearOwnerNode() OVERRIDE;
+
virtual CSSRule* ownerRule() const OVERRIDE { return m_ownerRule; }
virtual KURL baseURL() const OVERRIDE;
virtual bool isLoading() const OVERRIDE;
- void clearOwnerRule() { m_ownerRule = 0; }
+ void clearOwnerRule() { m_ownerRule = nullptr; }
Document* ownerDocument() const;
MediaQuerySet* mediaQueries() const { return m_mediaQueries.get(); }
- void setMediaQueries(PassRefPtr<MediaQuerySet>);
+ void setMediaQueries(PassRefPtrWillBeRawPtr<MediaQuerySet>);
void setTitle(const String& title) { m_title = title; }
class RuleMutationScope {
WTF_MAKE_NONCOPYABLE(RuleMutationScope);
+ STACK_ALLOCATED();
public:
- RuleMutationScope(CSSStyleSheet*);
- RuleMutationScope(CSSRule*);
+ explicit RuleMutationScope(CSSStyleSheet*);
+ explicit RuleMutationScope(CSSRule*);
~RuleMutationScope();
private:
- CSSStyleSheet* m_styleSheet;
+ RawPtrWillBeMember<CSSStyleSheet> m_styleSheet;
};
void willMutateRules();
@@ -105,42 +109,44 @@ public:
void clearChildRuleCSSOMWrappers();
- void registerExtraChildRuleCSSOMWrapper(PassRefPtr<CSSRule>);
-
StyleSheetContents* contents() const { return m_contents.get(); }
bool isInline() const { return m_isInlineStylesheet; }
TextPosition startPositionInSource() const { return m_startPosition; }
+ bool sheetLoaded();
+ bool loadCompleted() const { return m_loadCompleted; }
+ void startLoadingDynamicSheet();
+
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
- CSSStyleSheet(PassRefPtr<StyleSheetContents>, CSSImportRule* ownerRule);
- CSSStyleSheet(PassRefPtr<StyleSheetContents>, Node* ownerNode, bool isInlineStylesheet, const TextPosition& startPosition);
+ CSSStyleSheet(PassRefPtrWillBeRawPtr<StyleSheetContents>, CSSImportRule* ownerRule);
+ CSSStyleSheet(PassRefPtrWillBeRawPtr<StyleSheetContents>, Node* ownerNode, bool isInlineStylesheet, const TextPosition& startPosition);
- virtual bool isCSSStyleSheet() const { return true; }
- virtual String type() const { return "text/css"; }
+ virtual bool isCSSStyleSheet() const OVERRIDE { return true; }
+ virtual String type() const OVERRIDE { return "text/css"; }
- void extraCSSOMWrapperIndices(Vector<unsigned>& indices);
- void reattachChildRuleCSSOMWrappers(const Vector<unsigned>& extraCSSOMWrapperIndices);
+ void reattachChildRuleCSSOMWrappers();
bool canAccessRules() const;
- RefPtr<StyleSheetContents> m_contents;
+ void setLoadCompleted(bool);
+
+ RefPtrWillBeMember<StyleSheetContents> m_contents;
bool m_isInlineStylesheet;
bool m_isDisabled;
String m_title;
- RefPtr<MediaQuerySet> m_mediaQueries;
+ RefPtrWillBeMember<MediaQuerySet> m_mediaQueries;
- Node* m_ownerNode;
- CSSRule* m_ownerRule;
+ RawPtrWillBeMember<Node> m_ownerNode;
+ RawPtrWillBeMember<CSSRule> m_ownerRule;
TextPosition m_startPosition;
-
- mutable RefPtr<MediaList> m_mediaCSSOMWrapper;
- mutable Vector<RefPtr<CSSRule> > m_childRuleCSSOMWrappers;
- // These are CSSOMWrappers that come from getMatchedCSSRules and thus don't map 1-1 to
- // the StyleRules in the StyleSheetContents.
- mutable Vector<RefPtr<CSSRule> > m_extraChildRuleCSSOMWrappers;
- mutable OwnPtr<CSSRuleList> m_ruleListCSSOMWrapper;
+ bool m_loadCompleted;
+ mutable RefPtrWillBeMember<MediaList> m_mediaCSSOMWrapper;
+ mutable WillBeHeapVector<RefPtrWillBeMember<CSSRule> > m_childRuleCSSOMWrappers;
+ mutable OwnPtrWillBeMember<CSSRuleList> m_ruleListCSSOMWrapper;
};
inline CSSStyleSheet::RuleMutationScope::RuleMutationScope(CSSStyleSheet* sheet)
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.idl b/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.idl
index a9b09007967..71619f33e45 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSStyleSheet.idl
@@ -20,7 +20,7 @@
// Introduced in DOM Level 2:
[
- GenerateVisitDOMWrapper=ownerNode,
+ SetWrapperReferenceFrom=ownerNode,
] interface CSSStyleSheet : StyleSheet {
readonly attribute CSSRule ownerRule;
readonly attribute CSSRuleList cssRules;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSupportsRule.h b/chromium/third_party/WebKit/Source/core/css/CSSSupportsRule.h
index 4d15dd2523f..75f467553cd 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSupportsRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSSupportsRule.h
@@ -36,11 +36,11 @@ namespace WebCore {
class CSSRule;
class StyleRuleSupports;
-class CSSSupportsRule : public CSSGroupingRule {
+class CSSSupportsRule FINAL : public CSSGroupingRule {
public:
- static PassRefPtr<CSSSupportsRule> create(StyleRuleSupports* rule, CSSStyleSheet* sheet)
+ static PassRefPtrWillBeRawPtr<CSSSupportsRule> create(StyleRuleSupports* rule, CSSStyleSheet* sheet)
{
- return adoptRef(new CSSSupportsRule(rule, sheet));
+ return adoptRefWillBeNoop(new CSSSupportsRule(rule, sheet));
}
virtual ~CSSSupportsRule() { }
@@ -50,6 +50,8 @@ public:
String conditionText() const;
+ virtual void trace(Visitor* visitor) OVERRIDE { CSSGroupingRule::trace(visitor); }
+
private:
CSSSupportsRule(StyleRuleSupports*, CSSStyleSheet*);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTestHelper.cpp b/chromium/third_party/WebKit/Source/core/css/CSSTestHelper.cpp
new file mode 100644
index 00000000000..4edca948153
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTestHelper.cpp
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2014, Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Opera Software ASA nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "core/css/CSSTestHelper.h"
+
+#include "core/css/CSSRuleList.h"
+#include "core/css/CSSStyleSheet.h"
+#include "core/css/RuleSet.h"
+#include "core/css/StyleSheetContents.h"
+#include "core/dom/Document.h"
+#include "wtf/text/WTFString.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+CSSTestHelper::~CSSTestHelper()
+{
+}
+
+CSSTestHelper::CSSTestHelper()
+{
+ m_document = Document::create();
+ TextPosition position;
+ m_styleSheet = CSSStyleSheet::createInline(m_document.get(), KURL(), position, "UTF-8");
+}
+
+RuleSet& CSSTestHelper::ruleSet()
+{
+ RuleSet& ruleSet = m_styleSheet->contents()->ensureRuleSet(MediaQueryEvaluator(), RuleHasNoSpecialState);
+ ruleSet.compactRulesIfNeeded();
+ return ruleSet;
+}
+
+void CSSTestHelper::addCSSRules(const char* cssText)
+{
+ TextPosition position;
+ unsigned sheetLength = m_styleSheet->length();
+ ASSERT_TRUE(m_styleSheet->contents()->parseStringAtPosition(cssText, position, true));
+ ASSERT_TRUE(m_styleSheet->length() > sheetLength);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTestHelper.h b/chromium/third_party/WebKit/Source/core/css/CSSTestHelper.h
new file mode 100644
index 00000000000..f217b77afbf
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTestHelper.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2014, Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Opera Software ASA nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef CSSTestHelper_h
+#define CSSTestHelper_h
+
+#include "core/css/RuleSet.h"
+#include "wtf/RefPtr.h"
+
+namespace WebCore {
+
+class Document;
+class CSSStyleSheet;
+
+// A helper class for writing tests of CSS rules. Example usage:
+//
+// CSSTestHelper helper;
+// helper.addCSSRule("body { color: red} #a { position: absolute }");
+// RuleSet& ruleSet = helper.ruleSet();
+// ... examine RuleSet to find the rule and test properties on it.
+
+class CSSTestHelper {
+public:
+ CSSTestHelper();
+ ~CSSTestHelper();
+
+ void addCSSRules(const char* ruleText);
+ RuleSet& ruleSet();
+
+private:
+ RefPtrWillBePersistent<Document> m_document;
+ RefPtrWillBePersistent<CSSStyleSheet> m_styleSheet;
+};
+
+} // namespace WebCore
+
+#endif // CSSTestHelper_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.cpp
index 49420cbb26b..b8eee452aca 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.cpp
@@ -46,12 +46,28 @@ bool CSSCubicBezierTimingFunctionValue::equals(const CSSCubicBezierTimingFunctio
String CSSStepsTimingFunctionValue::customCSSText() const
{
- return "steps(" + String::number(m_steps) + ", " + (m_stepAtStart ? "start" : "end") + ')';
+ String stepAtPositionString;
+ switch (m_stepAtPosition) {
+ case StepsTimingFunction::StepAtStart:
+ stepAtPositionString = "start";
+ break;
+ case StepsTimingFunction::StepAtMiddle:
+ stepAtPositionString = "middle";
+ break;
+ case StepsTimingFunction::StepAtEnd:
+ stepAtPositionString = "end";
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ stepAtPositionString = "end";
+ break;
+ }
+ return "steps(" + String::number(m_steps) + ", " + stepAtPositionString + ')';
}
bool CSSStepsTimingFunctionValue::equals(const CSSStepsTimingFunctionValue& other) const
{
- return m_steps == other.m_steps && m_stepAtStart == other.m_stepAtStart;
+ return m_steps == other.m_steps && m_stepAtPosition == other.m_stepAtPosition;
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.h b/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.h
index 54f566171c2..f0daa301a3e 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTimingFunctionValue.h
@@ -27,15 +27,16 @@
#define CSSTimingFunctionValue_h
#include "core/css/CSSValue.h"
+#include "platform/animation/TimingFunction.h"
#include "wtf/PassRefPtr.h"
namespace WebCore {
class CSSCubicBezierTimingFunctionValue : public CSSValue {
public:
- static PassRefPtr<CSSCubicBezierTimingFunctionValue> create(double x1, double y1, double x2, double y2)
+ static PassRefPtrWillBeRawPtr<CSSCubicBezierTimingFunctionValue> create(double x1, double y1, double x2, double y2)
{
- return adoptRef(new CSSCubicBezierTimingFunctionValue(x1, y1, x2, y2));
+ return adoptRefWillBeNoop(new CSSCubicBezierTimingFunctionValue(x1, y1, x2, y2));
}
String customCSSText() const;
@@ -47,6 +48,8 @@ public:
bool equals(const CSSCubicBezierTimingFunctionValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSCubicBezierTimingFunctionValue(double x1, double y1, double x2, double y2)
: CSSValue(CubicBezierTimingFunctionClass)
@@ -67,28 +70,30 @@ DEFINE_CSS_VALUE_TYPE_CASTS(CSSCubicBezierTimingFunctionValue, isCubicBezierTimi
class CSSStepsTimingFunctionValue : public CSSValue {
public:
- static PassRefPtr<CSSStepsTimingFunctionValue> create(int steps, bool stepAtStart)
+ static PassRefPtrWillBeRawPtr<CSSStepsTimingFunctionValue> create(int steps, StepsTimingFunction::StepAtPosition stepAtPosition)
{
- return adoptRef(new CSSStepsTimingFunctionValue(steps, stepAtStart));
+ return adoptRefWillBeNoop(new CSSStepsTimingFunctionValue(steps, stepAtPosition));
}
int numberOfSteps() const { return m_steps; }
- bool stepAtStart() const { return m_stepAtStart; }
+ StepsTimingFunction::StepAtPosition stepAtPosition() const { return m_stepAtPosition; }
String customCSSText() const;
bool equals(const CSSStepsTimingFunctionValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
- CSSStepsTimingFunctionValue(int steps, bool stepAtStart)
+ CSSStepsTimingFunctionValue(int steps, StepsTimingFunction::StepAtPosition stepAtPosition)
: CSSValue(StepsTimingFunctionClass)
, m_steps(steps)
- , m_stepAtStart(stepAtStart)
+ , m_stepAtPosition(stepAtPosition)
{
}
int m_steps;
- bool m_stepAtStart;
+ StepsTimingFunction::StepAtPosition m_stepAtPosition;
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSStepsTimingFunctionValue, isStepsTimingFunctionValue());
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.cpp b/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.cpp
index 6085a69892b..66583963904 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.cpp
@@ -31,10 +31,45 @@
#include "config.h"
#include "core/css/CSSToLengthConversionData.h"
+#include "core/rendering/RenderView.h"
#include "core/rendering/style/RenderStyle.h"
namespace WebCore {
+CSSToLengthConversionData::CSSToLengthConversionData(const RenderStyle* style, const RenderStyle* rootStyle, const RenderView* renderView, float zoom, bool computingFontSize)
+ : m_style(style)
+ , m_rootStyle(rootStyle)
+ , m_viewportWidth(renderView ? renderView->layoutViewportWidth() : 0)
+ , m_viewportHeight(renderView ? renderView->layoutViewportHeight() : 0)
+ , m_zoom(zoom)
+ , m_useEffectiveZoom(false)
+ , m_computingFontSize(computingFontSize)
+{
+ ASSERT(zoom > 0);
+}
+
+CSSToLengthConversionData::CSSToLengthConversionData(const RenderStyle* style, const RenderStyle* rootStyle, const RenderView* renderView, bool computingFontSize)
+ : m_style(style)
+ , m_rootStyle(rootStyle)
+ , m_viewportWidth(renderView ? renderView->layoutViewportWidth() : 0)
+ , m_viewportHeight(renderView ? renderView->layoutViewportHeight() : 0)
+ , m_useEffectiveZoom(true)
+ , m_computingFontSize(computingFontSize)
+{
+}
+
+CSSToLengthConversionData::CSSToLengthConversionData(const RenderStyle* style, const RenderStyle* rootStyle, float viewportWidth, float viewportHeight, float zoom, bool computingFontSize)
+ : m_style(style)
+ , m_rootStyle(rootStyle)
+ , m_viewportWidth(viewportWidth)
+ , m_viewportHeight(viewportHeight)
+ , m_zoom(zoom)
+ , m_useEffectiveZoom(false)
+ , m_computingFontSize(computingFontSize)
+{
+ ASSERT(zoom > 0);
+}
+
float CSSToLengthConversionData::zoom() const
{
if (m_useEffectiveZoom)
@@ -42,4 +77,25 @@ float CSSToLengthConversionData::zoom() const
return m_zoom;
}
+double CSSToLengthConversionData::viewportWidthPercent() const
+{
+ m_style->setHasViewportUnits();
+ return m_viewportWidth / 100;
+}
+double CSSToLengthConversionData::viewportHeightPercent() const
+{
+ m_style->setHasViewportUnits();
+ return m_viewportHeight / 100;
+}
+double CSSToLengthConversionData::viewportMinPercent() const
+{
+ m_style->setHasViewportUnits();
+ return std::min(m_viewportWidth, m_viewportHeight) / 100;
+}
+double CSSToLengthConversionData::viewportMaxPercent() const
+{
+ m_style->setHasViewportUnits();
+ return std::max(m_viewportWidth, m_viewportHeight) / 100;
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.h b/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.h
index 975be5f2122..6b81ce993b9 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSToLengthConversionData.h
@@ -37,41 +37,38 @@
namespace WebCore {
class RenderStyle;
+class RenderView;
class CSSToLengthConversionData {
public:
- CSSToLengthConversionData(const RenderStyle* style, const RenderStyle* rootStyle, float zoom, bool computingFontSize = false)
- : m_style(style)
- , m_rootStyle(rootStyle)
- , m_zoom(zoom)
- , m_useEffectiveZoom(false)
- , m_computingFontSize(computingFontSize)
- {
- ASSERT(zoom > 0);
- }
- CSSToLengthConversionData(const RenderStyle* style, const RenderStyle* rootStyle, bool computingFontSize = false)
- : m_style(style)
- , m_rootStyle(rootStyle)
- , m_useEffectiveZoom(true)
- , m_computingFontSize(computingFontSize)
- {
- }
+ CSSToLengthConversionData(const RenderStyle* currStyle, const RenderStyle* rootStyle, const RenderView*, float zoom, bool computingFontSize = false);
+ CSSToLengthConversionData(const RenderStyle* currStyle, const RenderStyle* rootStyle, const RenderView*, bool computingFontSize = false);
+ CSSToLengthConversionData(const RenderStyle* currStyle, const RenderStyle* rootStyle, float viewportWidth, float viewportHeight, float zoom, bool computingFontSize = false);
+
const RenderStyle& style() const { return *m_style; }
- const RenderStyle& rootStyle() const { return *m_rootStyle; }
+ const RenderStyle* rootStyle() const { return m_rootStyle; }
float zoom() const;
bool computingFontSize() const { return m_computingFontSize; }
+ // Accessing these marks the style as having viewport units
+ double viewportWidthPercent() const;
+ double viewportHeightPercent() const;
+ double viewportMinPercent() const;
+ double viewportMaxPercent() const;
+
void setStyle(const RenderStyle* style) { m_style = style; }
void setRootStyle(const RenderStyle* rootStyle) { m_rootStyle = rootStyle; }
CSSToLengthConversionData copyWithAdjustedZoom(float newZoom) const
{
- return CSSToLengthConversionData(m_style, m_rootStyle, newZoom, m_computingFontSize);
+ return CSSToLengthConversionData(m_style, m_rootStyle, m_viewportWidth, m_viewportHeight, newZoom, m_computingFontSize);
}
private:
const RenderStyle* m_style;
const RenderStyle* m_rootStyle;
+ float m_viewportWidth;
+ float m_viewportHeight;
float m_zoom;
bool m_useEffectiveZoom;
bool m_computingFontSize;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTokenizer-in.cpp b/chromium/third_party/WebKit/Source/core/css/CSSTokenizer-in.cpp
index 5ee194a188c..3b8aef115ae 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSTokenizer-in.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTokenizer-in.cpp
@@ -28,7 +28,7 @@
#include "core/css/CSSTokenizer.h"
#include "core/css/CSSKeyframeRule.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSParserValues.h"
#include "core/css/MediaQuery.h"
#include "core/css/StyleRule.h"
@@ -37,7 +37,7 @@
namespace WebCore {
-#include "CSSGrammar.h"
+#include "core/CSSGrammar.h"
enum CharacterType {
// Types for the main switch.
@@ -304,14 +304,17 @@ inline UChar*& CSSTokenizer::currentCharacter<UChar>()
return m_currentCharacter16;
}
-UChar*& CSSTokenizer::currentCharacter16()
+UChar* CSSTokenizer::allocateStringBuffer16(size_t len)
{
- if (!m_currentCharacter16) {
- m_dataStart16 = adoptArrayPtr(new UChar[m_length]);
- m_currentCharacter16 = m_dataStart16.get();
- }
+ // Allocates and returns a CSSTokenizer owned buffer for storing
+ // UTF-16 data. Used to get a suitable life span for UTF-16
+ // strings, identifiers and URIs created by the tokenizer.
+ OwnPtr<UChar[]> buffer = adoptArrayPtr(new UChar[len]);
- return m_currentCharacter16;
+ UChar* bufferPtr = buffer.get();
+
+ m_cssStrings16.append(buffer.release());
+ return bufferPtr;
}
template <>
@@ -350,13 +353,17 @@ inline bool CSSTokenizer::isIdentifierStart()
return isIdentifierStartAfterDash((*currentCharacter<CharacterType>() != '-') ? currentCharacter<CharacterType>() : currentCharacter<CharacterType>() + 1);
}
+enum CheckStringValidationMode {
+ AbortIfInvalid,
+ SkipInvalid
+};
+
template <typename CharacterType>
-static inline CharacterType* checkAndSkipString(CharacterType* currentCharacter, int quote)
+static inline CharacterType* checkAndSkipString(CharacterType* currentCharacter, int quote, CheckStringValidationMode mode)
{
- // Returns with 0, if string check is failed. Otherwise
- // it returns with the following character. This is necessary
- // since we cannot revert escape sequences, thus strings
- // must be validated before parsing.
+ // If mode is AbortIfInvalid and the string check fails it returns
+ // with 0. Otherwise it returns with a pointer to the first
+ // character after the string.
while (true) {
if (UNLIKELY(*currentCharacter == quote)) {
// String parsing is successful.
@@ -366,7 +373,7 @@ static inline CharacterType* checkAndSkipString(CharacterType* currentCharacter,
// String parsing is successful up to end of input.
return currentCharacter;
}
- if (UNLIKELY(*currentCharacter <= '\r' && (*currentCharacter == '\n' || (*currentCharacter | 0x1) == '\r'))) {
+ if (mode == AbortIfInvalid && UNLIKELY(*currentCharacter <= '\r' && (*currentCharacter == '\n' || (*currentCharacter | 0x1) == '\r'))) {
// String parsing is failed for character '\n', '\f' or '\r'.
return 0;
}
@@ -378,9 +385,13 @@ static inline CharacterType* checkAndSkipString(CharacterType* currentCharacter,
} else if (currentCharacter[1] == '\r') {
currentCharacter += currentCharacter[2] == '\n' ? 3 : 2;
} else {
- currentCharacter = checkAndSkipEscape(currentCharacter);
- if (!currentCharacter)
- return 0;
+ CharacterType* next = checkAndSkipEscape(currentCharacter);
+ if (!next) {
+ if (mode == AbortIfInvalid)
+ return 0;
+ next = currentCharacter + 1;
+ }
+ currentCharacter = next;
}
}
}
@@ -412,7 +423,7 @@ unsigned CSSTokenizer::parseEscape(CharacterType*& src)
return unicode;
}
- return *currentCharacter<CharacterType>()++;
+ return *src++;
}
template <>
@@ -438,6 +449,24 @@ inline void CSSTokenizer::UnicodeToChars<UChar>(UChar*& result, unsigned unicode
++result;
}
+template <typename SrcCharacterType>
+size_t CSSTokenizer::peekMaxIdentifierLen(SrcCharacterType* src)
+{
+ // The decoded form of an identifier (after resolving escape
+ // sequences) will not contain more characters (ASCII or UTF-16
+ // codepoints) than the input. This code can therefore ignore
+ // escape sequences completely.
+ SrcCharacterType* start = src;
+ do {
+ if (LIKELY(*src != '\\'))
+ src++;
+ else
+ parseEscape<SrcCharacterType>(src);
+ } while (isCSSLetter(src[0]) || (src[0] == '\\' && isCSSEscape(src[1])));
+
+ return src - start;
+}
+
template <typename SrcCharacterType, typename DestCharacterType>
inline bool CSSTokenizer::parseIdentifierInternal(SrcCharacterType*& src, DestCharacterType*& result, bool& hasEscape)
{
@@ -471,7 +500,7 @@ inline void CSSTokenizer::parseIdentifier(CharacterType*& result, CSSParserStrin
if (UNLIKELY(!parseIdentifierInternal(currentCharacter<CharacterType>(), result, hasEscape))) {
// Found an escape we couldn't handle with 8 bits, copy what has been recognized and continue
ASSERT(is8BitSource());
- UChar*& result16 = currentCharacter16();
+ UChar* result16 = allocateStringBuffer16((result - start) + peekMaxIdentifierLen(currentCharacter<CharacterType>()));
UChar* start16 = result16;
int i = 0;
for (; i < result - start; i++)
@@ -489,6 +518,18 @@ inline void CSSTokenizer::parseIdentifier(CharacterType*& result, CSSParserStrin
resultString.init(start, result - start);
}
+template <typename SrcCharacterType>
+size_t CSSTokenizer::peekMaxStringLen(SrcCharacterType* src, UChar quote)
+{
+ // The decoded form of a CSS string (after resolving escape
+ // sequences) will not contain more characters (ASCII or UTF-16
+ // codepoints) than the input. This code can therefore ignore
+ // escape sequences completely and just return the length of the
+ // input string (possibly including terminating quote if any).
+ SrcCharacterType* end = checkAndSkipString(src, quote, SkipInvalid);
+ return end ? end - src : 0;
+}
+
template <typename SrcCharacterType, typename DestCharacterType>
inline bool CSSTokenizer::parseStringInternal(SrcCharacterType*& src, DestCharacterType*& result, UChar quote)
{
@@ -502,8 +543,6 @@ inline bool CSSTokenizer::parseStringInternal(SrcCharacterType*& src, DestCharac
// String parsing is done, but don't advance pointer if at the end of input.
return true;
}
- ASSERT(*src > '\r' || (*src < '\n' && *src) || *src == '\v');
-
if (LIKELY(src[0] != '\\')) {
*result++ = *src++;
} else if (src[1] == '\n' || src[1] == '\f') {
@@ -532,7 +571,7 @@ inline void CSSTokenizer::parseString(CharacterType*& result, CSSParserString& r
if (UNLIKELY(!parseStringInternal(currentCharacter<CharacterType>(), result, quote))) {
// Found an escape we couldn't handle with 8 bits, copy what has been recognized and continue
ASSERT(is8BitSource());
- UChar*& result16 = currentCharacter16();
+ UChar* result16 = allocateStringBuffer16((result - start) + peekMaxStringLen(currentCharacter<CharacterType>(), quote));
UChar* start16 = result16;
int i = 0;
for (; i < result - start; i++)
@@ -556,7 +595,7 @@ inline bool CSSTokenizer::findURI(CharacterType*& start, CharacterType*& end, UC
if (*start == '"' || *start == '\'') {
quote = *start++;
- end = checkAndSkipString(start, quote);
+ end = checkAndSkipString(start, quote, AbortIfInvalid);
if (!end)
return false;
} else {
@@ -580,6 +619,29 @@ inline bool CSSTokenizer::findURI(CharacterType*& start, CharacterType*& end, UC
return true;
}
+template <typename SrcCharacterType>
+inline size_t CSSTokenizer::peekMaxURILen(SrcCharacterType* src, UChar quote)
+{
+ // The decoded form of a URI (after resolving escape sequences)
+ // will not contain more characters (ASCII or UTF-16 codepoints)
+ // than the input. This code can therefore ignore escape sequences
+ // completely.
+ SrcCharacterType* start = src;
+ if (quote) {
+ ASSERT(quote == '"' || quote == '\'');
+ return peekMaxStringLen(src, quote);
+ }
+
+ while (isURILetter(*src)) {
+ if (LIKELY(*src != '\\'))
+ src++;
+ else
+ parseEscape<SrcCharacterType>(src);
+ }
+
+ return src - start;
+}
+
template <typename SrcCharacterType, typename DestCharacterType>
inline bool CSSTokenizer::parseURIInternal(SrcCharacterType*& src, DestCharacterType*& dest, UChar quote)
{
@@ -593,7 +655,7 @@ inline bool CSSTokenizer::parseURIInternal(SrcCharacterType*& src, DestCharacter
*dest++ = *src++;
} else {
unsigned unicode = parseEscape<SrcCharacterType>(src);
- if (unicode > 0xff && sizeof(SrcCharacterType) == 1)
+ if (unicode > 0xff && sizeof(DestCharacterType) == 1)
return false;
UnicodeToChars(dest, unicode);
}
@@ -619,11 +681,12 @@ inline void CSSTokenizer::parseURI(CSSParserString& string)
// Reset the current character to the start of the URI and re-parse with
// a 16-bit destination.
ASSERT(is8BitSource());
- UChar* uriStart16 = currentCharacter16();
currentCharacter<CharacterType>() = uriStart;
- bool result = parseURIInternal(currentCharacter<CharacterType>(), currentCharacter16(), quote);
+ UChar* result16 = allocateStringBuffer16(peekMaxURILen(currentCharacter<CharacterType>(), quote));
+ UChar* uriStart16 = result16;
+ bool result = parseURIInternal(currentCharacter<CharacterType>(), result16, quote);
ASSERT_UNUSED(result, result);
- string.init(uriStart16, currentCharacter16() - uriStart16);
+ string.init(uriStart16, result16 - uriStart16);
}
currentCharacter<CharacterType>() = uriEnd + 1;
@@ -719,12 +782,6 @@ inline bool CSSTokenizer::detectFunctionTypeToken(int length)
m_token = CUEFUNCTION;
return true;
}
- CASE("var") {
- if (!RuntimeEnabledFeatures::cssVariablesEnabled())
- return false;
- m_token = VARFUNCTION;
- return true;
- }
CASE("calc") {
m_token = CALCFUNCTION;
return true;
@@ -733,6 +790,10 @@ inline bool CSSTokenizer::detectFunctionTypeToken(int length)
m_token = HOSTFUNCTION;
return true;
}
+ CASE("host-context") {
+ m_token = HOSTCONTEXTFUNCTION;
+ return true;
+ }
CASE("nth-child") {
m_parsingMode = NthChildMode;
return true;
@@ -881,18 +942,9 @@ inline void CSSTokenizer::detectDashToken(int length)
CASE("webkit-any") {
m_token = ANYFUNCTION;
}
- CASE("webkit-min") {
- m_token = MINFUNCTION;
- }
- CASE("webkit-max") {
- m_token = MAXFUNCTION;
- }
CASE("webkit-calc") {
m_token = CALCFUNCTION;
}
- CASE("webkit-distributed") {
- m_token = DISTRIBUTEDFUNCTION;
- }
}
}
@@ -1009,14 +1061,6 @@ inline void CSSTokenizer::detectAtToken(int length, bool hasEscape)
if (LIKELY(!hasEscape && m_internal))
m_token = INTERNAL_RULE_SYM;
}
- CASE("-webkit-region") {
- if (LIKELY(!hasEscape))
- m_token = WEBKIT_REGION_RULE_SYM;
- }
- CASE("-webkit-filter") {
- if (LIKELY(!hasEscape))
- m_token = WEBKIT_FILTER_RULE_SYM;
- }
CASE("-internal-decls") {
if (LIKELY(!hasEscape && m_internal))
m_token = INTERNAL_DECLS_SYM;
@@ -1075,18 +1119,6 @@ inline void CSSTokenizer::detectSupportsToken(int length)
}
}
-template <typename CharacterType>
-inline void CSSTokenizer::detectCSSVariableDefinitionToken(int length)
-{
- static const int prefixLength = static_cast<int>(sizeof("var-") - 1);
- if (length <= prefixLength)
- return;
- CharacterType* name = tokenStart<CharacterType>();
- COMPILE_ASSERT(prefixLength > 0, CSS_variable_prefix_must_be_nonempty);
- if (name[prefixLength - 1] == '-' && isIdentifierStartAfterDash(name + prefixLength) && isEqualToCSSCaseSensitiveIdentifier(name, "var"))
- m_token = VAR_DEFINITION;
-}
-
template <typename SrcCharacterType>
int CSSTokenizer::realLex(void* yylvalWithoutType)
{
@@ -1176,8 +1208,6 @@ restartAfterComment:
}
}
}
- } else if (UNLIKELY(RuntimeEnabledFeatures::cssVariablesEnabled())) {
- detectCSSVariableDefinitionToken<SrcCharacterType>(result - tokenStart<SrcCharacterType>());
}
break;
@@ -1338,7 +1368,7 @@ restartAfterComment:
break;
case CharacterQuote:
- if (checkAndSkipString(currentCharacter<SrcCharacterType>(), m_token)) {
+ if (checkAndSkipString(currentCharacter<SrcCharacterType>(), m_token, AbortIfInvalid)) {
++result;
parseString<SrcCharacterType>(result, yylval->string, m_token);
m_token = STRING;
@@ -1388,9 +1418,9 @@ restartAfterComment:
// Ignore comments. They are not even considered as white spaces.
if (*currentCharacter<SrcCharacterType>() == '*') {
const CSSParserLocation startLocation = currentLocation();
- if (m_parser.m_sourceDataHandler) {
+ if (m_parser.m_observer) {
unsigned startOffset = currentCharacter<SrcCharacterType>() - dataStart<SrcCharacterType>() - 1; // Start with a slash.
- m_parser.m_sourceDataHandler->startComment(startOffset - m_parsedTextPrefixLength);
+ m_parser.m_observer->startComment(startOffset - m_parsedTextPrefixLength);
}
++currentCharacter<SrcCharacterType>();
while (currentCharacter<SrcCharacterType>()[0] != '*' || currentCharacter<SrcCharacterType>()[1] != '/') {
@@ -1399,16 +1429,16 @@ restartAfterComment:
if (*currentCharacter<SrcCharacterType>() == '\0') {
// Unterminated comments are simply ignored.
currentCharacter<SrcCharacterType>() -= 2;
- m_parser.reportError(startLocation, CSSParser::UnterminatedCommentError);
+ m_parser.reportError(startLocation, UnterminatedCommentCSSError);
break;
}
++currentCharacter<SrcCharacterType>();
}
currentCharacter<SrcCharacterType>() += 2;
- if (m_parser.m_sourceDataHandler) {
+ if (m_parser.m_observer) {
unsigned endOffset = currentCharacter<SrcCharacterType>() - dataStart<SrcCharacterType>();
unsigned userTextEndOffset = static_cast<unsigned>(m_length - 1 - m_parsedTextSuffixLength);
- m_parser.m_sourceDataHandler->endComment(std::min(endOffset, userTextEndOffset) - m_parsedTextPrefixLength);
+ m_parser.m_observer->endComment(std::min(endOffset, userTextEndOffset) - m_parsedTextPrefixLength);
}
goto restartAfterComment;
}
@@ -1451,7 +1481,9 @@ restartAfterComment:
m_token = ATKEYWORD;
++result;
parseIdentifier(result, resultString, hasEscape);
- detectAtToken<SrcCharacterType>(result - tokenStart<SrcCharacterType>(), hasEscape);
+ // The standard enables unicode escapes in at-rules. In this case only the resultString will contain the
+ // correct identifier, hence we have to use it to determine its length instead of the usual pointer arithmetic.
+ detectAtToken<SrcCharacterType>(resultString.length() + 1, hasEscape);
}
break;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTokenizer.h b/chromium/third_party/WebKit/Source/core/css/CSSTokenizer.h
index 05b319c177a..508bf71ee29 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSTokenizer.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTokenizer.h
@@ -29,7 +29,7 @@
namespace WebCore {
-class CSSParser;
+class BisonCSSParser;
struct CSSParserLocation;
struct CSSParserString;
@@ -37,9 +37,9 @@ class CSSTokenizer {
WTF_MAKE_NONCOPYABLE(CSSTokenizer);
public:
// FIXME: This should not be needed but there are still some ties between the 2 classes.
- friend class CSSParser;
+ friend class BisonCSSParser;
- CSSTokenizer(CSSParser& parser)
+ CSSTokenizer(BisonCSSParser& parser)
: m_parser(parser)
, m_parsedTextPrefixLength(0)
, m_parsedTextSuffixLength(0)
@@ -74,7 +74,7 @@ public:
inline unsigned tokenStartOffset();
private:
- UChar*& currentCharacter16();
+ UChar* allocateStringBuffer16(size_t len);
template <typename CharacterType>
inline CharacterType*& currentCharacter();
@@ -92,29 +92,33 @@ private:
inline CSSParserLocation tokenLocation();
template <typename CharacterType>
- unsigned parseEscape(CharacterType*&);
+ static unsigned parseEscape(CharacterType*&);
template <typename DestCharacterType>
- inline void UnicodeToChars(DestCharacterType*&, unsigned);
- template <typename SrcCharacterType, typename DestCharacterType>
- inline bool parseIdentifierInternal(SrcCharacterType*&, DestCharacterType*&, bool&);
+ static inline void UnicodeToChars(DestCharacterType*&, unsigned);
+ template <typename SrcCharacterType, typename DestCharacterType>
+ static inline bool parseIdentifierInternal(SrcCharacterType*&, DestCharacterType*&, bool&);
+ template <typename SrcCharacterType>
+ static size_t peekMaxIdentifierLen(SrcCharacterType*);
template <typename CharacterType>
inline void parseIdentifier(CharacterType*&, CSSParserString&, bool&);
+ template <typename SrcCharacterType>
+ static size_t peekMaxStringLen(SrcCharacterType*, UChar quote);
template <typename SrcCharacterType, typename DestCharacterType>
- inline bool parseStringInternal(SrcCharacterType*&, DestCharacterType*&, UChar);
-
+ static inline bool parseStringInternal(SrcCharacterType*&, DestCharacterType*&, UChar);
template <typename CharacterType>
inline void parseString(CharacterType*&, CSSParserString& resultString, UChar);
template <typename CharacterType>
inline bool findURI(CharacterType*& start, CharacterType*& end, UChar& quote);
-
+ template <typename SrcCharacterType>
+ static size_t peekMaxURILen(SrcCharacterType*, UChar quote);
template <typename SrcCharacterType, typename DestCharacterType>
- inline bool parseURIInternal(SrcCharacterType*&, DestCharacterType*&, UChar quote);
-
+ static inline bool parseURIInternal(SrcCharacterType*&, DestCharacterType*&, UChar quote);
template <typename CharacterType>
inline void parseURI(CSSParserString&);
+
template <typename CharacterType>
inline bool parseUnicodeRange();
template <typename CharacterType>
@@ -133,13 +137,11 @@ private:
inline void detectAtToken(int, bool);
template <typename CharacterType>
inline void detectSupportsToken(int);
- template <typename CharacterType>
- inline void detectCSSVariableDefinitionToken(int);
template <typename SourceCharacterType>
int realLex(void* yylval);
- CSSParser& m_parser;
+ BisonCSSParser& m_parser;
size_t m_parsedTextPrefixLength;
size_t m_parsedTextSuffixLength;
@@ -157,6 +159,13 @@ private:
OwnPtr<UChar[]> m_dataStart16;
LChar* m_currentCharacter8;
UChar* m_currentCharacter16;
+
+ // During parsing of an ASCII stylesheet we might locate escape
+ // sequences that expand into UTF-16 code points. Strings,
+ // identifiers and URIs containing such escape sequences are
+ // stored in m_cssStrings16 so that we don't have to store the
+ // whole stylesheet as UTF-16.
+ Vector<OwnPtr<UChar[]> > m_cssStrings16;
union {
LChar* ptr8;
UChar* ptr16;
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.cpp
index de981949bd3..ebb21b931ba 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.cpp
@@ -76,20 +76,15 @@ String CSSTransformValue::customCSSText() const
return transformValueToCssString(m_type, CSSValueList::customCSSText());
}
-String CSSTransformValue::customSerializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- return transformValueToCssString(m_type, CSSValueList::customSerializeResolvingVariables(variables));
-}
-
CSSTransformValue::CSSTransformValue(const CSSTransformValue& cloneFrom)
: CSSValueList(cloneFrom)
, m_type(cloneFrom.m_type)
{
}
-PassRefPtr<CSSTransformValue> CSSTransformValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSTransformValue> CSSTransformValue::cloneForCSSOM() const
{
- return adoptRef(new CSSTransformValue(*this));
+ return adoptRefWillBeNoop(new CSSTransformValue(*this));
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.h b/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.h
index 1ca3bbd45f1..11cd454a0d0 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSTransformValue.h
@@ -59,18 +59,19 @@ public:
Matrix3DTransformOperation
};
- static PassRefPtr<CSSTransformValue> create(TransformOperationType type)
+ static PassRefPtrWillBeRawPtr<CSSTransformValue> create(TransformOperationType type)
{
- return adoptRef(new CSSTransformValue(type));
+ return adoptRefWillBeNoop(new CSSTransformValue(type));
}
String customCSSText() const;
bool equals(const CSSTransformValue& other) const { return m_type == other.m_type && CSSValueList::equals(other); }
- String customSerializeResolvingVariables(const HashMap<AtomicString, String>&) const;
TransformOperationType operationType() const { return m_type; }
- PassRefPtr<CSSTransformValue> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSTransformValue> cloneForCSSOM() const;
+
+ void traceAfterDispatch(Visitor* visitor) { CSSValueList::traceAfterDispatch(visitor); }
private:
CSSTransformValue(TransformOperationType);
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSUnicodeRangeValue.h b/chromium/third_party/WebKit/Source/core/css/CSSUnicodeRangeValue.h
index 3ce02a98cc6..c198a237d6e 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSUnicodeRangeValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSUnicodeRangeValue.h
@@ -33,9 +33,9 @@ namespace WebCore {
class CSSUnicodeRangeValue : public CSSValue {
public:
- static PassRefPtr<CSSUnicodeRangeValue> create(UChar32 from, UChar32 to)
+ static PassRefPtrWillBeRawPtr<CSSUnicodeRangeValue> create(UChar32 from, UChar32 to)
{
- return adoptRef(new CSSUnicodeRangeValue(from, to));
+ return adoptRefWillBeNoop(new CSSUnicodeRangeValue(from, to));
}
UChar32 from() const { return m_from; }
@@ -45,6 +45,8 @@ public:
bool equals(const CSSUnicodeRangeValue&) const;
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
CSSUnicodeRangeValue(UChar32 from, UChar32 to)
: CSSValue(UnicodeRangeClass)
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSUnknownRule.h b/chromium/third_party/WebKit/Source/core/css/CSSUnknownRule.h
index 629aaead0d3..06d1be4283a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSUnknownRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSUnknownRule.h
@@ -26,7 +26,7 @@
namespace WebCore {
-class CSSUnknownRule : public CSSRule {
+class CSSUnknownRule FINAL : public CSSRule {
public:
CSSUnknownRule() : CSSRule(0) { }
virtual ~CSSUnknownRule() { }
@@ -34,6 +34,7 @@ public:
virtual CSSRule::Type type() const OVERRIDE { return UNKNOWN_RULE; }
virtual String cssText() const OVERRIDE { return String(); }
virtual void reattach(StyleRuleBase*) OVERRIDE { }
+ virtual void trace(Visitor* visitor) OVERRIDE { CSSRule::trace(visitor); }
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValue.cpp b/chromium/third_party/WebKit/Source/core/css/CSSValue.cpp
index 6d74434cc11..332638e95eb 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValue.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValue.cpp
@@ -41,29 +41,25 @@
#include "core/css/CSSFunctionValue.h"
#include "core/css/CSSGradientValue.h"
#include "core/css/CSSGridLineNamesValue.h"
-#include "core/css/CSSGridTemplateValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
#include "core/css/CSSImageSetValue.h"
#include "core/css/CSSImageValue.h"
#include "core/css/CSSInheritedValue.h"
#include "core/css/CSSInitialValue.h"
#include "core/css/CSSLineBoxContainValue.h"
-#include "core/css/CSSMixFunctionValue.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSReflectValue.h"
#include "core/css/CSSSVGDocumentValue.h"
-#include "core/css/CSSShaderValue.h"
#include "core/css/CSSShadowValue.h"
#include "core/css/CSSTimingFunctionValue.h"
#include "core/css/CSSTransformValue.h"
#include "core/css/CSSUnicodeRangeValue.h"
#include "core/css/CSSValueList.h"
-#include "core/css/CSSVariableValue.h"
-#include "core/svg/SVGColor.h"
#include "core/svg/SVGPaint.h"
namespace WebCore {
-struct SameSizeAsCSSValue : public RefCounted<SameSizeAsCSSValue> {
+struct SameSizeAsCSSValue : public RefCountedWillBeGarbageCollectedFinalized<SameSizeAsCSSValue> {
uint32_t bitfields;
};
@@ -71,10 +67,15 @@ COMPILE_ASSERT(sizeof(CSSValue) <= sizeof(SameSizeAsCSSValue), CSS_value_should_
class TextCloneCSSValue : public CSSValue {
public:
- static PassRefPtr<TextCloneCSSValue> create(ClassType classType, const String& text) { return adoptRef(new TextCloneCSSValue(classType, text)); }
+ static PassRefPtrWillBeRawPtr<TextCloneCSSValue> create(ClassType classType, const String& text)
+ {
+ return adoptRefWillBeNoop(new TextCloneCSSValue(classType, text));
+ }
String cssText() const { return m_cssText; }
+ void traceAfterDispatch(Visitor* visitor) { CSSValue::traceAfterDispatch(visitor); }
+
private:
TextCloneCSSValue(ClassType classType, const String& text)
: CSSValue(classType, /*isCSSOMSafe*/ true)
@@ -106,21 +107,6 @@ CSSValue::Type CSSValue::cssValueType() const
return CSS_CUSTOM;
}
-void CSSValue::addSubresourceStyleURLs(ListHashSet<KURL>& urls, const StyleSheetContents* styleSheet) const
-{
- // This should get called for internal instances only.
- ASSERT(!isCSSOMSafe());
-
- if (isPrimitiveValue())
- toCSSPrimitiveValue(this)->addSubresourceStyleURLs(urls, styleSheet);
- else if (isValueList())
- toCSSValueList(this)->addSubresourceStyleURLs(urls, styleSheet);
- else if (classType() == FontFaceSrcClass)
- toCSSFontFaceSrcValue(this)->addSubresourceStyleURLs(urls, styleSheet);
- else if (classType() == ReflectClass)
- toCSSReflectValue(this)->addSubresourceStyleURLs(urls, styleSheet);
-}
-
bool CSSValue::hasFailedOrCanceledSubresources() const
{
// This should get called for internal instances only.
@@ -185,8 +171,8 @@ bool CSSValue::equals(const CSSValue& other) const
return compareCSSValues<CSSInitialValue>(*this, other);
case GridLineNamesClass:
return compareCSSValues<CSSGridLineNamesValue>(*this, other);
- case GridTemplateClass:
- return compareCSSValues<CSSGridTemplateValue>(*this, other);
+ case GridTemplateAreasClass:
+ return compareCSSValues<CSSGridTemplateAreasValue>(*this, other);
case PrimitiveClass:
return compareCSSValues<CSSPrimitiveValue>(*this, other);
case ReflectClass:
@@ -213,14 +199,6 @@ bool CSSValue::equals(const CSSValue& other) const
return compareCSSValues<CSSFilterValue>(*this, other);
case CSSArrayFunctionValueClass:
return compareCSSValues<CSSArrayFunctionValue>(*this, other);
- case CSSMixFunctionValueClass:
- return compareCSSValues<CSSMixFunctionValue>(*this, other);
- case CSSShaderClass:
- return compareCSSValues<CSSShaderValue>(*this, other);
- case VariableClass:
- return compareCSSValues<CSSVariableValue>(*this, other);
- case SVGColorClass:
- return compareCSSValues<SVGColor>(*this, other);
case SVGPaintClass:
return compareCSSValues<SVGPaint>(*this, other);
case CSSSVGDocumentClass:
@@ -275,8 +253,8 @@ String CSSValue::cssText() const
return toCSSInitialValue(this)->customCSSText();
case GridLineNamesClass:
return toCSSGridLineNamesValue(this)->customCSSText();
- case GridTemplateClass:
- return toCSSGridTemplateValue(this)->customCSSText();
+ case GridTemplateAreasClass:
+ return toCSSGridTemplateAreasValue(this)->customCSSText();
case PrimitiveClass:
return toCSSPrimitiveValue(this)->customCSSText();
case ReflectClass:
@@ -303,14 +281,6 @@ String CSSValue::cssText() const
return toCSSFilterValue(this)->customCSSText();
case CSSArrayFunctionValueClass:
return toCSSArrayFunctionValue(this)->customCSSText();
- case CSSMixFunctionValueClass:
- return toCSSMixFunctionValue(this)->customCSSText();
- case CSSShaderClass:
- return toCSSShaderValue(this)->customCSSText();
- case VariableClass:
- return toCSSVariableValue(this)->value();
- case SVGColorClass:
- return toSVGColor(this)->customCSSText();
case SVGPaintClass:
return toSVGPaint(this)->customCSSText();
case CSSSVGDocumentClass:
@@ -320,22 +290,6 @@ String CSSValue::cssText() const
return String();
}
-String CSSValue::serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- switch (classType()) {
- case PrimitiveClass:
- return toCSSPrimitiveValue(this)->customSerializeResolvingVariables(variables);
- case ReflectClass:
- return toCSSReflectValue(this)->customSerializeResolvingVariables(variables);
- case ValueListClass:
- return toCSSValueList(this)->customSerializeResolvingVariables(variables);
- case CSSTransformClass:
- return toCSSTransformValue(this)->customSerializeResolvingVariables(variables);
- default:
- return cssText();
- }
-}
-
void CSSValue::destroy()
{
if (m_isTextClone) {
@@ -391,8 +345,8 @@ void CSSValue::destroy()
case GridLineNamesClass:
delete toCSSGridLineNamesValue(this);
return;
- case GridTemplateClass:
- delete toCSSGridTemplateValue(this);
+ case GridTemplateAreasClass:
+ delete toCSSGridTemplateAreasValue(this);
return;
case PrimitiveClass:
delete toCSSPrimitiveValue(this);
@@ -433,29 +387,231 @@ void CSSValue::destroy()
case CSSArrayFunctionValueClass:
delete toCSSArrayFunctionValue(this);
return;
- case CSSMixFunctionValueClass:
- delete toCSSMixFunctionValue(this);
+ case SVGPaintClass:
+ delete toSVGPaint(this);
+ return;
+ case CSSSVGDocumentClass:
+ delete toCSSSVGDocumentValue(this);
+ return;
+ }
+ ASSERT_NOT_REACHED();
+}
+
+void CSSValue::finalizeGarbageCollectedObject()
+{
+ if (m_isTextClone) {
+ ASSERT(isCSSOMSafe());
+ static_cast<TextCloneCSSValue*>(this)->~TextCloneCSSValue();
+ return;
+ }
+ ASSERT(!isCSSOMSafe() || isSubtypeExposedToCSSOM());
+
+ switch (classType()) {
+ case AspectRatioClass:
+ toCSSAspectRatioValue(this)->~CSSAspectRatioValue();
+ return;
+ case BorderImageSliceClass:
+ toCSSBorderImageSliceValue(this)->~CSSBorderImageSliceValue();
+ return;
+ case CanvasClass:
+ toCSSCanvasValue(this)->~CSSCanvasValue();
+ return;
+ case CursorImageClass:
+ toCSSCursorImageValue(this)->~CSSCursorImageValue();
+ return;
+ case FontClass:
+ toCSSFontValue(this)->~CSSFontValue();
+ return;
+ case FontFaceSrcClass:
+ toCSSFontFaceSrcValue(this)->~CSSFontFaceSrcValue();
+ return;
+ case FontFeatureClass:
+ toCSSFontFeatureValue(this)->~CSSFontFeatureValue();
+ return;
+ case FunctionClass:
+ toCSSFunctionValue(this)->~CSSFunctionValue();
+ return;
+ case LinearGradientClass:
+ toCSSLinearGradientValue(this)->~CSSLinearGradientValue();
+ return;
+ case RadialGradientClass:
+ toCSSRadialGradientValue(this)->~CSSRadialGradientValue();
+ return;
+ case CrossfadeClass:
+ toCSSCrossfadeValue(this)->~CSSCrossfadeValue();
+ return;
+ case ImageClass:
+ toCSSImageValue(this)->~CSSImageValue();
+ return;
+ case InheritedClass:
+ toCSSInheritedValue(this)->~CSSInheritedValue();
+ return;
+ case InitialClass:
+ toCSSInitialValue(this)->~CSSInitialValue();
+ return;
+ case GridLineNamesClass:
+ toCSSGridLineNamesValue(this)->~CSSGridLineNamesValue();
+ return;
+ case GridTemplateAreasClass:
+ toCSSGridTemplateAreasValue(this)->~CSSGridTemplateAreasValue();
+ return;
+ case PrimitiveClass:
+ toCSSPrimitiveValue(this)->~CSSPrimitiveValue();
+ return;
+ case ReflectClass:
+ toCSSReflectValue(this)->~CSSReflectValue();
+ return;
+ case ShadowClass:
+ toCSSShadowValue(this)->~CSSShadowValue();
+ return;
+ case CubicBezierTimingFunctionClass:
+ toCSSCubicBezierTimingFunctionValue(this)->~CSSCubicBezierTimingFunctionValue();
+ return;
+ case StepsTimingFunctionClass:
+ toCSSStepsTimingFunctionValue(this)->~CSSStepsTimingFunctionValue();
+ return;
+ case UnicodeRangeClass:
+ toCSSUnicodeRangeValue(this)->~CSSUnicodeRangeValue();
+ return;
+ case ValueListClass:
+ toCSSValueList(this)->~CSSValueList();
+ return;
+ case CSSTransformClass:
+ toCSSTransformValue(this)->~CSSTransformValue();
+ return;
+ case LineBoxContainClass:
+ toCSSLineBoxContainValue(this)->~CSSLineBoxContainValue();
return;
- case CSSShaderClass:
- delete toCSSShaderValue(this);
+ case CalculationClass:
+ toCSSCalcValue(this)->~CSSCalcValue();
return;
- case VariableClass:
- delete toCSSVariableValue(this);
+ case ImageSetClass:
+ toCSSImageSetValue(this)->~CSSImageSetValue();
return;
- case SVGColorClass:
- delete toSVGColor(this);
+ case CSSFilterClass:
+ toCSSFilterValue(this)->~CSSFilterValue();
+ return;
+ case CSSArrayFunctionValueClass:
+ toCSSArrayFunctionValue(this)->~CSSArrayFunctionValue();
return;
case SVGPaintClass:
- delete toSVGPaint(this);
+ toSVGPaint(this)->~SVGPaint();
return;
case CSSSVGDocumentClass:
- delete toCSSSVGDocumentValue(this);
+ toCSSSVGDocumentValue(this)->~CSSSVGDocumentValue();
+ return;
+ }
+ ASSERT_NOT_REACHED();
+}
+
+void CSSValue::trace(Visitor* visitor)
+{
+ if (m_isTextClone) {
+ ASSERT(isCSSOMSafe());
+ static_cast<TextCloneCSSValue*>(this)->traceAfterDispatch(visitor);
+ return;
+ }
+ ASSERT(!isCSSOMSafe() || isSubtypeExposedToCSSOM());
+
+ switch (classType()) {
+ case AspectRatioClass:
+ toCSSAspectRatioValue(this)->traceAfterDispatch(visitor);
+ return;
+ case BorderImageSliceClass:
+ toCSSBorderImageSliceValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CanvasClass:
+ toCSSCanvasValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CursorImageClass:
+ toCSSCursorImageValue(this)->traceAfterDispatch(visitor);
+ return;
+ case FontClass:
+ toCSSFontValue(this)->traceAfterDispatch(visitor);
+ return;
+ case FontFaceSrcClass:
+ toCSSFontFaceSrcValue(this)->traceAfterDispatch(visitor);
+ return;
+ case FontFeatureClass:
+ toCSSFontFeatureValue(this)->traceAfterDispatch(visitor);
+ return;
+ case FunctionClass:
+ toCSSFunctionValue(this)->traceAfterDispatch(visitor);
+ return;
+ case LinearGradientClass:
+ toCSSLinearGradientValue(this)->traceAfterDispatch(visitor);
+ return;
+ case RadialGradientClass:
+ toCSSRadialGradientValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CrossfadeClass:
+ toCSSCrossfadeValue(this)->traceAfterDispatch(visitor);
+ return;
+ case ImageClass:
+ toCSSImageValue(this)->traceAfterDispatch(visitor);
+ return;
+ case InheritedClass:
+ toCSSInheritedValue(this)->traceAfterDispatch(visitor);
+ return;
+ case InitialClass:
+ toCSSInitialValue(this)->traceAfterDispatch(visitor);
+ return;
+ case GridLineNamesClass:
+ toCSSGridLineNamesValue(this)->traceAfterDispatch(visitor);
+ return;
+ case GridTemplateAreasClass:
+ toCSSGridTemplateAreasValue(this)->traceAfterDispatch(visitor);
+ return;
+ case PrimitiveClass:
+ toCSSPrimitiveValue(this)->traceAfterDispatch(visitor);
+ return;
+ case ReflectClass:
+ toCSSReflectValue(this)->traceAfterDispatch(visitor);
+ return;
+ case ShadowClass:
+ toCSSShadowValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CubicBezierTimingFunctionClass:
+ toCSSCubicBezierTimingFunctionValue(this)->traceAfterDispatch(visitor);
+ return;
+ case StepsTimingFunctionClass:
+ toCSSStepsTimingFunctionValue(this)->traceAfterDispatch(visitor);
+ return;
+ case UnicodeRangeClass:
+ toCSSUnicodeRangeValue(this)->traceAfterDispatch(visitor);
+ return;
+ case ValueListClass:
+ toCSSValueList(this)->traceAfterDispatch(visitor);
+ return;
+ case CSSTransformClass:
+ toCSSTransformValue(this)->traceAfterDispatch(visitor);
+ return;
+ case LineBoxContainClass:
+ toCSSLineBoxContainValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CalculationClass:
+ toCSSCalcValue(this)->traceAfterDispatch(visitor);
+ return;
+ case ImageSetClass:
+ toCSSImageSetValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CSSFilterClass:
+ toCSSFilterValue(this)->traceAfterDispatch(visitor);
+ return;
+ case CSSArrayFunctionValueClass:
+ toCSSArrayFunctionValue(this)->traceAfterDispatch(visitor);
+ return;
+ case SVGPaintClass:
+ toSVGPaint(this)->traceAfterDispatch(visitor);
+ return;
+ case CSSSVGDocumentClass:
+ toCSSSVGDocumentValue(this)->traceAfterDispatch(visitor);
return;
}
ASSERT_NOT_REACHED();
}
-PassRefPtr<CSSValue> CSSValue::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSValue> CSSValue::cloneForCSSOM() const
{
switch (classType()) {
case PrimitiveClass:
@@ -469,14 +625,10 @@ PassRefPtr<CSSValue> CSSValue::cloneForCSSOM() const
return toCSSFilterValue(this)->cloneForCSSOM();
case CSSArrayFunctionValueClass:
return toCSSArrayFunctionValue(this)->cloneForCSSOM();
- case CSSMixFunctionValueClass:
- return toCSSMixFunctionValue(this)->cloneForCSSOM();
case CSSTransformClass:
return toCSSTransformValue(this)->cloneForCSSOM();
case ImageSetClass:
return toCSSImageSetValue(this)->cloneForCSSOM();
- case SVGColorClass:
- return toSVGColor(this)->cloneForCSSOM();
case SVGPaintClass:
return toSVGPaint(this)->cloneForCSSOM();
default:
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValue.h b/chromium/third_party/WebKit/Source/core/css/CSSValue.h
index e6b21b8ce2b..a883479b899 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValue.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValue.h
@@ -22,6 +22,7 @@
#define CSSValue_h
#include "core/dom/ExceptionCode.h"
+#include "platform/heap/Handle.h"
#include "platform/weborigin/KURL.h"
#include "wtf/HashMap.h"
#include "wtf/ListHashSet.h"
@@ -40,7 +41,7 @@ enum CSSTextFormattingFlags { QuoteCSSStringIfNeeded, AlwaysQuoteCSSString };
// They should be handled by separate wrapper classes.
// Please don't expose more CSSValue types to the web.
-class CSSValue : public RefCounted<CSSValue> {
+class CSSValue : public RefCountedWillBeGarbageCollectedFinalized<CSSValue> {
public:
enum Type {
CSS_INHERIT = 0,
@@ -53,17 +54,20 @@ public:
// Override RefCounted's deref() to ensure operator delete is called on
// the appropriate subclass type.
+ // When oilpan is enabled the finalize method is called by the garbage
+ // collector and not immediately when deref reached zero.
+#if !ENABLE(OILPAN)
void deref()
{
if (derefBase())
destroy();
}
+#endif // !ENABLE(OILPAN)
Type cssValueType() const;
String cssText() const;
void setCSSText(const String&, ExceptionState&) { } // FIXME: Not implemented.
- String serializeResolvingVariables(const HashMap<AtomicString, String>&) const;
bool isPrimitiveValue() const { return m_classType == PrimitiveClass; }
bool isValueList() const { return m_classType >= ValueListClass; }
@@ -98,11 +102,7 @@ public:
bool isCalcValue() const {return m_classType == CalculationClass; }
bool isFilterValue() const { return m_classType == CSSFilterClass; }
bool isArrayFunctionValue() const { return m_classType == CSSArrayFunctionValueClass; }
- bool isMixFunctionValue() const { return m_classType == CSSMixFunctionValueClass; }
- bool isShaderValue() const { return m_classType == CSSShaderClass; }
- bool isVariableValue() const { return m_classType == VariableClass; }
- bool isGridTemplateValue() const { return m_classType == GridTemplateClass; }
- bool isSVGColor() const { return m_classType == SVGColorClass || m_classType == SVGPaintClass; }
+ bool isGridTemplateAreasValue() const { return m_classType == GridTemplateAreasClass; }
bool isSVGPaint() const { return m_classType == SVGPaintClass; }
bool isSVGDocumentValue() const { return m_classType == CSSSVGDocumentClass; }
bool isUnicodeRangeValue() const { return m_classType == UnicodeRangeClass; }
@@ -111,17 +111,19 @@ public:
bool isCSSOMSafe() const { return m_isCSSOMSafe; }
bool isSubtypeExposedToCSSOM() const
{
- return isPrimitiveValue() || isSVGColor() || isValueList();
+ return isPrimitiveValue() || isSVGPaint() || isValueList();
}
- PassRefPtr<CSSValue> cloneForCSSOM() const;
-
- void addSubresourceStyleURLs(ListHashSet<KURL>&, const StyleSheetContents*) const;
+ PassRefPtrWillBeRawPtr<CSSValue> cloneForCSSOM() const;
bool hasFailedOrCanceledSubresources() const;
bool equals(const CSSValue&) const;
+ void finalizeGarbageCollectedObject();
+ void traceAfterDispatch(Visitor*) { }
+ void trace(Visitor*);
+
protected:
static const size_t ClassTypeBits = 6;
@@ -158,12 +160,9 @@ protected:
UnicodeRangeClass,
LineBoxContainClass,
CalculationClass,
- CSSShaderClass,
- VariableClass,
- GridTemplateClass,
+ GridTemplateAreasClass,
// SVG classes.
- SVGColorClass,
SVGPaintClass,
CSSSVGDocumentClass,
@@ -172,7 +171,6 @@ protected:
ImageSetClass,
CSSFilterClass,
CSSArrayFunctionValueClass,
- CSSMixFunctionValueClass,
CSSTransformClass,
GridLineNamesClass,
// Do not append non-list class types here.
@@ -213,7 +211,7 @@ protected:
// to maximize struct packing.
// CSSPrimitiveValue bits:
- unsigned m_primitiveUnitType : 7; // CSSPrimitiveValue::UnitTypes
+ unsigned m_primitiveUnitType : 7; // CSSPrimitiveValue::UnitType
mutable unsigned m_hasCachedCSSText : 1;
unsigned m_isQuirkValue : 1;
@@ -223,16 +221,16 @@ private:
unsigned m_classType : ClassTypeBits; // ClassType
};
-template<typename CSSValueType>
-inline bool compareCSSValueVector(const Vector<RefPtr<CSSValueType> >& firstVector, const Vector<RefPtr<CSSValueType> >& secondVector)
+template<typename CSSValueType, size_t inlineCapacity>
+inline bool compareCSSValueVector(const WillBeHeapVector<RefPtrWillBeMember<CSSValueType>, inlineCapacity>& firstVector, const WillBeHeapVector<RefPtrWillBeMember<CSSValueType>, inlineCapacity>& secondVector)
{
size_t size = firstVector.size();
if (size != secondVector.size())
return false;
for (size_t i = 0; i < size; i++) {
- const RefPtr<CSSValueType>& firstPtr = firstVector[i];
- const RefPtr<CSSValueType>& secondPtr = secondVector[i];
+ const RefPtrWillBeMember<CSSValueType>& firstPtr = firstVector[i];
+ const RefPtrWillBeMember<CSSValueType>& secondPtr = secondVector[i];
if (firstPtr == secondPtr || (firstPtr && secondPtr && firstPtr->equals(*secondPtr)))
continue;
return false;
@@ -246,6 +244,18 @@ inline bool compareCSSValuePtr(const RefPtr<CSSValueType>& first, const RefPtr<C
return first ? second && first->equals(*second) : !second;
}
+template<typename CSSValueType>
+inline bool compareCSSValuePtr(const RawPtr<CSSValueType>& first, const RawPtr<CSSValueType>& second)
+{
+ return first ? second && first->equals(*second) : !second;
+}
+
+template<typename CSSValueType>
+inline bool compareCSSValuePtr(const Member<CSSValueType>& first, const Member<CSSValueType>& second)
+{
+ return first ? second && first->equals(*second) : !second;
+}
+
#define DEFINE_CSS_VALUE_TYPE_CASTS(thisType, predicate) \
DEFINE_TYPE_CASTS(thisType, CSSValue, value, value->predicate, value.predicate)
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValue.idl b/chromium/third_party/WebKit/Source/core/css/CSSValue.idl
index dfdacd3a828..145010b29bb 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValue.idl
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValue.idl
@@ -21,6 +21,7 @@
[
Custom=Wrap,
DependentLifetime,
+ WillBeGarbageCollected,
] interface CSSValue {
// UnitTypes
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValueKeywords.in b/chromium/third_party/WebKit/Source/core/css/CSSValueKeywords.in
index c2c3a1b4765..c8512398070 100755..100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValueKeywords.in
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValueKeywords.in
@@ -9,10 +9,11 @@
inherit
initial
//
-// CSS_PROP_OUTLINE_STYLE
-// CSS_PROP_BORDER_TOP_STYLE
-// CSS_PROP_BORDER_BOTTOM_STYLE
-// CSS_PROP_BORDER_LEFT_STYLE
+// outline-style
+// border-top-style
+// border-bottom-style
+// border-left-style
+// border-right-style
// The order here must match the order of the EBorderStyle enum in RenderStyleConstants.h.
none
hidden
@@ -26,7 +27,7 @@ solid
double
//
-// CSS_PROP_FONT:
+// font
//
caption
icon
@@ -39,20 +40,21 @@ small-caption
status-bar
//
-// CSS_PROP_FONT_STYLE:
+// font-style
//
//normal
italic
oblique
// The following is only allowed in @font-face:
all
+
//
-// CSS_PROP_FONT_VARIANT:
+// font-variant
//
//normal
small-caps
-// -webkit-font-variant-ligatures:
+// font-variant-ligatures:
//
// normal
common-ligatures
@@ -61,9 +63,11 @@ discretionary-ligatures
no-discretionary-ligatures
historical-ligatures
no-historical-ligatures
+contextual
+no-contextual
//
-// CSS_PROP_FONT_WEIGHT:
+// font-weigth
//
normal
bold
@@ -78,8 +82,9 @@ lighter
700
800
900
+
//
-// CSS_PROP_FONT_SIZE:
+// font-size
//
xx-small
x-small
@@ -91,22 +96,9 @@ xx-large
-webkit-xxx-large
smaller
larger
+
//
-// CSS_PROP_FONT_STRETCH:
-//
-//normal
-wider
-narrower
-ultra-condensed
-extra-condensed
-condensed
-semi-condensed
-semi-expanded
-expanded
-extra-expanded
-ultra-expanded
-//
-// CSS_PROP_GENERIC_FONT_FAMILY:
+// font-family (<generic-family> in CSS 2.1)
//
serif
sans-serif
@@ -115,9 +107,10 @@ fantasy
monospace
-webkit-body
-webkit-pictograph
+
//
//
-// CSS_PROP_*_COLOR
+// *-color
//
aqua
black
@@ -177,7 +170,7 @@ grey
// colors in non strict mode
-webkit-text mode=QuirksOrUASheet
//
-// CSS_PROP_BACKGROUND_REPEAT:
+// background-repeat
//
repeat
repeat-x
@@ -186,7 +179,7 @@ no-repeat
// round
// space
//
-// CSS_PROP__WEBKIT_BACKGROUND_COMPOSITE:
+// -webkit-background-composite
//
clear
copy
@@ -203,7 +196,7 @@ plus-darker
// highlight
plus-lighter
//
-// CSS_PROP_VERTICAL_ALIGN:
+// vertical-align
//
baseline
middle
@@ -216,7 +209,7 @@ bottom
// HTML alignment MIDDLE has no corresponding CSS alignment
-webkit-baseline-middle
//
-// CSS_PROP_TEXT_ALIGN:
+// text-align
// The order here must match the order of the ETextAlign enum in RenderStyleConstants.h.
//
-webkit-auto
@@ -229,19 +222,19 @@ justify
-webkit-center
-webkit-match-parent
//
-// CSS_PROP_TEXT_JUSTIFY:
+// text-justify
//
//auto
//none
inter-word
distribute
//
-// CSS_PROP_LIST_STYLE_POSITION:
+// list-style-position
//
outside
inside
//
-// CSS_PROP_LIST_STYLE_TYPE:
+// list-style-type
// The order here must match the order of the EListStyleType enum in RenderStyleConstants.h.
//
disc
@@ -326,7 +319,7 @@ hiragana-iroha
katakana-iroha
//none
//
-// CSS_PROP_DISPLAY:
+// display
// The order here must match the order of the EDisplay enum in RenderStyleConstants.h.
//
inline
@@ -349,12 +342,11 @@ flex
inline-flex
grid
inline-grid
-lazy-block
//none
-webkit-flex
-webkit-inline-flex
//
-// CSS_PROP_CURSOR:
+// cursor
// The order here must match the order of the ECursor enum in RenderStyleConstants.h.
//
auto
@@ -370,8 +362,8 @@ alias
progress
no-drop
not-allowed
--webkit-zoom-in
--webkit-zoom-out
+zoom-in
+zoom-out
e-resize
ne-resize
nw-resize
@@ -392,21 +384,23 @@ help
all-scroll
-webkit-grab
-webkit-grabbing
+-webkit-zoom-in
+-webkit-zoom-out
// none
//
-// CSS_PROP_DIRECTION:
+// direction
//
ltr
rtl
//
-// CSS_PROP_TEXT_TRANSFORM:
+// text-transform
//
capitalize
uppercase
lowercase
//none
//
-// CSS_PROP_VISIBILITY:
+// visibility
//
visible
//hidden
@@ -428,13 +422,10 @@ bidi-override
blink
both
close-quote
-crop
-cross
embed
fixed
hand
hide
-higher
invert
-webkit-isolate
-webkit-isolate-override
@@ -443,12 +434,8 @@ landscape
ledger
legal
letter
-level
line-through
local
-loud
-lower
-mix
no-close-quote
no-open-quote
nowrap
@@ -472,38 +459,38 @@ wavy
-webkit-nowrap
// CSS3 Values
-// CSS_PROP_BOX_ALIGN
+// box-align
stretch
start
end
//center
//baseline
-// CSS_PROP_BOX_DECORATION_BREAK
+// box-decoration-break
clone
slice
-// CSS_PROP_BOX_DIRECTION
+// box-direction
// normal
reverse
-// CSS_PROP_BOX_ORIENT
+// box-orient
horizontal
vertical
inline-axis
block-axis
-// CSS_PROP_BOX_PACK
+// box-pack
// start
// end
// center
// justify
-// CSS_PROP_BOX_LINES
+// box-lines
single
multiple
-// CSS_PROP_ALIGN_CONTENT
+// align-content
flex-start
flex-end
// center
@@ -511,21 +498,21 @@ space-between
space-around
// stretch
-// CSS_PROP_ALIGN_ITEMS / CSS_PROP_ALIGN_SELF
+// align-items / align-self
// flex-start
// flex-end
// center
// baseline
// stretch
-// CSS_PROP_JUSTIFY_CONTENT
+// justify-content
// flex-start
// flex-end
// center
// space-between
// space-around
-// CSS_PROP_FLEX_FLOW
+// flex-flow
row
row-reverse
column
@@ -534,7 +521,7 @@ column-reverse
// wrap
wrap-reverse
-// CSS_PROP_MARQUEE_DIRECTION
+// -internal-marquee-direction
forwards
backwards
ahead
@@ -545,39 +532,34 @@ up
down
// auto
-// CSS_PROP_MARQUEE_SPEED
+// -internal-marquee-speed
slow
// normal
fast
-// CSS_PROP_MARQUEE_REPETITION
+// -internal-marquee-repetition
infinite
-// CSS_PROP_MARQUEE_STYLE
+// -internal-marquee-style
// none
slide
// scroll
alternate
//
-// CSS_PROP__KHTML_USER_MODIFY
+// -webkit-user-modify
//
read-only
read-write
read-write-plaintext-only
//
-// CSS_PROP__KHTML_USER_DRAG
+// -webkit-user-drag
//
element
//
-// CSS_PROP__KHTML_USER_SELECT
-//
-ignore
-
-//
-// CSS_PROP_WIDTH/MIN_WIDTH/MAX_WIDTH
+// width/min-width/max-width
//
intrinsic
min-intrinsic
@@ -594,48 +576,48 @@ min-content
max-content
//
-// CSS_PROP_TEXT_OVERFLOW
+// text-overflow
//
clip
ellipsis
//
-// CSS_PROP__KHTML_MARGIN_COLLAPSE
+// -webkit-margin-collapse
//
// collapse
// separate
discard
//
-// CSS_PROP_TEXT_*_COLOR
+// text-*-color
//
dot-dash
dot-dot-dash
wave
//
-// CSS_PROP_TEXT_*_MODE
+// text-*-mode
//
continuous
skip-white-space
//
-// CSS_PROP_WORD_BREAK
+// word-break
//
break-all
//
-// CSS_PROP_WORD_WRAP
+// word-wrap
//
break-word
//
-// CSS_PROP__KHTML_NBSP_MODE
+// nbsp-mode
//
space
//
-// CSS_PROP__KHTML_LINE_BREAK
+// -webkit-line-break
//
// auto
loose
@@ -653,7 +635,6 @@ square-button
button
button-bevel
inner-spin-button
--webkit-input-speech-button
listbox
listitem
media-enter-fullscreen-button
@@ -663,17 +644,12 @@ media-fullscreen-volume-slider-thumb
media-mute-button
media-play-button
media-overlay-play-button
-media-seek-back-button
-media-seek-forward-button
-media-rewind-button
-media-return-to-realtime-button
media-toggle-closed-captions-button
media-slider
media-sliderthumb
media-volume-slider-container
media-volume-slider
media-volume-sliderthumb
-media-volume-slider-mute-button
media-controls-background
media-controls-fullscreen-background
media-current-time-display
@@ -704,14 +680,14 @@ textarea
caps-lock-indicator
//
-// CSS_PROP_BORDER_IMAGE
+// border-image
//
// stretch
// repeat
round
//
-// CSS_PROP_BACKGROUND_CLIP/ORIGIN
+// background-clip/background-origin
//
// border/content/padding are deprecated and ultimately will only apply to the -webkit- form of these properties.
// border-box/content-box/padding-box should be used instead.
@@ -723,7 +699,7 @@ content-box
padding
padding-box
-// CSS_SHAPES
+// CSS 3 SHAPES
margin-box
//
@@ -733,50 +709,50 @@ contain
cover
//
-// CSS_PROP__KHTML_RTL_ORDERING
+// -webkit-rtl-ordering
//
logical
visual
//
-// CSS_PROP__WEBKIT_BORDER_FIT
+// -webkit-border-fit
//
lines
//
-// CSS_PROP__WEBKIT_ANIMATION_DIRECTION
+// animation-direction
//
// alternate
alternate-reverse
//
-// CSS_PROP__WEBKIT_ANIMATION_FILL_MODE
+// animation-fill-mode
//
// forwards
// backwards
// both
//
-// CSS_PROP__WEBKIT_ANIMATION_ITERATION_COUNT
+// animation-iteration-count
//
// infinite
//
-// CSS_PROP__WEBKIT_ANIMATION_PLAY_STATE
+// animation-play-state
//
running
paused
//
-// CSS_PROP__WEBKIT_TRANSFORM_STYLE
+// transform-style
//
flat
preserve-3d
//
-// CSS_PROP__WEBKIT_TRANSITION_TIMING_FUNCTION
-// CSS_PROP__WEBKIT_ANIMATION_TIMING_FUNCTION
+// transition-timing-function
+// animation-timing-function
//
ease
linear
@@ -784,22 +760,23 @@ ease-in
ease-out
ease-in-out
step-start
+step-middle
step-end
//
-// CSS_PROP_ZOOM
+// zoom
//
document
reset
//
-// CSS_PROP_USER_ZOOM
+// user-zoom
//
// fixed
zoom
//
-// CSS_PROP_POINTER_EVENTS
+// pointer-events
//
visiblePainted
visibleFill
@@ -813,7 +790,7 @@ bounding-box
//none
//
-// CSS_PROP_SPEECH
+// speech
//
spell-out
digits
@@ -838,16 +815,6 @@ geometricPrecision
economy
exact
-// (-webkit-view-mode:) media feature:
-floating
-fullscreen
-maximized
-minimized
-windowed
-
-// -webkit-hyphenate-limit-lines
-no-limit
-
// -webkit-writing-mode
// SVG compatibility
lr
@@ -911,15 +878,12 @@ off
optimizeQuality
-webkit-optimize-contrast
-// shape-inside
// shape-outside
nonzero
evenodd
-outside-shape
-
-// -webkit-region-fragment
-// auto
-break
+at
+// closest-side
+// farthest-side
// -webkit-wrap-flow
// auto
@@ -933,9 +897,6 @@ maximum
wrap
// none
-// -webkit-line-align
-edges
-
alphabetic
// position
@@ -946,13 +907,6 @@ sticky
coarse
fine
-// -webkit-filter
-// values for the custom() function
-// border-box
-// padding-box
-// content-box
-filter-box
-detached
// blend modes
// normal
multiply
@@ -985,17 +939,20 @@ balance
drag
no-drag
-// -webkit-grid-{start|end|before|after}
+// grid-{column|row}-{start|end}
span
// text-indent
each-line
+//hanging // hanging exists in SVGCSSValueKeywords.in
// (scan:) media feature
progressive
interlace
-// CSS_PROP_PAINT_ORDER
+//
+// paint-order
+//
// normal
// fill
// stroke
@@ -1017,3 +974,34 @@ script
// touch-action
pan-x
pan-y
+manipulation
+
+// justify-self
+// auto
+// stretch
+// baseline
+// center
+// start
+// end
+self-start
+self-end
+// flex-start
+// flex-end
+// left
+// right
+true
+safe
+
+// scroll-behavior
+instant
+smooth
+
+// will-change
+// auto
+contents
+scroll-position
+
+// all
+// initial
+// inherit
+unset
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValueList.cpp b/chromium/third_party/WebKit/Source/core/css/CSSValueList.cpp
index e1505c2e504..9d31f6bdf5b 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValueList.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValueList.cpp
@@ -53,7 +53,7 @@ bool CSSValueList::removeAll(CSSValue* val)
{
bool found = false;
for (size_t index = 0; index < m_values.size(); index++) {
- RefPtr<CSSValue>& value = m_values.at(index);
+ RefPtrWillBeMember<CSSValue>& value = m_values.at(index);
if (value && val && value->equals(*val)) {
m_values.remove(index);
found = true;
@@ -66,16 +66,16 @@ bool CSSValueList::removeAll(CSSValue* val)
bool CSSValueList::hasValue(CSSValue* val) const
{
for (size_t index = 0; index < m_values.size(); index++) {
- const RefPtr<CSSValue>& value = m_values.at(index);
+ const RefPtrWillBeMember<CSSValue>& value = m_values.at(index);
if (value && val && value->equals(*val))
return true;
}
return false;
}
-PassRefPtr<CSSValueList> CSSValueList::copy()
+PassRefPtrWillBeRawPtr<CSSValueList> CSSValueList::copy()
{
- RefPtr<CSSValueList> newList;
+ RefPtrWillBeRawPtr<CSSValueList> newList = nullptr;
switch (m_valueListSeparator) {
case SpaceSeparator:
newList = createSpaceSeparated();
@@ -127,9 +127,7 @@ String CSSValueList::customCSSText(CSSTextFormattingFlags formattingFlag) const
bool CSSValueList::equals(const CSSValueList& other) const
{
- // FIXME: the explicit Vector conversion copies into a temporary and is
- // wasteful.
- return m_valueListSeparator == other.m_valueListSeparator && compareCSSValueVector<CSSValue>(Vector<RefPtr<CSSValue> >(m_values), Vector<RefPtr<CSSValue> >(other.m_values));
+ return m_valueListSeparator == other.m_valueListSeparator && compareCSSValueVector(m_values, other.m_values);
}
bool CSSValueList::equals(const CSSValue& other) const
@@ -137,45 +135,10 @@ bool CSSValueList::equals(const CSSValue& other) const
if (m_values.size() != 1)
return false;
- const RefPtr<CSSValue>& value = m_values[0];
+ const RefPtrWillBeMember<CSSValue>& value = m_values[0];
return value && value->equals(other);
}
-String CSSValueList::customSerializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
-{
- StringBuilder result;
- String separator;
- switch (m_valueListSeparator) {
- case SpaceSeparator:
- separator = " ";
- break;
- case CommaSeparator:
- separator = ", ";
- break;
- case SlashSeparator:
- separator = " / ";
- break;
- default:
- ASSERT_NOT_REACHED();
- }
-
- unsigned size = m_values.size();
- for (unsigned i = 0; i < size; i++) {
- if (!result.isEmpty())
- result.append(separator);
- result.append(m_values[i]->serializeResolvingVariables(variables));
- }
-
- return result.toString();
-}
-
-void CSSValueList::addSubresourceStyleURLs(ListHashSet<KURL>& urls, const StyleSheetContents* styleSheet) const
-{
- size_t size = m_values.size();
- for (size_t i = 0; i < size; ++i)
- m_values[i]->addSubresourceStyleURLs(urls, styleSheet);
-}
-
bool CSSValueList::hasFailedOrCanceledSubresources() const
{
for (unsigned i = 0; i < m_values.size(); ++i) {
@@ -194,9 +157,15 @@ CSSValueList::CSSValueList(const CSSValueList& cloneFrom)
m_values[i] = cloneFrom.m_values[i]->cloneForCSSOM();
}
-PassRefPtr<CSSValueList> CSSValueList::cloneForCSSOM() const
+PassRefPtrWillBeRawPtr<CSSValueList> CSSValueList::cloneForCSSOM() const
+{
+ return adoptRefWillBeNoop(new CSSValueList(*this));
+}
+
+void CSSValueList::traceAfterDispatch(Visitor* visitor)
{
- return adoptRef(new CSSValueList(*this));
+ visitor->trace(m_values);
+ CSSValue::traceAfterDispatch(visitor);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValueList.h b/chromium/third_party/WebKit/Source/core/css/CSSValueList.h
index 2f08014f190..2d34b4f9406 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValueList.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValueList.h
@@ -31,21 +31,21 @@ class CSSParserValueList;
class CSSValueList : public CSSValue {
public:
- static PassRefPtr<CSSValueList> createCommaSeparated()
+ static PassRefPtrWillBeRawPtr<CSSValueList> createCommaSeparated()
{
- return adoptRef(new CSSValueList(CommaSeparator));
+ return adoptRefWillBeNoop(new CSSValueList(CommaSeparator));
}
- static PassRefPtr<CSSValueList> createSpaceSeparated()
+ static PassRefPtrWillBeRawPtr<CSSValueList> createSpaceSeparated()
{
- return adoptRef(new CSSValueList(SpaceSeparator));
+ return adoptRefWillBeNoop(new CSSValueList(SpaceSeparator));
}
- static PassRefPtr<CSSValueList> createSlashSeparated()
+ static PassRefPtrWillBeRawPtr<CSSValueList> createSlashSeparated()
{
- return adoptRef(new CSSValueList(SlashSeparator));
+ return adoptRefWillBeNoop(new CSSValueList(SlashSeparator));
}
- static PassRefPtr<CSSValueList> createFromParserValueList(CSSParserValueList* list)
+ static PassRefPtrWillBeRawPtr<CSSValueList> createFromParserValueList(CSSParserValueList* list)
{
- return adoptRef(new CSSValueList(list));
+ return adoptRefWillBeNoop(new CSSValueList(list));
}
size_t length() const { return m_values.size(); }
@@ -53,22 +53,21 @@ public:
const CSSValue* item(size_t index) const { return index < m_values.size() ? m_values[index].get() : 0; }
CSSValue* itemWithoutBoundsCheck(size_t index) { return m_values[index].get(); }
- void append(PassRefPtr<CSSValue> value) { m_values.append(value); }
- void prepend(PassRefPtr<CSSValue> value) { m_values.prepend(value); }
+ void append(PassRefPtrWillBeRawPtr<CSSValue> value) { m_values.append(value); }
+ void prepend(PassRefPtrWillBeRawPtr<CSSValue> value) { m_values.prepend(value); }
bool removeAll(CSSValue*);
bool hasValue(CSSValue*) const;
- PassRefPtr<CSSValueList> copy();
+ PassRefPtrWillBeRawPtr<CSSValueList> copy();
String customCSSText(CSSTextFormattingFlags = QuoteCSSStringIfNeeded) const;
bool equals(const CSSValueList&) const;
bool equals(const CSSValue&) const;
- String customSerializeResolvingVariables(const HashMap<AtomicString, String>&) const;
-
- void addSubresourceStyleURLs(ListHashSet<KURL>&, const StyleSheetContents*) const;
bool hasFailedOrCanceledSubresources() const;
- PassRefPtr<CSSValueList> cloneForCSSOM() const;
+ PassRefPtrWillBeRawPtr<CSSValueList> cloneForCSSOM() const;
+
+ void traceAfterDispatch(Visitor*);
protected:
CSSValueList(ClassType, ValueListSeparator);
@@ -78,7 +77,7 @@ private:
explicit CSSValueList(ValueListSeparator);
explicit CSSValueList(CSSParserValueList*);
- Vector<RefPtr<CSSValue>, 4> m_values;
+ WillBeHeapVector<RefPtrWillBeMember<CSSValue>, 4> m_values;
};
DEFINE_CSS_VALUE_TYPE_CASTS(CSSValueList, isValueList());
@@ -86,6 +85,7 @@ DEFINE_CSS_VALUE_TYPE_CASTS(CSSValueList, isValueList());
// Objects of this class are intended to be stack-allocated and scoped to a single function.
// Please take care not to pass these around as they do hold onto a raw pointer.
class CSSValueListInspector {
+ STACK_ALLOCATED();
public:
CSSValueListInspector(CSSValue* value) : m_list((value && value->isValueList()) ? toCSSValueList(value) : 0) { }
CSSValue* item(size_t index) const { ASSERT_WITH_SECURITY_IMPLICATION(index < length()); return m_list->itemWithoutBoundsCheck(index); }
@@ -93,13 +93,14 @@ public:
CSSValue* second() const { return item(1); }
size_t length() const { return m_list ? m_list->length() : 0; }
private:
- CSSValueList* m_list;
+ RawPtrWillBeMember<CSSValueList> m_list;
};
// Wrapper that can be used to iterate over any CSSValue. Non-list values and 0 behave as zero-length lists.
// Objects of this class are intended to be stack-allocated and scoped to a single function.
// Please take care not to pass these around as they do hold onto a raw pointer.
class CSSValueListIterator {
+ STACK_ALLOCATED();
public:
CSSValueListIterator(CSSValue* value) : m_inspector(value), m_position(0) { }
bool hasMore() const { return m_position < m_inspector.length(); }
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValuePool.cpp b/chromium/third_party/WebKit/Source/core/css/CSSValuePool.cpp
index 4550915eba4..3d914d33198 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValuePool.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValuePool.cpp
@@ -26,7 +26,7 @@
#include "config.h"
#include "core/css/CSSValuePool.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSValueList.h"
#include "core/rendering/style/RenderStyle.h"
@@ -34,8 +34,13 @@ namespace WebCore {
CSSValuePool& cssValuePool()
{
+#if ENABLE(OILPAN)
+ DEFINE_STATIC_LOCAL(Persistent<CSSValuePool>, pool, (new CSSValuePool()));
+ return *pool;
+#else
DEFINE_STATIC_LOCAL(CSSValuePool, pool, ());
return pool;
+#endif // ENABLE(OILPAN)
}
CSSValuePool::CSSValuePool()
@@ -46,9 +51,13 @@ CSSValuePool::CSSValuePool()
, m_colorWhite(CSSPrimitiveValue::createColor(Color::white))
, m_colorBlack(CSSPrimitiveValue::createColor(Color::black))
{
+ m_identifierValueCache.resize(numCSSValueKeywords);
+ m_pixelValueCache.resize(maximumCacheableIntegerValue + 1);
+ m_percentValueCache.resize(maximumCacheableIntegerValue + 1);
+ m_numberValueCache.resize(maximumCacheableIntegerValue + 1);
}
-PassRefPtr<CSSPrimitiveValue> CSSValuePool::createIdentifierValue(CSSValueID ident)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSValuePool::createIdentifierValue(CSSValueID ident)
{
if (ident <= 0)
return CSSPrimitiveValue::createIdentifier(ident);
@@ -58,12 +67,12 @@ PassRefPtr<CSSPrimitiveValue> CSSValuePool::createIdentifierValue(CSSValueID ide
return m_identifierValueCache[ident];
}
-PassRefPtr<CSSPrimitiveValue> CSSValuePool::createIdentifierValue(CSSPropertyID ident)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSValuePool::createIdentifierValue(CSSPropertyID ident)
{
return CSSPrimitiveValue::createIdentifier(ident);
}
-PassRefPtr<CSSPrimitiveValue> CSSValuePool::createColorValue(unsigned rgbValue)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSValuePool::createColorValue(unsigned rgbValue)
{
// These are the empty and deleted values of the hash table.
if (rgbValue == Color::transparent)
@@ -79,15 +88,18 @@ PassRefPtr<CSSPrimitiveValue> CSSValuePool::createColorValue(unsigned rgbValue)
if (m_colorValueCache.size() > maximumColorCacheSize)
m_colorValueCache.clear();
- RefPtr<CSSPrimitiveValue> dummyValue;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> dummyValue = nullptr;
ColorValueCache::AddResult entry = m_colorValueCache.add(rgbValue, dummyValue);
if (entry.isNewEntry)
- entry.iterator->value = CSSPrimitiveValue::createColor(rgbValue);
- return entry.iterator->value;
+ entry.storedValue->value = CSSPrimitiveValue::createColor(rgbValue);
+ return entry.storedValue->value;
}
-PassRefPtr<CSSPrimitiveValue> CSSValuePool::createValue(double value, CSSPrimitiveValue::UnitTypes type)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSValuePool::createValue(double value, CSSPrimitiveValue::UnitType type)
{
+ if (std::isinf(value))
+ value = 0;
+
if (value < 0 || value > maximumCacheableIntegerValue)
return CSSPrimitiveValue::create(value, type);
@@ -95,50 +107,65 @@ PassRefPtr<CSSPrimitiveValue> CSSValuePool::createValue(double value, CSSPrimiti
if (value != intValue)
return CSSPrimitiveValue::create(value, type);
- RefPtr<CSSPrimitiveValue>* cache;
switch (type) {
case CSSPrimitiveValue::CSS_PX:
- cache = m_pixelValueCache;
- break;
+ if (!m_pixelValueCache[intValue])
+ m_pixelValueCache[intValue] = CSSPrimitiveValue::create(value, type);
+ return m_pixelValueCache[intValue];
case CSSPrimitiveValue::CSS_PERCENTAGE:
- cache = m_percentValueCache;
- break;
+ if (!m_percentValueCache[intValue])
+ m_percentValueCache[intValue] = CSSPrimitiveValue::create(value, type);
+ return m_percentValueCache[intValue];
case CSSPrimitiveValue::CSS_NUMBER:
- cache = m_numberValueCache;
- break;
+ if (!m_numberValueCache[intValue])
+ m_numberValueCache[intValue] = CSSPrimitiveValue::create(value, type);
+ return m_numberValueCache[intValue];
default:
return CSSPrimitiveValue::create(value, type);
}
-
- if (!cache[intValue])
- cache[intValue] = CSSPrimitiveValue::create(value, type);
- return cache[intValue];
}
-PassRefPtr<CSSPrimitiveValue> CSSValuePool::createValue(const Length& value, const RenderStyle& style)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSValuePool::createValue(const Length& value, const RenderStyle& style)
{
return CSSPrimitiveValue::create(value, style.effectiveZoom());
}
-PassRefPtr<CSSPrimitiveValue> CSSValuePool::createFontFamilyValue(const String& familyName)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSValuePool::createFontFamilyValue(const String& familyName)
{
- RefPtr<CSSPrimitiveValue>& value = m_fontFamilyValueCache.add(familyName, 0).iterator->value;
+ RefPtrWillBeMember<CSSPrimitiveValue>& value = m_fontFamilyValueCache.add(familyName, nullptr).storedValue->value;
if (!value)
value = CSSPrimitiveValue::create(familyName, CSSPrimitiveValue::CSS_STRING);
return value;
}
-PassRefPtr<CSSValueList> CSSValuePool::createFontFaceValue(const AtomicString& string)
+PassRefPtrWillBeRawPtr<CSSValueList> CSSValuePool::createFontFaceValue(const AtomicString& string)
{
// Just wipe out the cache and start rebuilding if it gets too big.
const unsigned maximumFontFaceCacheSize = 128;
if (m_fontFaceValueCache.size() > maximumFontFaceCacheSize)
m_fontFaceValueCache.clear();
- RefPtr<CSSValueList>& value = m_fontFaceValueCache.add(string, 0).iterator->value;
+ RefPtrWillBeMember<CSSValueList>& value = m_fontFaceValueCache.add(string, nullptr).storedValue->value;
if (!value)
- value = CSSParser::parseFontFaceValue(string);
+ value = BisonCSSParser::parseFontFaceValue(string);
return value;
}
+void CSSValuePool::trace(Visitor* visitor)
+{
+ visitor->trace(m_inheritedValue);
+ visitor->trace(m_implicitInitialValue);
+ visitor->trace(m_explicitInitialValue);
+ visitor->trace(m_identifierValueCache);
+ visitor->trace(m_colorValueCache);
+ visitor->trace(m_colorTransparent);
+ visitor->trace(m_colorWhite);
+ visitor->trace(m_colorBlack);
+ visitor->trace(m_pixelValueCache);
+ visitor->trace(m_percentValueCache);
+ visitor->trace(m_numberValueCache);
+ visitor->trace(m_fontFaceValueCache);
+ visitor->trace(m_fontFamilyValueCache);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSValuePool.h b/chromium/third_party/WebKit/Source/core/css/CSSValuePool.h
index 75b8984a1f7..87eacf6d385 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSValuePool.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSValuePool.h
@@ -26,8 +26,8 @@
#ifndef CSSValuePool_h
#define CSSValuePool_h
-#include "CSSPropertyNames.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSPropertyNames.h"
+#include "core/CSSValueKeywords.h"
#include "core/css/CSSInheritedValue.h"
#include "core/css/CSSInitialValue.h"
#include "core/css/CSSPrimitiveValue.h"
@@ -39,48 +39,50 @@ namespace WebCore {
class CSSValueList;
-class CSSValuePool {
- WTF_MAKE_FAST_ALLOCATED;
+class CSSValuePool : public NoBaseWillBeGarbageCollected<CSSValuePool> {
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- PassRefPtr<CSSValueList> createFontFaceValue(const AtomicString&);
- PassRefPtr<CSSPrimitiveValue> createFontFamilyValue(const String&);
- PassRefPtr<CSSInheritedValue> createInheritedValue() { return m_inheritedValue; }
- PassRefPtr<CSSInitialValue> createImplicitInitialValue() { return m_implicitInitialValue; }
- PassRefPtr<CSSInitialValue> createExplicitInitialValue() { return m_explicitInitialValue; }
- PassRefPtr<CSSPrimitiveValue> createIdentifierValue(CSSValueID identifier);
- PassRefPtr<CSSPrimitiveValue> createIdentifierValue(CSSPropertyID identifier);
- PassRefPtr<CSSPrimitiveValue> createColorValue(unsigned rgbValue);
- PassRefPtr<CSSPrimitiveValue> createValue(double value, CSSPrimitiveValue::UnitTypes);
- PassRefPtr<CSSPrimitiveValue> createValue(const String& value, CSSPrimitiveValue::UnitTypes type) { return CSSPrimitiveValue::create(value, type); }
- PassRefPtr<CSSPrimitiveValue> createValue(const Length& value, const RenderStyle&);
- PassRefPtr<CSSPrimitiveValue> createValue(const Length& value, float zoom) { return CSSPrimitiveValue::create(value, zoom); }
- template<typename T> static PassRefPtr<CSSPrimitiveValue> createValue(T value) { return CSSPrimitiveValue::create(value); }
+ PassRefPtrWillBeRawPtr<CSSValueList> createFontFaceValue(const AtomicString&);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createFontFamilyValue(const String&);
+ PassRefPtrWillBeRawPtr<CSSInheritedValue> createInheritedValue() { return m_inheritedValue; }
+ PassRefPtrWillBeRawPtr<CSSInitialValue> createImplicitInitialValue() { return m_implicitInitialValue; }
+ PassRefPtrWillBeRawPtr<CSSInitialValue> createExplicitInitialValue() { return m_explicitInitialValue; }
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createIdentifierValue(CSSValueID identifier);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createIdentifierValue(CSSPropertyID identifier);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createColorValue(unsigned rgbValue);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createValue(double value, CSSPrimitiveValue::UnitType);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createValue(const String& value, CSSPrimitiveValue::UnitType type) { return CSSPrimitiveValue::create(value, type); }
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createValue(const Length& value, const RenderStyle&);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createValue(const Length& value, float zoom) { return CSSPrimitiveValue::create(value, zoom); }
+ template<typename T> static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createValue(T value) { return CSSPrimitiveValue::create(value); }
+
+ void trace(Visitor*);
private:
CSSValuePool();
- RefPtr<CSSInheritedValue> m_inheritedValue;
- RefPtr<CSSInitialValue> m_implicitInitialValue;
- RefPtr<CSSInitialValue> m_explicitInitialValue;
+ RefPtrWillBeMember<CSSInheritedValue> m_inheritedValue;
+ RefPtrWillBeMember<CSSInitialValue> m_implicitInitialValue;
+ RefPtrWillBeMember<CSSInitialValue> m_explicitInitialValue;
- RefPtr<CSSPrimitiveValue> m_identifierValueCache[numCSSValueKeywords];
+ WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue>, numCSSValueKeywords> m_identifierValueCache;
- typedef HashMap<unsigned, RefPtr<CSSPrimitiveValue> > ColorValueCache;
+ typedef WillBeHeapHashMap<unsigned, RefPtrWillBeMember<CSSPrimitiveValue> > ColorValueCache;
ColorValueCache m_colorValueCache;
- RefPtr<CSSPrimitiveValue> m_colorTransparent;
- RefPtr<CSSPrimitiveValue> m_colorWhite;
- RefPtr<CSSPrimitiveValue> m_colorBlack;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_colorTransparent;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_colorWhite;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_colorBlack;
static const int maximumCacheableIntegerValue = 255;
- RefPtr<CSSPrimitiveValue> m_pixelValueCache[maximumCacheableIntegerValue + 1];
- RefPtr<CSSPrimitiveValue> m_percentValueCache[maximumCacheableIntegerValue + 1];
- RefPtr<CSSPrimitiveValue> m_numberValueCache[maximumCacheableIntegerValue + 1];
+ WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue>, maximumCacheableIntegerValue + 1> m_pixelValueCache;
+ WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue>, maximumCacheableIntegerValue + 1> m_percentValueCache;
+ WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue>, maximumCacheableIntegerValue + 1> m_numberValueCache;
- typedef HashMap<AtomicString, RefPtr<CSSValueList> > FontFaceValueCache;
+ typedef WillBeHeapHashMap<AtomicString, RefPtrWillBeMember<CSSValueList> > FontFaceValueCache;
FontFaceValueCache m_fontFaceValueCache;
- typedef HashMap<String, RefPtr<CSSPrimitiveValue> > FontFamilyValueCache;
+ typedef WillBeHeapHashMap<String, RefPtrWillBeMember<CSSPrimitiveValue> > FontFamilyValueCache;
FontFamilyValueCache m_fontFamilyValueCache;
friend CSSValuePool& cssValuePool();
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariableValue.h b/chromium/third_party/WebKit/Source/core/css/CSSVariableValue.h
deleted file mode 100644
index 525581ae19c..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariableValue.h
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (C) 2012 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
- * its contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
- * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef CSSVariableValue_h
-#define CSSVariableValue_h
-
-#include "CSSPropertyNames.h"
-#include "core/css/CSSParserValues.h"
-#include "core/css/CSSValue.h"
-
-namespace WebCore {
-
-class CSSVariableValue : public CSSValue {
-public:
- static PassRefPtr<CSSVariableValue> create(const AtomicString& name, const String& value)
- {
- return adoptRef(new CSSVariableValue(name, value));
- }
-
- const AtomicString& name() const { return m_name; }
- const String& value() const { return m_value; }
-
- bool equals(const CSSVariableValue& other) const { return m_name == other.m_name && m_value == other.m_value; }
-
-private:
- CSSVariableValue(const AtomicString& name, const String& value)
- : CSSValue(VariableClass)
- , m_name(name)
- , m_value(value)
- {
- }
-
- const AtomicString m_name;
- const String m_value;
-};
-
-DEFINE_CSS_VALUE_TYPE_CASTS(CSSVariableValue, isVariableValue());
-
-}
-
-#endif /* CSSVariableValue_h */
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariablesIterator.h b/chromium/third_party/WebKit/Source/core/css/CSSVariablesIterator.h
deleted file mode 100644
index edfe3a7e9ed..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariablesIterator.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef CSSVariablesIterator_h
-#define CSSVariablesIterator_h
-
-#include "wtf/RefCounted.h"
-
-namespace WebCore {
-
-class CSSVariablesIterator : public RefCounted<CSSVariablesIterator> {
-public:
- virtual ~CSSVariablesIterator() { }
- virtual void advance() = 0;
- virtual bool atEnd() const = 0;
- virtual AtomicString name() const = 0;
- virtual String value() const = 0;
- virtual void addedVariable(const AtomicString& name) { }
- virtual void removedVariable(const AtomicString& name) { }
- virtual void clearedVariables() { }
-};
-
-}
-
-#endif // CSSVariablesIterator_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.cpp b/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.cpp
deleted file mode 100644
index eb6232dd43a..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.cpp
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
- * its contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
- * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "core/css/CSSVariablesMap.h"
-
-#include "core/css/CSSStyleDeclaration.h"
-
-namespace WebCore {
-
-unsigned CSSVariablesMap::size() const
-{
- if (m_styleDeclaration)
- return m_styleDeclaration->variableCount();
- return 0;
-}
-
-String CSSVariablesMap::get(const AtomicString& name) const
-{
- if (m_styleDeclaration)
- return m_styleDeclaration->variableValue(name);
- return String();
-}
-
-bool CSSVariablesMap::has(const AtomicString& name) const
-{
- if (m_styleDeclaration)
- return !get(name).isEmpty();
- return false;
-}
-
-void CSSVariablesMap::set(const AtomicString& name, const String& value, ExceptionState& exceptionState)
-{
- if (!m_styleDeclaration)
- return;
- if (m_styleDeclaration->setVariableValue(name, value, exceptionState)) {
- Iterators::iterator end = m_activeIterators.end();
- for (Iterators::iterator it = m_activeIterators.begin(); it != end; ++it)
- (*it)->addedVariable(name);
- }
-}
-
-bool CSSVariablesMap::remove(const AtomicString& name)
-{
- if (!m_styleDeclaration)
- return false;
- if (m_styleDeclaration->removeVariable(name)) {
- Iterators::iterator end = m_activeIterators.end();
- for (Iterators::iterator it = m_activeIterators.begin(); it != end; ++it)
- (*it)->removedVariable(name);
- return true;
- }
- return false;
-}
-
-void CSSVariablesMap::clear(ExceptionState& exceptionState)
-{
- if (!m_styleDeclaration)
- return;
- if (m_styleDeclaration->clearVariables(exceptionState)) {
- Iterators::iterator end = m_activeIterators.end();
- for (Iterators::iterator it = m_activeIterators.begin(); it != end; ++it)
- (*it)->clearedVariables();
- }
-}
-
-void CSSVariablesMap::forEach(PassOwnPtr<CSSVariablesMapForEachCallback> callback, ScriptValue& thisArg) const
-{
- forEach(callback, &thisArg);
-}
-
-void CSSVariablesMap::forEach(PassOwnPtr<CSSVariablesMapForEachCallback> callback) const
-{
- forEach(callback, 0);
-}
-
-void CSSVariablesMap::forEach(PassOwnPtr<CSSVariablesMapForEachCallback> callback, ScriptValue* thisArg) const
-{
- if (!m_styleDeclaration)
- return;
- RefPtr<CSSVariablesIterator> iterator = m_styleDeclaration->variablesIterator();
- m_activeIterators.append(iterator.get());
- while (!iterator->atEnd()) {
- String name = iterator->name();
- String value = iterator->value();
- if (thisArg)
- callback->handleItem(*thisArg, value, name, const_cast<CSSVariablesMap*>(this));
- else
- callback->handleItem(value, name, const_cast<CSSVariablesMap*>(this));
- iterator->advance();
- }
- ASSERT(m_activeIterators.last() == iterator.get());
- m_activeIterators.removeLast();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.h b/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.h
deleted file mode 100644
index 12b1bee2845..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.h
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef CSSVariablesMap_h
-#define CSSVariablesMap_h
-
-#include "RuntimeEnabledFeatures.h"
-#include "core/css/CSSVariablesMapForEachCallback.h"
-#include "wtf/PassOwnPtr.h"
-#include "wtf/RefCounted.h"
-#include "wtf/text/WTFString.h"
-
-namespace WebCore {
-
-class CSSStyleDeclaration;
-class CSSVariablesIterator;
-class ExceptionState;
-
-class CSSVariablesMap FINAL : public RefCounted<CSSVariablesMap> {
-public:
- static PassRefPtr<CSSVariablesMap> create(CSSStyleDeclaration* styleDeclaration)
- {
- return adoptRef(new CSSVariablesMap(styleDeclaration));
- }
-
- unsigned size() const;
- String get(const AtomicString& name) const;
- bool has(const AtomicString& name) const;
- void set(const AtomicString& name, const String& value, ExceptionState&);
- bool remove(const AtomicString& name);
- void clear(ExceptionState&);
- void forEach(PassOwnPtr<CSSVariablesMapForEachCallback>, ScriptValue& thisArg) const;
- void forEach(PassOwnPtr<CSSVariablesMapForEachCallback>) const;
-
- void clearStyleDeclaration() { m_styleDeclaration = 0; }
-
-private:
- explicit CSSVariablesMap(CSSStyleDeclaration* styleDeclaration)
- : m_styleDeclaration(styleDeclaration)
- {
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- }
-
- void forEach(PassOwnPtr<CSSVariablesMapForEachCallback>, ScriptValue* thisArg) const;
-
- CSSStyleDeclaration* m_styleDeclaration;
- typedef Vector<CSSVariablesIterator*> Iterators;
- mutable Iterators m_activeIterators;
-};
-
-} // namespace WebCore
-
-#endif // CSSVariablesMap_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.cpp b/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.cpp
index a5d1f0e9cf9..9c56ee4a48b 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.cpp
@@ -46,8 +46,10 @@ CSSViewportRule::CSSViewportRule(StyleRuleViewport* viewportRule, CSSStyleSheet*
CSSViewportRule::~CSSViewportRule()
{
+#if !ENABLE(OILPAN)
if (m_propertiesCSSOMWrapper)
m_propertiesCSSOMWrapper->clearParentRule();
+#endif
}
CSSStyleDeclaration* CSSViewportRule::style() const
@@ -63,7 +65,7 @@ String CSSViewportRule::cssText() const
StringBuilder result;
result.appendLiteral("@viewport { ");
- String decls = m_viewportRule->properties()->asText();
+ String decls = m_viewportRule->properties().asText();
result.append(decls);
if (!decls.isEmpty())
result.append(' ');
@@ -81,4 +83,11 @@ void CSSViewportRule::reattach(StyleRuleBase* rule)
m_propertiesCSSOMWrapper->reattach(m_viewportRule->mutableProperties());
}
+void CSSViewportRule::trace(Visitor* visitor)
+{
+ visitor->trace(m_viewportRule);
+ visitor->trace(m_propertiesCSSOMWrapper);
+ CSSRule::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.h b/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.h
index 2ef8c81511f..20a84b5c73a 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/CSSViewportRule.h
@@ -32,6 +32,7 @@
#define CSSViewportRule_h
#include "core/css/CSSRule.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -39,13 +40,13 @@ class CSSStyleDeclaration;
class StyleRuleViewport;
class StyleRuleCSSStyleDeclaration;
-class CSSViewportRule: public CSSRule {
+class CSSViewportRule FINAL: public CSSRule {
public:
- static PassRefPtr<CSSViewportRule> create(StyleRuleViewport* viewportRule, CSSStyleSheet* sheet)
+ static PassRefPtrWillBeRawPtr<CSSViewportRule> create(StyleRuleViewport* viewportRule, CSSStyleSheet* sheet)
{
- return adoptRef(new CSSViewportRule(viewportRule, sheet));
+ return adoptRefWillBeNoop(new CSSViewportRule(viewportRule, sheet));
}
- ~CSSViewportRule();
+ virtual ~CSSViewportRule();
virtual CSSRule::Type type() const OVERRIDE { return VIEWPORT_RULE; }
virtual String cssText() const OVERRIDE;
@@ -53,11 +54,13 @@ public:
CSSStyleDeclaration* style() const;
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
CSSViewportRule(StyleRuleViewport*, CSSStyleSheet*);
- RefPtr<StyleRuleViewport> m_viewportRule;
- mutable RefPtr<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
+ RefPtrWillBeMember<StyleRuleViewport> m_viewportRule;
+ mutable RefPtrWillBeMember<StyleRuleCSSStyleDeclaration> m_propertiesCSSOMWrapper;
};
DEFINE_CSS_RULE_TYPE_CASTS(CSSViewportRule, VIEWPORT_RULE);
diff --git a/chromium/third_party/WebKit/Source/core/css/Counter.cpp b/chromium/third_party/WebKit/Source/core/css/Counter.cpp
new file mode 100644
index 00000000000..d012b1a6c24
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/Counter.cpp
@@ -0,0 +1,17 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/Counter.h"
+
+namespace WebCore {
+
+void Counter::trace(Visitor* visitor)
+{
+ visitor->trace(m_identifier);
+ visitor->trace(m_listStyle);
+ visitor->trace(m_separator);
+}
+
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/Counter.h b/chromium/third_party/WebKit/Source/core/css/Counter.h
index cb73a3dd36d..68b3a7360fb 100644
--- a/chromium/third_party/WebKit/Source/core/css/Counter.h
+++ b/chromium/third_party/WebKit/Source/core/css/Counter.h
@@ -26,11 +26,11 @@
namespace WebCore {
-class Counter : public RefCounted<Counter> {
+class Counter : public RefCountedWillBeGarbageCollected<Counter> {
public:
- static PassRefPtr<Counter> create(PassRefPtr<CSSPrimitiveValue> identifier, PassRefPtr<CSSPrimitiveValue> listStyle, PassRefPtr<CSSPrimitiveValue> separator)
+ static PassRefPtrWillBeRawPtr<Counter> create(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> identifier, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> listStyle, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> separator)
{
- return adoptRef(new Counter(identifier, listStyle, separator));
+ return adoptRefWillBeNoop(new Counter(identifier, listStyle, separator));
}
String identifier() const { return m_identifier ? m_identifier->getStringValue() : String(); }
@@ -39,9 +39,9 @@ public:
CSSValueID listStyleIdent() const { return m_listStyle ? m_listStyle->getValueID() : CSSValueInvalid; }
- void setIdentifier(PassRefPtr<CSSPrimitiveValue> identifier) { m_identifier = identifier; }
- void setListStyle(PassRefPtr<CSSPrimitiveValue> listStyle) { m_listStyle = listStyle; }
- void setSeparator(PassRefPtr<CSSPrimitiveValue> separator) { m_separator = separator; }
+ void setIdentifier(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> identifier) { m_identifier = identifier; }
+ void setListStyle(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> listStyle) { m_listStyle = listStyle; }
+ void setSeparator(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> separator) { m_separator = separator; }
bool equals(const Counter& other) const
{
@@ -50,24 +50,26 @@ public:
&& separator() == other.separator();
}
- PassRefPtr<Counter> cloneForCSSOM() const
+ PassRefPtrWillBeRawPtr<Counter> cloneForCSSOM() const
{
- return create(m_identifier ? m_identifier->cloneForCSSOM() : 0
- , m_listStyle ? m_listStyle->cloneForCSSOM() : 0
- , m_separator ? m_separator->cloneForCSSOM() : 0);
+ return create(m_identifier ? m_identifier->cloneForCSSOM() : nullptr
+ , m_listStyle ? m_listStyle->cloneForCSSOM() : nullptr
+ , m_separator ? m_separator->cloneForCSSOM() : nullptr);
}
+ void trace(Visitor*);
+
private:
- Counter(PassRefPtr<CSSPrimitiveValue> identifier, PassRefPtr<CSSPrimitiveValue> listStyle, PassRefPtr<CSSPrimitiveValue> separator)
+ Counter(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> identifier, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> listStyle, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> separator)
: m_identifier(identifier)
, m_listStyle(listStyle)
, m_separator(separator)
{
}
- RefPtr<CSSPrimitiveValue> m_identifier; // string
- RefPtr<CSSPrimitiveValue> m_listStyle; // ident
- RefPtr<CSSPrimitiveValue> m_separator; // string
+ RefPtrWillBeMember<CSSPrimitiveValue> m_identifier; // string
+ RefPtrWillBeMember<CSSPrimitiveValue> m_listStyle; // ident
+ RefPtrWillBeMember<CSSPrimitiveValue> m_separator; // string
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/Counter.idl b/chromium/third_party/WebKit/Source/core/css/Counter.idl
index 7006aa5001d..886436eea9d 100644
--- a/chromium/third_party/WebKit/Source/core/css/Counter.idl
+++ b/chromium/third_party/WebKit/Source/core/css/Counter.idl
@@ -19,6 +19,7 @@
// Introduced in DOM Level 2:
[
+ WillBeGarbageCollected
] interface Counter {
readonly attribute DOMString identifier;
readonly attribute DOMString listStyle;
diff --git a/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.cpp b/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.cpp
index 248ddcc4648..d0edccaa075 100644
--- a/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.cpp
@@ -30,16 +30,16 @@
#include "config.h"
#include "core/css/DOMWindowCSS.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/RuntimeCSSEnabled.h"
#include "core/css/StylePropertySet.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
-PassRefPtr<DOMWindowCSS> DOMWindowCSS::create()
+PassRefPtrWillBeRawPtr<DOMWindowCSS> DOMWindowCSS::create()
{
- return adoptRef(new DOMWindowCSS());
+ return adoptRefWillBeNoop(new DOMWindowCSS());
}
static String valueWithoutImportant(const String& value)
@@ -65,7 +65,7 @@ bool DOMWindowCSS::supports(const String& property, const String& value) const
if (!RuntimeCSSEnabled::isCSSPropertyEnabled(propertyID))
return false;
- // CSSParser::parseValue() won't work correctly if !important is present,
+ // BisonCSSParser::parseValue() won't work correctly if !important is present,
// so just get rid of it. It doesn't matter to supports() if it's actually
// there or not, provided how it's specified in the value is correct.
String normalizedValue = value.stripWhiteSpace().simplifyWhiteSpace();
@@ -74,14 +74,14 @@ bool DOMWindowCSS::supports(const String& property, const String& value) const
if (normalizedValue.isEmpty())
return false;
- RefPtr<MutableStylePropertySet> dummyStyle = MutableStylePropertySet::create();
- return CSSParser::parseValue(dummyStyle.get(), propertyID, normalizedValue, false, HTMLStandardMode, 0);
+ RefPtrWillBeRawPtr<MutableStylePropertySet> dummyStyle = MutableStylePropertySet::create();
+ return BisonCSSParser::parseValue(dummyStyle.get(), propertyID, normalizedValue, false, HTMLStandardMode, 0);
}
bool DOMWindowCSS::supports(const String& conditionText) const
{
- CSSParserContext context(HTMLStandardMode);
- CSSParser parser(context);
+ CSSParserContext context(HTMLStandardMode, 0);
+ BisonCSSParser parser(context);
return parser.parseSupportsCondition(conditionText);
}
diff --git a/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.h b/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.h
index e6c6d19b2dc..25a7eb6f9e7 100644
--- a/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.h
+++ b/chromium/third_party/WebKit/Source/core/css/DOMWindowCSS.h
@@ -30,19 +30,22 @@
#ifndef DOMWindowCSS_h
#define DOMWindowCSS_h
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefCounted.h"
namespace WebCore {
-class DOMWindowCSS : public RefCounted<DOMWindowCSS> {
+class DOMWindowCSS : public RefCountedWillBeGarbageCollected<DOMWindowCSS> {
public:
- static PassRefPtr<DOMWindowCSS> create();
+ static PassRefPtrWillBeRawPtr<DOMWindowCSS> create();
bool supports(const String& property, const String& value) const;
bool supports(const String& conditionText) const;
+ void trace(Visitor*) { }
+
private:
DOMWindowCSS()
{
diff --git a/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.cpp b/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.cpp
index 408668f70fc..2df6c3e27bc 100644
--- a/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.cpp
@@ -30,7 +30,7 @@
namespace WebCore {
-PassRefPtr<FontFaceSet> DocumentFontFaceSet::fonts(Document* document)
+PassRefPtrWillBeRawPtr<FontFaceSet> DocumentFontFaceSet::fonts(Document& document)
{
return FontFaceSet::from(document);
}
diff --git a/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.h b/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.h
index 910d878291e..b1ecf426d14 100644
--- a/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.h
+++ b/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.h
@@ -26,6 +26,7 @@
#ifndef DocumentFontFaceSet_h
#define DocumentFontFaceSet_h
+#include "platform/heap/Handle.h"
#include "wtf/PassRefPtr.h"
namespace WebCore {
@@ -35,7 +36,7 @@ class FontFaceSet;
class DocumentFontFaceSet {
public:
- static PassRefPtr<FontFaceSet> fonts(Document*);
+ static PassRefPtrWillBeRawPtr<FontFaceSet> fonts(Document&);
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.idl b/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.idl
index 820fdc899e9..6ed56abb6fb 100644
--- a/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.idl
+++ b/chromium/third_party/WebKit/Source/core/css/DocumentFontFaceSet.idl
@@ -28,6 +28,8 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-partial interface Document {
- [RuntimeEnabled=FontLoadEvents] readonly attribute FontFaceSet fonts;
+[
+ RuntimeEnabled=FontLoadEvents,
+] partial interface Document {
+ [MeasureAs=DocumentFonts] readonly attribute FontFaceSet fonts;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/DragUpdateTest.cpp b/chromium/third_party/WebKit/Source/core/css/DragUpdateTest.cpp
new file mode 100644
index 00000000000..c801b6b11bc
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/DragUpdateTest.cpp
@@ -0,0 +1,69 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/dom/Element.h"
+#include "core/frame/FrameView.h"
+#include "core/html/HTMLDocument.h"
+#include "core/html/HTMLElement.h"
+#include "core/testing/DummyPageHolder.h"
+#include <gtest/gtest.h>
+
+using namespace WebCore;
+
+namespace {
+
+TEST(DragUpdateTest, AffectedByDragUpdate)
+{
+ // Check that when dragging the div in the document below, you only get a
+ // single element style recalc.
+
+ OwnPtr<DummyPageHolder> dummyPageHolder = DummyPageHolder::create(IntSize(800, 600));
+ HTMLDocument* document = toHTMLDocument(&dummyPageHolder->document());
+ document->documentElement()->setInnerHTML("<style>div {width:100px;height:100px} div:-webkit-drag { background-color: green }</style>"
+ "<div>"
+ "<span></span>"
+ "<span></span>"
+ "<span></span>"
+ "<span></span>"
+ "</div>", ASSERT_NO_EXCEPTION);
+
+ document->view()->updateLayoutAndStyleIfNeededRecursive();
+ unsigned startCount = document->styleEngine()->resolverAccessCount();
+
+ document->documentElement()->renderer()->updateDragState(true);
+ document->view()->updateLayoutAndStyleIfNeededRecursive();
+
+ unsigned accessCount = document->styleEngine()->resolverAccessCount() - startCount;
+
+ ASSERT_EQ(1U, accessCount);
+}
+
+TEST(DragUpdateTest, ChildrenOrSiblingsAffectedByDragUpdate)
+{
+ // Check that when dragging the div in the document below, you get a
+ // full subtree style recalc.
+
+ OwnPtr<DummyPageHolder> dummyPageHolder = DummyPageHolder::create(IntSize(800, 600));
+ HTMLDocument* document = toHTMLDocument(&dummyPageHolder->document());
+ document->documentElement()->setInnerHTML("<style>div {width:100px;height:100px} div:-webkit-drag span { background-color: green }</style>"
+ "<div>"
+ "<span></span>"
+ "<span></span>"
+ "<span></span>"
+ "<span></span>"
+ "</div>", ASSERT_NO_EXCEPTION);
+
+ document->updateLayout();
+ unsigned startCount = document->styleEngine()->resolverAccessCount();
+
+ document->documentElement()->renderer()->updateDragState(true);
+ document->updateLayout();
+
+ unsigned accessCount = document->styleEngine()->resolverAccessCount() - startCount;
+
+ ASSERT_EQ(5U, accessCount);
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.cpp b/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.cpp
index 4fdd44c8eb4..79ef923b697 100644
--- a/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.cpp
@@ -29,31 +29,32 @@
#include "config.h"
#include "core/css/ElementRuleCollector.h"
+#include "core/css/CSSImportRule.h"
+#include "core/css/CSSKeyframesRule.h"
+#include "core/css/CSSMediaRule.h"
#include "core/css/CSSRuleList.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSStyleRule.h"
#include "core/css/CSSStyleSheet.h"
-#include "core/css/SelectorCheckerFastPath.h"
+#include "core/css/CSSSupportsRule.h"
#include "core/css/SiblingTraversalStrategies.h"
#include "core/css/StylePropertySet.h"
#include "core/css/resolver/StyleResolver.h"
#include "core/dom/shadow/ShadowRoot.h"
-#include "core/rendering/RenderRegion.h"
+#include "core/rendering/style/StyleInheritedData.h"
namespace WebCore {
ElementRuleCollector::ElementRuleCollector(const ElementResolveContext& context,
- const SelectorFilter& filter, RenderStyle* style, ShouldIncludeStyleSheetInCSSOMWrapper includeStyleSheet)
+ const SelectorFilter& filter, RenderStyle* style)
: m_context(context)
, m_selectorFilter(filter)
, m_style(style)
- , m_regionForStyling(0)
, m_pseudoStyleRequest(NOPSEUDO)
, m_mode(SelectorChecker::ResolvingStyle)
, m_canUseFastReject(m_selectorFilter.parentStackIsConsistent(context.parentNode()))
, m_sameOriginOnly(false)
, m_matchingUARules(false)
- , m_includeStyleSheet(includeStyleSheet)
{ }
ElementRuleCollector::~ElementRuleCollector()
@@ -65,23 +66,23 @@ MatchResult& ElementRuleCollector::matchedResult()
return m_result;
}
-PassRefPtr<StyleRuleList> ElementRuleCollector::matchedStyleRuleList()
+PassRefPtrWillBeRawPtr<StyleRuleList> ElementRuleCollector::matchedStyleRuleList()
{
ASSERT(m_mode == SelectorChecker::CollectingStyleRules);
return m_styleRuleList.release();
}
-PassRefPtr<CSSRuleList> ElementRuleCollector::matchedCSSRuleList()
+PassRefPtrWillBeRawPtr<CSSRuleList> ElementRuleCollector::matchedCSSRuleList()
{
ASSERT(m_mode == SelectorChecker::CollectingCSSRules);
return m_cssRuleList.release();
}
-inline void ElementRuleCollector::addMatchedRule(const RuleData* rule, unsigned specificity, CascadeScope cascadeScope, CascadeOrder cascadeOrder, unsigned styleSheetIndex)
+inline void ElementRuleCollector::addMatchedRule(const RuleData* rule, unsigned specificity, CascadeScope cascadeScope, CascadeOrder cascadeOrder, unsigned styleSheetIndex, const CSSStyleSheet* parentStyleSheet)
{
if (!m_matchedRules)
- m_matchedRules = adoptPtr(new Vector<MatchedRule, 32>);
- m_matchedRules->append(MatchedRule(rule, specificity, cascadeScope, cascadeOrder, styleSheetIndex));
+ m_matchedRules = adoptPtrWillBeNoop(new WillBeHeapVector<MatchedRule, 32>);
+ m_matchedRules->append(MatchedRule(rule, specificity, cascadeScope, cascadeOrder, styleSheetIndex, parentStyleSheet));
}
void ElementRuleCollector::clearMatchedRules()
@@ -129,10 +130,7 @@ static bool rulesApplicableInCurrentTreeScope(const Element* element, const Cont
if (!scopingNode || treeScope == scopingNode->treeScope())
return true;
// d) the rules comes from a scoped style sheet within an active shadow root whose host is the given element
- if (element->isInShadowTree() && (behaviorAtBoundary & SelectorChecker::ScopeIsShadowHost) && scopingNode == element->containingShadowRoot()->host())
- return true;
- // e) the rules can cross boundaries
- if ((behaviorAtBoundary & SelectorChecker::BoundaryBehaviorMask) == SelectorChecker::CrossesBoundary)
+ if (SelectorChecker::isHostInItsShadowTree(*element, behaviorAtBoundary, scopingNode))
return true;
return false;
}
@@ -146,7 +144,7 @@ void ElementRuleCollector::collectMatchingRules(const MatchRequest& matchRequest
const AtomicString& pseudoId = element.shadowPseudoId();
if (!pseudoId.isEmpty()) {
ASSERT(element.isStyledElement());
- collectMatchingRulesForList(matchRequest.ruleSet->shadowPseudoElementRules(pseudoId.impl()), behaviorAtBoundary, ignoreCascadeScope, cascadeOrder, matchRequest, ruleRange);
+ collectMatchingRulesForList(matchRequest.ruleSet->shadowPseudoElementRules(pseudoId), behaviorAtBoundary, ignoreCascadeScope, cascadeOrder, matchRequest, ruleRange);
}
if (element.isVTTElement())
@@ -164,65 +162,68 @@ void ElementRuleCollector::collectMatchingRules(const MatchRequest& matchRequest
// We need to collect the rules for id, class, tag, and everything else into a buffer and
// then sort the buffer.
if (element.hasID())
- collectMatchingRulesForList(matchRequest.ruleSet->idRules(element.idForStyleResolution().impl()), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
+ collectMatchingRulesForList(matchRequest.ruleSet->idRules(element.idForStyleResolution()), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
if (element.isStyledElement() && element.hasClass()) {
for (size_t i = 0; i < element.classNames().size(); ++i)
- collectMatchingRulesForList(matchRequest.ruleSet->classRules(element.classNames()[i].impl()), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
+ collectMatchingRulesForList(matchRequest.ruleSet->classRules(element.classNames()[i]), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
}
if (element.isLink())
collectMatchingRulesForList(matchRequest.ruleSet->linkPseudoClassRules(), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
if (SelectorChecker::matchesFocusPseudoClass(element))
collectMatchingRulesForList(matchRequest.ruleSet->focusPseudoClassRules(), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
- collectMatchingRulesForList(matchRequest.ruleSet->tagRules(element.localName().impl()), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
+ collectMatchingRulesForList(matchRequest.ruleSet->tagRules(element.localName()), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
collectMatchingRulesForList(matchRequest.ruleSet->universalRules(), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
}
-void ElementRuleCollector::collectMatchingRulesForRegion(const MatchRequest& matchRequest, RuleRange& ruleRange, SelectorChecker::BehaviorAtBoundary behaviorAtBoundary, CascadeScope cascadeScope, CascadeOrder cascadeOrder)
+CSSRuleList* ElementRuleCollector::nestedRuleList(CSSRule* rule)
{
- if (!m_regionForStyling)
- return;
-
- unsigned size = matchRequest.ruleSet->m_regionSelectorsAndRuleSets.size();
- for (unsigned i = 0; i < size; ++i) {
- const CSSSelector* regionSelector = matchRequest.ruleSet->m_regionSelectorsAndRuleSets.at(i).selector;
- if (checkRegionSelector(regionSelector, toElement(m_regionForStyling->nodeForRegion()))) {
- RuleSet* regionRules = matchRequest.ruleSet->m_regionSelectorsAndRuleSets.at(i).ruleSet.get();
- ASSERT(regionRules);
- collectMatchingRules(MatchRequest(regionRules, matchRequest.includeEmptyRules, matchRequest.scope), ruleRange, behaviorAtBoundary, cascadeScope, cascadeOrder);
- }
+ switch (rule->type()) {
+ case CSSRule::MEDIA_RULE:
+ return toCSSMediaRule(rule)->cssRules();
+ case CSSRule::KEYFRAMES_RULE:
+ return toCSSKeyframesRule(rule)->cssRules();
+ case CSSRule::SUPPORTS_RULE:
+ return toCSSSupportsRule(rule)->cssRules();
+ default:
+ return 0;
}
}
-
-static CSSStyleSheet* findStyleSheet(StyleEngine* styleEngine, StyleRule* rule)
+template<class CSSRuleCollection>
+CSSRule* ElementRuleCollector::findStyleRule(CSSRuleCollection* cssRules, StyleRule* styleRule)
{
- // FIXME: StyleEngine has a bunch of different accessors for StyleSheet lists, is this the only one we need to care about?
- const Vector<RefPtr<CSSStyleSheet> >& stylesheets = styleEngine->activeAuthorStyleSheets();
- for (size_t i = 0; i < stylesheets.size(); ++i) {
- CSSStyleSheet* sheet = stylesheets[i].get();
- for (unsigned j = 0; j < sheet->length(); ++j) {
- CSSRule* cssRule = sheet->item(j);
- if (cssRule->type() != CSSRule::STYLE_RULE)
- continue;
+ if (!cssRules)
+ return 0;
+ CSSRule* result = 0;
+ for (unsigned i = 0; i < cssRules->length() && !result; ++i) {
+ CSSRule* cssRule = cssRules->item(i);
+ CSSRule::Type cssRuleType = cssRule->type();
+ if (cssRuleType == CSSRule::STYLE_RULE) {
CSSStyleRule* cssStyleRule = toCSSStyleRule(cssRule);
- if (cssStyleRule->styleRule() == rule)
- return sheet;
+ if (cssStyleRule->styleRule() == styleRule)
+ result = cssRule;
+ } else if (cssRuleType == CSSRule::IMPORT_RULE) {
+ CSSImportRule* cssImportRule = toCSSImportRule(cssRule);
+ result = findStyleRule(cssImportRule->styleSheet(), styleRule);
+ } else {
+ result = findStyleRule(nestedRuleList(cssRule), styleRule);
}
}
- return 0;
+ return result;
}
-void ElementRuleCollector::appendCSSOMWrapperForRule(StyleRule* rule)
+void ElementRuleCollector::appendCSSOMWrapperForRule(CSSStyleSheet* parentStyleSheet, StyleRule* rule)
{
- // FIXME: There should be no codepath that creates a CSSOMWrapper without a parent stylesheet or rule because
- // then that codepath can lead to the CSSStyleSheet contents not getting correctly copied when the rule is modified
- // through the wrapper (e.g. rule.selectorText="div"). Right now, the inspector uses the pointers for identity though,
- // so calling CSSStyleSheet->willMutateRules breaks the inspector.
- CSSStyleSheet* sheet = m_includeStyleSheet == IncludeStyleSheetInCSSOMWrapper ? findStyleSheet(m_context.element()->document().styleEngine(), rule) : 0;
- RefPtr<CSSRule> cssRule = rule->createCSSOMWrapper(sheet);
- if (sheet)
- sheet->registerExtraChildRuleCSSOMWrapper(cssRule);
+ // |parentStyleSheet| is 0 if and only if the |rule| is coming from User Agent. In this case,
+ // it is safe to create CSSOM wrappers without parentStyleSheets as they will be used only
+ // by inspector which will not try to edit them.
+ RefPtrWillBeRawPtr<CSSRule> cssRule = nullptr;
+ if (parentStyleSheet)
+ cssRule = findStyleRule(parentStyleSheet, rule);
+ else
+ cssRule = rule->createCSSOMWrapper();
+ ASSERT(!parentStyleSheet || cssRule);
ensureRuleList()->rules().append(cssRule);
}
@@ -233,7 +234,7 @@ void ElementRuleCollector::sortAndTransferMatchedRules()
sortMatchedRules();
- Vector<MatchedRule, 32>& matchedRules = *m_matchedRules;
+ WillBeHeapVector<MatchedRule, 32>& matchedRules = *m_matchedRules;
if (m_mode == SelectorChecker::CollectingStyleRules) {
for (unsigned i = 0; i < matchedRules.size(); ++i)
ensureStyleRuleList()->m_list.append(matchedRules[i].ruleData()->rule());
@@ -242,7 +243,7 @@ void ElementRuleCollector::sortAndTransferMatchedRules()
if (m_mode == SelectorChecker::CollectingCSSRules) {
for (unsigned i = 0; i < matchedRules.size(); ++i)
- appendCSSOMWrapperForRule(matchedRules[i].ruleData()->rule());
+ appendCSSOMWrapperForRule(const_cast<CSSStyleSheet*>(matchedRules[i].parentStyleSheet()), matchedRules[i].ruleData()->rule());
return;
}
@@ -252,35 +253,12 @@ void ElementRuleCollector::sortAndTransferMatchedRules()
const RuleData* ruleData = matchedRules[i].ruleData();
if (m_style && ruleData->containsUncommonAttributeSelector())
m_style->setUnique();
- m_result.addMatchedProperties(ruleData->rule()->properties(), ruleData->rule(), ruleData->linkMatchType(), ruleData->propertyWhitelistType(m_matchingUARules));
+ m_result.addMatchedProperties(&ruleData->rule()->properties(), ruleData->rule(), ruleData->linkMatchType(), ruleData->propertyWhitelistType(m_matchingUARules));
}
}
inline bool ElementRuleCollector::ruleMatches(const RuleData& ruleData, const ContainerNode* scope, SelectorChecker::BehaviorAtBoundary behaviorAtBoundary, SelectorChecker::MatchResult* result)
{
- // Scoped rules can't match because the fast path uses a pool of tag/class/ids, collected from
- // elements in that tree and those will never match the host, since it's in a different pool.
- if (ruleData.hasFastCheckableSelector() && !scope) {
- // We know this selector does not include any pseudo elements.
- if (m_pseudoStyleRequest.pseudoId != NOPSEUDO)
- return false;
- // We know a sufficiently simple single part selector matches simply because we found it from the rule hash.
- // This is limited to HTML only so we don't need to check the namespace.
- ASSERT(m_context.element());
- if (ruleData.hasRightmostSelectorMatchingHTMLBasedOnRuleHash() && m_context.element()->isHTMLElement()) {
- if (!ruleData.hasMultipartSelector())
- return true;
- }
- if (ruleData.selector()->m_match == CSSSelector::Tag && !SelectorChecker::tagMatches(*m_context.element(), ruleData.selector()->tagQName()))
- return false;
- SelectorCheckerFastPath selectorCheckerFastPath(ruleData.selector(), *m_context.element());
- if (!selectorCheckerFastPath.matchesRightmostAttributeSelector())
- return false;
-
- return selectorCheckerFastPath.matches();
- }
-
- // Slow path.
SelectorChecker selectorChecker(m_context.element()->document(), m_mode);
SelectorChecker::SelectorCheckingContext context(ruleData.selector(), m_context.element(), SelectorChecker::VisitedMatchEnabled);
context.elementStyle = m_style.get();
@@ -306,8 +284,8 @@ void ElementRuleCollector::collectRuleIfMatches(const RuleData& ruleData, Select
SelectorChecker::MatchResult result;
if (ruleMatches(ruleData, matchRequest.scope, behaviorAtBoundary, &result)) {
// If the rule has no properties to apply, then ignore it in the non-debug mode.
- const StylePropertySet* properties = rule->properties();
- if (!properties || (properties->isEmpty() && !matchRequest.includeEmptyRules))
+ const StylePropertySet& properties = rule->properties();
+ if (properties.isEmpty() && !matchRequest.includeEmptyRules)
return;
// FIXME: Exposing the non-standard getMatchedCSSRules API to web is the only reason this is needed.
if (m_sameOriginOnly && !ruleData.hasDocumentSecurityOrigin())
@@ -329,30 +307,12 @@ void ElementRuleCollector::collectRuleIfMatches(const RuleData& ruleData, Select
ruleRange.firstRuleIndex = ruleRange.lastRuleIndex;
// Add this rule to our list of matched rules.
- addMatchedRule(&ruleData, result.specificity, cascadeScope, cascadeOrder, matchRequest.styleSheetIndex);
+ addMatchedRule(&ruleData, result.specificity, cascadeScope, cascadeOrder, matchRequest.styleSheetIndex, matchRequest.styleSheet);
return;
}
}
}
-void ElementRuleCollector::collectMatchingRulesForList(const RuleData* rules, SelectorChecker::BehaviorAtBoundary behaviorAtBoundary, CascadeScope cascadeScope, CascadeOrder cascadeOrder, const MatchRequest& matchRequest, RuleRange& ruleRange)
-{
- if (!rules)
- return;
- while (!rules->isLastInArray())
- collectRuleIfMatches(*rules++, behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
- collectRuleIfMatches(*rules, behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
-}
-
-void ElementRuleCollector::collectMatchingRulesForList(const Vector<RuleData>* rules, SelectorChecker::BehaviorAtBoundary behaviorAtBoundary, CascadeScope cascadeScope, CascadeOrder cascadeOrder, const MatchRequest& matchRequest, RuleRange& ruleRange)
-{
- if (!rules)
- return;
- unsigned size = rules->size();
- for (unsigned i = 0; i < size; ++i)
- collectRuleIfMatches(rules->at(i), behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
-}
-
static inline bool compareRules(const MatchedRule& matchedRule1, const MatchedRule& matchedRule2)
{
if (matchedRule1.cascadeScope() != matchedRule2.cascadeScope())
@@ -363,9 +323,6 @@ static inline bool compareRules(const MatchedRule& matchedRule1, const MatchedRu
if (specificity1 != specificity2)
return specificity1 < specificity2;
- if (matchedRule1.styleSheetIndex() != matchedRule2.styleSheetIndex())
- return matchedRule1.styleSheetIndex() < matchedRule2.styleSheetIndex();
-
return matchedRule1.position() < matchedRule2.position();
}
diff --git a/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.h b/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.h
index cf47567909a..2423b1f23b3 100644
--- a/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.h
+++ b/chromium/third_party/WebKit/Source/core/css/ElementRuleCollector.h
@@ -27,14 +27,13 @@
#include "core/css/resolver/ElementResolveContext.h"
#include "core/css/resolver/MatchRequest.h"
#include "core/css/resolver/MatchResult.h"
-#include "core/css/resolver/StyleResolverIncludes.h"
#include "wtf/RefPtr.h"
#include "wtf/Vector.h"
namespace WebCore {
+class CSSStyleSheet;
class CSSRuleList;
-class RenderRegion;
class RuleData;
class RuleSet;
class ScopedStyleResolver;
@@ -48,37 +47,61 @@ const CascadeScope ignoreCascadeScope = 0;
const CascadeOrder ignoreCascadeOrder = 0;
class MatchedRule {
- WTF_MAKE_FAST_ALLOCATED;
+ ALLOW_ONLY_INLINE_ALLOCATION();
public:
- explicit MatchedRule(const RuleData* ruleData, unsigned specificity, CascadeScope cascadeScope, CascadeOrder cascadeOrder, unsigned styleSheetIndex)
+ MatchedRule(const RuleData* ruleData, unsigned specificity, CascadeScope cascadeScope, CascadeOrder cascadeOrder, unsigned styleSheetIndex, const CSSStyleSheet* parentStyleSheet)
: m_ruleData(ruleData)
, m_specificity(specificity)
, m_cascadeScope(cascadeScope)
- , m_styleSheetIndex(styleSheetIndex)
+ , m_parentStyleSheet(parentStyleSheet)
{
ASSERT(m_ruleData);
static const unsigned BitsForPositionInRuleData = 18;
- m_position = (cascadeOrder << BitsForPositionInRuleData) + m_ruleData->position();
+ static const unsigned BitsForStyleSheetIndex = 32;
+ m_position = ((uint64_t)cascadeOrder << (BitsForStyleSheetIndex + BitsForPositionInRuleData)) + ((uint64_t)styleSheetIndex << BitsForPositionInRuleData)+ m_ruleData->position();
}
const RuleData* ruleData() const { return m_ruleData; }
uint32_t cascadeScope() const { return m_cascadeScope; }
- uint32_t position() const { return m_position; }
+ uint64_t position() const { return m_position; }
unsigned specificity() const { return ruleData()->specificity() + m_specificity; }
- uint32_t styleSheetIndex() const { return m_styleSheetIndex; }
+ const CSSStyleSheet* parentStyleSheet() const { return m_parentStyleSheet; }
+ void trace(Visitor* visitor)
+ {
+ visitor->trace(m_parentStyleSheet);
+ }
private:
+ // FIXME: Oilpan: RuleData is in the oilpan heap and this pointer
+ // really should be traced. However, RuleData objects are
+ // allocated inside larger TerminatedArray objects and we cannot
+ // trace a raw rule data pointer at this point.
const RuleData* m_ruleData;
unsigned m_specificity;
CascadeScope m_cascadeScope;
- uint32_t m_position;
- uint32_t m_styleSheetIndex;
+ uint64_t m_position;
+ RawPtrWillBeMember<const CSSStyleSheet> m_parentStyleSheet;
};
-class StyleRuleList : public RefCounted<StyleRuleList> {
+} // namespace WebCore
+
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::MatchedRule);
+
+namespace WebCore {
+
+// FIXME: oilpan: when transition types are gone this class can be replaced with HeapVector.
+class StyleRuleList FINAL : public RefCountedWillBeGarbageCollected<StyleRuleList> {
public:
- static PassRefPtr<StyleRuleList> create() { return adoptRef(new StyleRuleList()); }
- Vector<StyleRule*> m_list;
+ static PassRefPtrWillBeRawPtr<StyleRuleList> create() { return adoptRefWillBeNoop(new StyleRuleList()); }
+
+ void trace(Visitor* visitor)
+ {
+#if ENABLE(OILPAN)
+ visitor->trace(m_list);
+#endif
+ }
+
+ WillBeHeapVector<RawPtrWillBeMember<StyleRule> > m_list;
};
// ElementRuleCollector is designed to be used as a stack object.
@@ -86,25 +109,24 @@ public:
// and then let it go out of scope.
// FIXME: Currently it modifies the RenderStyle but should not!
class ElementRuleCollector {
+ STACK_ALLOCATED();
WTF_MAKE_NONCOPYABLE(ElementRuleCollector);
public:
- ElementRuleCollector(const ElementResolveContext&, const SelectorFilter&, RenderStyle* = 0, ShouldIncludeStyleSheetInCSSOMWrapper = IncludeStyleSheetInCSSOMWrapper);
+ ElementRuleCollector(const ElementResolveContext&, const SelectorFilter&, RenderStyle* = 0);
~ElementRuleCollector();
void setMode(SelectorChecker::Mode mode) { m_mode = mode; }
void setPseudoStyleRequest(const PseudoStyleRequest& request) { m_pseudoStyleRequest = request; }
void setSameOriginOnly(bool f) { m_sameOriginOnly = f; }
- void setRegionForStyling(const RenderRegion* regionForStyling) { m_regionForStyling = regionForStyling; }
void setMatchingUARules(bool matchingUARules) { m_matchingUARules = matchingUARules; }
bool hasAnyMatchingRules(RuleSet*);
MatchResult& matchedResult();
- PassRefPtr<StyleRuleList> matchedStyleRuleList();
- PassRefPtr<CSSRuleList> matchedCSSRuleList();
+ PassRefPtrWillBeRawPtr<StyleRuleList> matchedStyleRuleList();
+ PassRefPtrWillBeRawPtr<CSSRuleList> matchedCSSRuleList();
void collectMatchingRules(const MatchRequest&, RuleRange&, SelectorChecker::BehaviorAtBoundary = SelectorChecker::DoesNotCrossBoundary, CascadeScope = ignoreCascadeScope, CascadeOrder = ignoreCascadeOrder);
- void collectMatchingRulesForRegion(const MatchRequest&, RuleRange&, SelectorChecker::BehaviorAtBoundary = SelectorChecker::DoesNotCrossBoundary, CascadeScope = ignoreCascadeScope, CascadeOrder = ignoreCascadeOrder);
void sortAndTransferMatchedRules();
void clearMatchedRules();
void addElementStyleProperties(const StylePropertySet*, bool isCacheable = true);
@@ -115,15 +137,26 @@ public:
private:
void collectRuleIfMatches(const RuleData&, SelectorChecker::BehaviorAtBoundary, CascadeScope, CascadeOrder, const MatchRequest&, RuleRange&);
- void collectMatchingRulesForList(const Vector<RuleData>*, SelectorChecker::BehaviorAtBoundary, CascadeScope, CascadeOrder, const MatchRequest&, RuleRange&);
- void collectMatchingRulesForList(const RuleData*, SelectorChecker::BehaviorAtBoundary, CascadeScope, CascadeOrder, const MatchRequest&, RuleRange&);
+
+ template<typename RuleDataListType>
+ void collectMatchingRulesForList(const RuleDataListType* rules, SelectorChecker::BehaviorAtBoundary behaviorAtBoundary, CascadeScope cascadeScope, CascadeOrder cascadeOrder, const MatchRequest& matchRequest, RuleRange& ruleRange)
+ {
+ if (!rules)
+ return;
+
+ for (typename RuleDataListType::const_iterator it = rules->begin(), end = rules->end(); it != end; ++it)
+ collectRuleIfMatches(*it, behaviorAtBoundary, cascadeScope, cascadeOrder, matchRequest, ruleRange);
+ }
+
bool ruleMatches(const RuleData&, const ContainerNode* scope, SelectorChecker::BehaviorAtBoundary, SelectorChecker::MatchResult*);
- void appendCSSOMWrapperForRule(StyleRule*);
+ CSSRuleList* nestedRuleList(CSSRule*);
+ template<class CSSRuleCollection>
+ CSSRule* findStyleRule(CSSRuleCollection*, StyleRule*);
+ void appendCSSOMWrapperForRule(CSSStyleSheet*, StyleRule*);
void sortMatchedRules();
- void addMatchedRule(const RuleData*, unsigned specificity, CascadeScope, CascadeOrder);
- void addMatchedRule(const RuleData*, unsigned specificity, CascadeScope, CascadeOrder, unsigned styleSheetIndex);
+ void addMatchedRule(const RuleData*, unsigned specificity, CascadeScope, CascadeOrder, unsigned styleSheetIndex, const CSSStyleSheet* parentStyleSheet);
StaticCSSRuleList* ensureRuleList();
StyleRuleList* ensureStyleRuleList();
@@ -133,19 +166,17 @@ private:
const SelectorFilter& m_selectorFilter;
RefPtr<RenderStyle> m_style; // FIXME: This can be mutated during matching!
- const RenderRegion* m_regionForStyling;
PseudoStyleRequest m_pseudoStyleRequest;
SelectorChecker::Mode m_mode;
bool m_canUseFastReject;
bool m_sameOriginOnly;
bool m_matchingUARules;
- bool m_includeStyleSheet;
- OwnPtr<Vector<MatchedRule, 32> > m_matchedRules;
+ OwnPtrWillBeMember<WillBeHeapVector<MatchedRule, 32> > m_matchedRules;
// Output.
- RefPtr<StaticCSSRuleList> m_cssRuleList;
- RefPtr<StyleRuleList> m_styleRuleList;
+ RefPtrWillBeMember<StaticCSSRuleList> m_cssRuleList;
+ RefPtrWillBeMember<StyleRuleList> m_styleRuleList;
MatchResult m_result;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFace.cpp b/chromium/third_party/WebKit/Source/core/css/FontFace.cpp
index 3b35cbca0fb..9590053c590 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontFace.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/FontFace.cpp
@@ -31,134 +31,161 @@
#include "config.h"
#include "core/css/FontFace.h"
-#include "CSSValueKeywords.h"
-#include "FontFamilyNames.h"
#include "bindings/v8/Dictionary.h"
#include "bindings/v8/ExceptionState.h"
-#include "bindings/v8/ScriptPromiseResolver.h"
-#include "bindings/v8/ScriptScope.h"
+#include "bindings/v8/ScriptPromiseResolverWithContext.h"
#include "bindings/v8/ScriptState.h"
+#include "core/CSSValueKeywords.h"
+#include "core/css/BinaryDataFontFaceSource.h"
#include "core/css/CSSFontFace.h"
#include "core/css/CSSFontFaceSrcValue.h"
-#include "core/css/CSSParser.h"
+#include "core/css/CSSFontSelector.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSUnicodeRangeValue.h"
#include "core/css/CSSValueList.h"
+#include "core/css/LocalFontFaceSource.h"
+#include "core/css/RemoteFontFaceSource.h"
#include "core/css/StylePropertySet.h"
#include "core/css/StyleRule.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/dom/DOMError.h"
#include "core/dom/Document.h"
#include "core/dom/ExceptionCode.h"
-#include "core/frame/Frame.h"
+#include "core/dom/StyleEngine.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
#include "core/svg/SVGFontFaceElement.h"
-#include "platform/fonts/FontDescription.h"
-#include "platform/fonts/FontTraitsMask.h"
-#include "platform/fonts/SimpleFontData.h"
+#include "core/svg/SVGFontFaceSource.h"
+#include "core/svg/SVGRemoteFontFaceSource.h"
+#include "platform/FontFamilyNames.h"
+#include "platform/SharedBuffer.h"
namespace WebCore {
class FontFaceReadyPromiseResolver {
public:
- static PassOwnPtr<FontFaceReadyPromiseResolver> create(ScriptPromise promise, ExecutionContext* context)
+ static PassOwnPtr<FontFaceReadyPromiseResolver> create(ScriptState* scriptState)
{
- return adoptPtr(new FontFaceReadyPromiseResolver(promise, context));
+ return adoptPtr(new FontFaceReadyPromiseResolver(scriptState));
}
- void resolve(PassRefPtr<FontFace> fontFace)
+ void resolve(PassRefPtrWillBeRawPtr<FontFace> fontFace)
{
- ScriptScope scope(m_scriptState);
switch (fontFace->loadStatus()) {
case FontFace::Loaded:
m_resolver->resolve(fontFace);
break;
case FontFace::Error:
- m_resolver->reject(DOMError::create(NetworkError));
+ m_resolver->reject(fontFace->error());
break;
default:
ASSERT_NOT_REACHED();
}
}
+ ScriptPromise promise() { return m_resolver->promise(); }
+
private:
- FontFaceReadyPromiseResolver(ScriptPromise promise, ExecutionContext* context)
- : m_scriptState(ScriptState::current())
- , m_resolver(ScriptPromiseResolver::create(promise, context))
- { }
- ScriptState* m_scriptState;
- RefPtr<ScriptPromiseResolver> m_resolver;
+ FontFaceReadyPromiseResolver(ScriptState* scriptState)
+ : m_resolver(ScriptPromiseResolverWithContext::create(scriptState))
+ {
+ }
+
+ RefPtr<ScriptPromiseResolverWithContext> m_resolver;
};
-static PassRefPtr<CSSValue> parseCSSValue(const String& s, CSSPropertyID propertyID)
+static PassRefPtrWillBeRawPtr<CSSValue> parseCSSValue(const Document* document, const String& s, CSSPropertyID propertyID)
{
if (s.isEmpty())
- return 0;
- RefPtr<MutableStylePropertySet> parsedStyle = MutableStylePropertySet::create();
- CSSParser::parseValue(parsedStyle.get(), propertyID, s, true, HTMLStandardMode, 0);
+ return nullptr;
+ RefPtrWillBeRawPtr<MutableStylePropertySet> parsedStyle = MutableStylePropertySet::create();
+ BisonCSSParser::parseValue(parsedStyle.get(), propertyID, s, true, *document);
return parsedStyle->getPropertyCSSValue(propertyID);
}
-PassRefPtr<FontFace> FontFace::create(const AtomicString& family, const String& source, const Dictionary& descriptors, ExceptionState& exceptionState)
+static bool initFontFace(FontFace* fontFace, ExecutionContext* context, const AtomicString& family, const Dictionary& descriptors, ExceptionState& exceptionState)
{
- RefPtr<CSSValue> src = parseCSSValue(source, CSSPropertySrc);
- if (!src || !src->isValueList()) {
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
- return 0;
- }
-
- RefPtr<FontFace> fontFace = adoptRef<FontFace>(new FontFace(src));
- fontFace->setFamily(family, exceptionState);
+ fontFace->setFamily(context, family, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
String value;
if (descriptors.get("style", value)) {
- fontFace->setStyle(value, exceptionState);
+ fontFace->setStyle(context, value, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
}
if (descriptors.get("weight", value)) {
- fontFace->setWeight(value, exceptionState);
+ fontFace->setWeight(context, value, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
}
if (descriptors.get("stretch", value)) {
- fontFace->setStretch(value, exceptionState);
+ fontFace->setStretch(context, value, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
}
if (descriptors.get("unicodeRange", value)) {
- fontFace->setUnicodeRange(value, exceptionState);
+ fontFace->setUnicodeRange(context, value, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
}
if (descriptors.get("variant", value)) {
- fontFace->setVariant(value, exceptionState);
+ fontFace->setVariant(context, value, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
}
if (descriptors.get("featureSettings", value)) {
- fontFace->setFeatureSettings(value, exceptionState);
+ fontFace->setFeatureSettings(context, value, exceptionState);
if (exceptionState.hadException())
- return 0;
+ return false;
+ }
+ return true;
+}
+
+PassRefPtrWillBeRawPtr<FontFace> FontFace::create(ExecutionContext* context, const AtomicString& family, const String& source, const Dictionary& descriptors, ExceptionState& exceptionState)
+{
+ RefPtrWillBeRawPtr<CSSValue> src = parseCSSValue(toDocument(context), source, CSSPropertySrc);
+ if (!src || !src->isValueList()) {
+ exceptionState.throwDOMException(SyntaxError, "The source provided ('" + source + "') could not be parsed as a value list.");
+ return nullptr;
}
- return fontFace;
+ RefPtrWillBeRawPtr<FontFace> fontFace = adoptRefWillBeNoop(new FontFace());
+ if (initFontFace(fontFace.get(), context, family, descriptors, exceptionState))
+ fontFace->initCSSFontFace(toDocument(context), src);
+ return fontFace.release();
}
-PassRefPtr<FontFace> FontFace::create(const StyleRuleFontFace* fontFaceRule)
+PassRefPtrWillBeRawPtr<FontFace> FontFace::create(ExecutionContext* context, const AtomicString& family, PassRefPtr<ArrayBuffer> source, const Dictionary& descriptors, ExceptionState& exceptionState)
{
- const StylePropertySet* properties = fontFaceRule->properties();
+ RefPtrWillBeRawPtr<FontFace> fontFace = adoptRefWillBeNoop(new FontFace());
+ if (initFontFace(fontFace.get(), context, family, descriptors, exceptionState))
+ fontFace->initCSSFontFace(static_cast<const unsigned char*>(source->data()), source->byteLength());
+ return fontFace.release();
+}
+
+PassRefPtrWillBeRawPtr<FontFace> FontFace::create(ExecutionContext* context, const AtomicString& family, PassRefPtr<ArrayBufferView> source, const Dictionary& descriptors, ExceptionState& exceptionState)
+{
+ RefPtrWillBeRawPtr<FontFace> fontFace = adoptRefWillBeNoop(new FontFace());
+ if (initFontFace(fontFace.get(), context, family, descriptors, exceptionState))
+ fontFace->initCSSFontFace(static_cast<const unsigned char*>(source->baseAddress()), source->byteLength());
+ return fontFace.release();
+}
+
+PassRefPtrWillBeRawPtr<FontFace> FontFace::create(Document* document, const StyleRuleFontFace* fontFaceRule)
+{
+ const StylePropertySet& properties = fontFaceRule->properties();
// Obtain the font-family property and the src property. Both must be defined.
- RefPtr<CSSValue> family = properties->getPropertyCSSValue(CSSPropertyFontFamily);
+ RefPtrWillBeRawPtr<CSSValue> family = properties.getPropertyCSSValue(CSSPropertyFontFamily);
if (!family || !family->isValueList())
- return 0;
- RefPtr<CSSValue> src = properties->getPropertyCSSValue(CSSPropertySrc);
+ return nullptr;
+ RefPtrWillBeRawPtr<CSSValue> src = properties.getPropertyCSSValue(CSSPropertySrc);
if (!src || !src->isValueList())
- return 0;
+ return nullptr;
- RefPtr<FontFace> fontFace = adoptRef<FontFace>(new FontFace(src));
+ RefPtrWillBeRawPtr<FontFace> fontFace = adoptRefWillBeNoop(new FontFace());
if (fontFace->setFamilyValue(toCSSValueList(family.get()))
&& fontFace->setPropertyFromStyle(properties, CSSPropertyFontStyle)
@@ -166,15 +193,17 @@ PassRefPtr<FontFace> FontFace::create(const StyleRuleFontFace* fontFaceRule)
&& fontFace->setPropertyFromStyle(properties, CSSPropertyFontStretch)
&& fontFace->setPropertyFromStyle(properties, CSSPropertyUnicodeRange)
&& fontFace->setPropertyFromStyle(properties, CSSPropertyFontVariant)
- && fontFace->setPropertyFromStyle(properties, CSSPropertyWebkitFontFeatureSettings))
- return fontFace;
- return 0;
+ && fontFace->setPropertyFromStyle(properties, CSSPropertyWebkitFontFeatureSettings)
+ && !fontFace->family().isEmpty()
+ && fontFace->traits().mask()) {
+ fontFace->initCSSFontFace(document, src);
+ return fontFace.release();
+ }
+ return nullptr;
}
-FontFace::FontFace(PassRefPtr<CSSValue> src)
- : m_src(src)
- , m_status(Unloaded)
- , m_cssFontFace(0)
+FontFace::FontFace()
+ : m_status(Unloaded)
{
}
@@ -212,49 +241,49 @@ String FontFace::featureSettings() const
return m_featureSettings ? m_featureSettings->cssText() : "normal";
}
-void FontFace::setStyle(const String& s, ExceptionState& exceptionState)
+void FontFace::setStyle(ExecutionContext* context, const String& s, ExceptionState& exceptionState)
{
- setPropertyFromString(s, CSSPropertyFontStyle, exceptionState);
+ setPropertyFromString(toDocument(context), s, CSSPropertyFontStyle, exceptionState);
}
-void FontFace::setWeight(const String& s, ExceptionState& exceptionState)
+void FontFace::setWeight(ExecutionContext* context, const String& s, ExceptionState& exceptionState)
{
- setPropertyFromString(s, CSSPropertyFontWeight, exceptionState);
+ setPropertyFromString(toDocument(context), s, CSSPropertyFontWeight, exceptionState);
}
-void FontFace::setStretch(const String& s, ExceptionState& exceptionState)
+void FontFace::setStretch(ExecutionContext* context, const String& s, ExceptionState& exceptionState)
{
- setPropertyFromString(s, CSSPropertyFontStretch, exceptionState);
+ setPropertyFromString(toDocument(context), s, CSSPropertyFontStretch, exceptionState);
}
-void FontFace::setUnicodeRange(const String& s, ExceptionState& exceptionState)
+void FontFace::setUnicodeRange(ExecutionContext* context, const String& s, ExceptionState& exceptionState)
{
- setPropertyFromString(s, CSSPropertyUnicodeRange, exceptionState);
+ setPropertyFromString(toDocument(context), s, CSSPropertyUnicodeRange, exceptionState);
}
-void FontFace::setVariant(const String& s, ExceptionState& exceptionState)
+void FontFace::setVariant(ExecutionContext* context, const String& s, ExceptionState& exceptionState)
{
- setPropertyFromString(s, CSSPropertyFontVariant, exceptionState);
+ setPropertyFromString(toDocument(context), s, CSSPropertyFontVariant, exceptionState);
}
-void FontFace::setFeatureSettings(const String& s, ExceptionState& exceptionState)
+void FontFace::setFeatureSettings(ExecutionContext* context, const String& s, ExceptionState& exceptionState)
{
- setPropertyFromString(s, CSSPropertyWebkitFontFeatureSettings, exceptionState);
+ setPropertyFromString(toDocument(context), s, CSSPropertyWebkitFontFeatureSettings, exceptionState);
}
-void FontFace::setPropertyFromString(const String& s, CSSPropertyID propertyID, ExceptionState& exceptionState)
+void FontFace::setPropertyFromString(const Document* document, const String& s, CSSPropertyID propertyID, ExceptionState& exceptionState)
{
- RefPtr<CSSValue> value = parseCSSValue(s, propertyID);
+ RefPtrWillBeRawPtr<CSSValue> value = parseCSSValue(document, s, propertyID);
if (!value || !setPropertyValue(value, propertyID))
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
+ exceptionState.throwDOMException(SyntaxError, "Failed to set '" + s + "' as a property value.");
}
-bool FontFace::setPropertyFromStyle(const StylePropertySet* properties, CSSPropertyID propertyID)
+bool FontFace::setPropertyFromStyle(const StylePropertySet& properties, CSSPropertyID propertyID)
{
- return setPropertyValue(properties->getPropertyCSSValue(propertyID), propertyID);
+ return setPropertyValue(properties.getPropertyCSSValue(propertyID), propertyID);
}
-bool FontFace::setPropertyValue(PassRefPtr<CSSValue> value, CSSPropertyID propertyID)
+bool FontFace::setPropertyValue(PassRefPtrWillBeRawPtr<CSSValue> value, CSSPropertyID propertyID)
{
switch (propertyID) {
case CSSPropertyFontStyle:
@@ -344,38 +373,62 @@ String FontFace::status() const
void FontFace::setLoadStatus(LoadStatus status)
{
m_status = status;
- if (m_status == Loaded || m_status == Error)
+ if (m_status == Error)
+ m_error = DOMError::create(NetworkError);
+ if (m_status == Loaded || m_status == Error) {
resolveReadyPromises();
-}
-
-void FontFace::load()
-{
- // FIXME: This does not load FontFace created by JavaScript, since m_cssFontFace is null.
- if (m_status != Unloaded || !m_cssFontFace)
- return;
-
- FontDescription fontDescription;
- FontFamily fontFamily;
- fontFamily.setFamily(m_family);
- fontDescription.setFamily(fontFamily);
- fontDescription.setTraitsMask(static_cast<FontTraitsMask>(traitsMask()));
- RefPtr<SimpleFontData> fontData = m_cssFontFace->getFontData(fontDescription);
- if (fontData && fontData->customFontData())
- fontData->customFontData()->beginLoadIfNeeded();
+ WillBeHeapVector<RefPtrWillBeMember<LoadFontCallback> > callbacks;
+ m_callbacks.swap(callbacks);
+ for (size_t i = 0; i < callbacks.size(); ++i) {
+ if (m_status == Loaded)
+ callbacks[i]->notifyLoaded(this);
+ else
+ callbacks[i]->notifyError(this);
+ }
+ }
}
-ScriptPromise FontFace::ready(ExecutionContext* context)
+ScriptPromise FontFace::fontStatusPromise(ScriptState* scriptState)
{
- ScriptPromise promise = ScriptPromise::createPending(context);
- OwnPtr<FontFaceReadyPromiseResolver> resolver = FontFaceReadyPromiseResolver::create(promise, context);
+ // Since we cannot hold a ScriptPromise as a member of FontFace (that will
+ // cause a circular reference), this creates new Promise every time.
+ OwnPtr<FontFaceReadyPromiseResolver> resolver = FontFaceReadyPromiseResolver::create(scriptState);
+ ScriptPromise promise = resolver->promise();
if (m_status == Loaded || m_status == Error)
resolver->resolve(this);
else
m_readyResolvers.append(resolver.release());
+
return promise;
}
+ScriptPromise FontFace::load(ScriptState* scriptState)
+{
+ loadInternal(scriptState->executionContext());
+ return fontStatusPromise(scriptState);
+}
+
+void FontFace::loadWithCallback(PassRefPtrWillBeRawPtr<LoadFontCallback> callback, ExecutionContext* context)
+{
+ loadInternal(context);
+ if (m_status == Loaded)
+ callback->notifyLoaded(this);
+ else if (m_status == Error)
+ callback->notifyError(this);
+ else
+ m_callbacks.append(callback);
+}
+
+void FontFace::loadInternal(ExecutionContext* context)
+{
+ if (m_status != Unloaded)
+ return;
+
+ m_cssFontFace->load();
+ toDocument(context)->styleEngine()->fontSelector()->fontLoader()->loadPendingFonts();
+}
+
void FontFace::resolveReadyPromises()
{
for (size_t i = 0; i < m_readyResolvers.size(); i++)
@@ -383,29 +436,27 @@ void FontFace::resolveReadyPromises()
m_readyResolvers.clear();
}
-unsigned FontFace::traitsMask() const
+FontTraits FontFace::traits() const
{
- unsigned traitsMask = 0;
-
+ FontStyle style = FontStyleNormal;
if (m_style) {
if (!m_style->isPrimitiveValue())
return 0;
switch (toCSSPrimitiveValue(m_style.get())->getValueID()) {
case CSSValueNormal:
- traitsMask |= FontStyleNormalMask;
+ style = FontStyleNormal;
break;
case CSSValueItalic:
case CSSValueOblique:
- traitsMask |= FontStyleItalicMask;
+ style = FontStyleItalic;
break;
default:
break;
}
- } else {
- traitsMask |= FontStyleNormalMask;
}
+ FontWeight weight = FontWeight400;
if (m_weight) {
if (!m_weight->isPrimitiveValue())
return 0;
@@ -413,44 +464,45 @@ unsigned FontFace::traitsMask() const
switch (toCSSPrimitiveValue(m_weight.get())->getValueID()) {
case CSSValueBold:
case CSSValue700:
- traitsMask |= FontWeight700Mask;
+ weight = FontWeight700;
break;
case CSSValueNormal:
case CSSValue400:
- traitsMask |= FontWeight400Mask;
+ weight = FontWeight400;
break;
case CSSValue900:
- traitsMask |= FontWeight900Mask;
+ weight = FontWeight900;
break;
case CSSValue800:
- traitsMask |= FontWeight800Mask;
+ weight = FontWeight800;
break;
case CSSValue600:
- traitsMask |= FontWeight600Mask;
+ weight = FontWeight600;
break;
case CSSValue500:
- traitsMask |= FontWeight500Mask;
+ weight = FontWeight500;
break;
case CSSValue300:
- traitsMask |= FontWeight300Mask;
+ weight = FontWeight300;
break;
case CSSValue200:
- traitsMask |= FontWeight200Mask;
+ weight = FontWeight200;
break;
+ case CSSValueLighter:
case CSSValue100:
- traitsMask |= FontWeight100Mask;
+ weight = FontWeight100;
break;
default:
+ ASSERT_NOT_REACHED();
break;
}
- } else {
- traitsMask |= FontWeight400Mask;
}
- if (RefPtr<CSSValue> fontVariant = m_variant) {
+ FontVariant variant = FontVariantNormal;
+ if (RefPtrWillBeRawPtr<CSSValue> fontVariant = m_variant) {
// font-variant descriptor can be a value list.
if (fontVariant->isPrimitiveValue()) {
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
list->append(fontVariant);
fontVariant = list;
} else if (!fontVariant->isValueList()) {
@@ -465,31 +517,40 @@ unsigned FontFace::traitsMask() const
for (unsigned i = 0; i < numVariants; ++i) {
switch (toCSSPrimitiveValue(variantList->itemWithoutBoundsCheck(i))->getValueID()) {
case CSSValueNormal:
- traitsMask |= FontVariantNormalMask;
+ variant = FontVariantNormal;
break;
case CSSValueSmallCaps:
- traitsMask |= FontVariantSmallCapsMask;
+ variant = FontVariantSmallCaps;
break;
default:
break;
}
}
- } else {
- traitsMask |= FontVariantNormalMask;
}
- return traitsMask;
+
+ return FontTraits(style, variant, weight, FontStretchNormal);
}
-PassRefPtr<CSSFontFace> FontFace::createCSSFontFace(Document* document)
+static PassOwnPtrWillBeRawPtr<CSSFontFace> createCSSFontFace(FontFace* fontFace, CSSValue* unicodeRange)
{
- if (m_cssFontFace)
- return m_cssFontFace;
+ Vector<CSSFontFace::UnicodeRange> ranges;
+ if (CSSValueList* rangeList = toCSSValueList(unicodeRange)) {
+ unsigned numRanges = rangeList->length();
+ for (unsigned i = 0; i < numRanges; i++) {
+ CSSUnicodeRangeValue* range = toCSSUnicodeRangeValue(rangeList->itemWithoutBoundsCheck(i));
+ ranges.append(CSSFontFace::UnicodeRange(range->from(), range->to()));
+ }
+ }
- RefPtr<CSSFontFace> cssFontFace = CSSFontFace::create(this);
- m_cssFontFace = cssFontFace.get();
+ return adoptPtrWillBeNoop(new CSSFontFace(fontFace, ranges));
+}
+
+void FontFace::initCSSFontFace(Document* document, PassRefPtrWillBeRawPtr<CSSValue> src)
+{
+ m_cssFontFace = createCSSFontFace(this, m_unicodeRange.get());
// Each item in the src property's list is a single CSSFontFaceSource. Put them all into a CSSFontFace.
- CSSValueList* srcList = toCSSValueList(m_src.get());
+ CSSValueList* srcList = toCSSValueList(src.get());
int srcLength = srcList->length();
bool foundSVGFont = false;
@@ -497,7 +558,7 @@ PassRefPtr<CSSFontFace> FontFace::createCSSFontFace(Document* document)
for (int i = 0; i < srcLength; i++) {
// An item in the list either specifies a string (local font name) or a URL (remote font to download).
CSSFontFaceSrcValue* item = toCSSFontFaceSrcValue(srcList->itemWithoutBoundsCheck(i));
- OwnPtr<CSSFontFaceSource> source;
+ OwnPtrWillBeRawPtr<CSSFontFaceSource> source = nullptr;
#if ENABLE(SVG_FONTS)
foundSVGFont = item->isSVGFontFaceSrc() || item->svgFontFaceElement();
@@ -508,33 +569,71 @@ PassRefPtr<CSSFontFace> FontFace::createCSSFontFace(Document* document)
if (allowDownloading && item->isSupportedFormat() && document) {
FontResource* fetched = item->fetch(document);
if (fetched) {
- source = adoptPtr(new CSSFontFaceSource(item->resource(), fetched));
+ FontLoader* fontLoader = document->styleEngine()->fontSelector()->fontLoader();
+
#if ENABLE(SVG_FONTS)
- if (foundSVGFont)
- source->setHasExternalSVGFont(true);
+ if (foundSVGFont) {
+ source = adoptPtrWillBeNoop(new SVGRemoteFontFaceSource(item->resource(), fetched, fontLoader));
+ } else
#endif
+ {
+ source = adoptPtrWillBeNoop(new RemoteFontFaceSource(fetched, fontLoader));
+ }
}
}
} else {
- source = adoptPtr(new CSSFontFaceSource(item->resource()));
- }
-
- if (source) {
#if ENABLE(SVG_FONTS)
- source->setSVGFontFaceElement(item->svgFontFaceElement());
+ if (item->svgFontFaceElement()) {
+ RefPtrWillBeRawPtr<SVGFontFaceElement> fontfaceElement = item->svgFontFaceElement();
+ // SVGFontFaceSource assumes that it is the case where <font-face> element resides in the same document.
+ // We put a RELEASE_ASSERT here as it will cause UAF if the assumption is false.
+ RELEASE_ASSERT(fontfaceElement->inDocument());
+ RELEASE_ASSERT(fontfaceElement->document() == document);
+ source = adoptPtrWillBeNoop(new SVGFontFaceSource(fontfaceElement.get()));
+ } else
#endif
- cssFontFace->addSource(source.release());
+ {
+ source = adoptPtrWillBeNoop(new LocalFontFaceSource(item->resource()));
+ }
}
+
+ if (source)
+ m_cssFontFace->addSource(source.release());
}
+}
- if (CSSValueList* rangeList = toCSSValueList(m_unicodeRange.get())) {
- unsigned numRanges = rangeList->length();
- for (unsigned i = 0; i < numRanges; i++) {
- CSSUnicodeRangeValue* range = toCSSUnicodeRangeValue(rangeList->itemWithoutBoundsCheck(i));
- cssFontFace->ranges().add(range->from(), range->to());
- }
+void FontFace::initCSSFontFace(const unsigned char* data, unsigned size)
+{
+ m_cssFontFace = createCSSFontFace(this, m_unicodeRange.get());
+
+ RefPtr<SharedBuffer> buffer = SharedBuffer::create(data, size);
+ OwnPtrWillBeRawPtr<BinaryDataFontFaceSource> source = adoptPtrWillBeNoop(new BinaryDataFontFaceSource(buffer.get()));
+ if (source->isValid()) {
+ m_status = Loaded;
+ } else {
+ m_status = Error;
+ m_error = DOMError::create(SyntaxError, "Invalid font data in ArrayBuffer.");
}
- return cssFontFace;
+ m_cssFontFace->addSource(source.release());
+}
+
+void FontFace::trace(Visitor* visitor)
+{
+ visitor->trace(m_src);
+ visitor->trace(m_style);
+ visitor->trace(m_weight);
+ visitor->trace(m_stretch);
+ visitor->trace(m_unicodeRange);
+ visitor->trace(m_variant);
+ visitor->trace(m_featureSettings);
+ visitor->trace(m_error);
+ visitor->trace(m_cssFontFace);
+ visitor->trace(m_callbacks);
+}
+
+bool FontFace::hadBlankText() const
+{
+ return m_cssFontFace->hadBlankText();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFace.h b/chromium/third_party/WebKit/Source/core/css/FontFace.h
index 900d3a7c962..c42316efdfa 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontFace.h
+++ b/chromium/third_party/WebKit/Source/core/css/FontFace.h
@@ -31,9 +31,11 @@
#ifndef FontFace_h
#define FontFace_h
-#include "CSSPropertyNames.h"
#include "bindings/v8/ScriptPromise.h"
+#include "core/CSSPropertyNames.h"
#include "core/css/CSSValue.h"
+#include "core/dom/DOMError.h"
+#include "platform/fonts/FontTraits.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefCounted.h"
#include "wtf/text/WTFString.h"
@@ -49,12 +51,14 @@ class FontFaceReadyPromiseResolver;
class StylePropertySet;
class StyleRuleFontFace;
-class FontFace : public RefCounted<FontFace> {
+class FontFace : public RefCountedWillBeGarbageCollectedFinalized<FontFace> {
public:
enum LoadStatus { Unloaded, Loading, Loaded, Error };
- static PassRefPtr<FontFace> create(const AtomicString& family, const String& source, const Dictionary&, ExceptionState&);
- static PassRefPtr<FontFace> create(const StyleRuleFontFace*);
+ static PassRefPtrWillBeRawPtr<FontFace> create(ExecutionContext*, const AtomicString& family, PassRefPtr<ArrayBuffer> source, const Dictionary&, ExceptionState&);
+ static PassRefPtrWillBeRawPtr<FontFace> create(ExecutionContext*, const AtomicString& family, PassRefPtr<ArrayBufferView>, const Dictionary&, ExceptionState&);
+ static PassRefPtrWillBeRawPtr<FontFace> create(ExecutionContext*, const AtomicString& family, const String& source, const Dictionary&, ExceptionState&);
+ static PassRefPtrWillBeRawPtr<FontFace> create(Document*, const StyleRuleFontFace*);
~FontFace();
@@ -67,49 +71,68 @@ public:
String featureSettings() const;
// FIXME: Changing these attributes should affect font matching.
- void setFamily(const AtomicString& s, ExceptionState&) { m_family = s; }
- void setStyle(const String&, ExceptionState&);
- void setWeight(const String&, ExceptionState&);
- void setStretch(const String&, ExceptionState&);
- void setUnicodeRange(const String&, ExceptionState&);
- void setVariant(const String&, ExceptionState&);
- void setFeatureSettings(const String&, ExceptionState&);
+ void setFamily(ExecutionContext*, const AtomicString& s, ExceptionState&) { m_family = s; }
+ void setStyle(ExecutionContext*, const String&, ExceptionState&);
+ void setWeight(ExecutionContext*, const String&, ExceptionState&);
+ void setStretch(ExecutionContext*, const String&, ExceptionState&);
+ void setUnicodeRange(ExecutionContext*, const String&, ExceptionState&);
+ void setVariant(ExecutionContext*, const String&, ExceptionState&);
+ void setFeatureSettings(ExecutionContext*, const String&, ExceptionState&);
String status() const;
+ ScriptPromise loaded(ScriptState* scriptState) { return fontStatusPromise(scriptState); }
- void load();
- ScriptPromise ready(ExecutionContext*);
+ ScriptPromise load(ScriptState*);
LoadStatus loadStatus() const { return m_status; }
void setLoadStatus(LoadStatus);
- unsigned traitsMask() const;
- PassRefPtr<CSSFontFace> createCSSFontFace(Document*);
- void cssFontFaceDestroyed() { m_cssFontFace = 0; }
+ DOMError* error() const { return m_error.get(); }
+ FontTraits traits() const;
+ CSSFontFace* cssFontFace() { return m_cssFontFace.get(); }
+
+ void trace(Visitor*);
+
+ bool hadBlankText() const;
+
+ class LoadFontCallback : public RefCountedWillBeGarbageCollectedFinalized<LoadFontCallback> {
+ public:
+ virtual ~LoadFontCallback() { }
+ virtual void notifyLoaded(FontFace*) = 0;
+ virtual void notifyError(FontFace*) = 0;
+ virtual void trace(Visitor*) { }
+ };
+ void loadWithCallback(PassRefPtrWillBeRawPtr<LoadFontCallback>, ExecutionContext*);
private:
- FontFace(PassRefPtr<CSSValue> source);
+ FontFace();
- void setPropertyFromString(const String&, CSSPropertyID, ExceptionState&);
- bool setPropertyFromStyle(const StylePropertySet*, CSSPropertyID);
- bool setPropertyValue(PassRefPtr<CSSValue>, CSSPropertyID);
+ void initCSSFontFace(Document*, PassRefPtrWillBeRawPtr<CSSValue> src);
+ void initCSSFontFace(const unsigned char* data, unsigned size);
+ void setPropertyFromString(const Document*, const String&, CSSPropertyID, ExceptionState&);
+ bool setPropertyFromStyle(const StylePropertySet&, CSSPropertyID);
+ bool setPropertyValue(PassRefPtrWillBeRawPtr<CSSValue>, CSSPropertyID);
bool setFamilyValue(CSSValueList*);
void resolveReadyPromises();
+ void loadInternal(ExecutionContext*);
+ ScriptPromise fontStatusPromise(ScriptState*);
AtomicString m_family;
- RefPtr<CSSValue> m_src;
- RefPtr<CSSValue> m_style;
- RefPtr<CSSValue> m_weight;
- RefPtr<CSSValue> m_stretch;
- RefPtr<CSSValue> m_unicodeRange;
- RefPtr<CSSValue> m_variant;
- RefPtr<CSSValue> m_featureSettings;
+ RefPtrWillBeMember<CSSValue> m_src;
+ RefPtrWillBeMember<CSSValue> m_style;
+ RefPtrWillBeMember<CSSValue> m_weight;
+ RefPtrWillBeMember<CSSValue> m_stretch;
+ RefPtrWillBeMember<CSSValue> m_unicodeRange;
+ RefPtrWillBeMember<CSSValue> m_variant;
+ RefPtrWillBeMember<CSSValue> m_featureSettings;
LoadStatus m_status;
+ RefPtrWillBeMember<DOMError> m_error;
Vector<OwnPtr<FontFaceReadyPromiseResolver> > m_readyResolvers;
- CSSFontFace* m_cssFontFace;
+ OwnPtrWillBeMember<CSSFontFace> m_cssFontFace;
+ WillBeHeapVector<RefPtrWillBeMember<LoadFontCallback> > m_callbacks;
};
-typedef Vector<RefPtr<FontFace> > FontFaceArray;
+typedef WillBeHeapVector<RefPtrWillBeMember<FontFace> > FontFaceArray;
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFace.idl b/chromium/third_party/WebKit/Source/core/css/FontFace.idl
index fcfef2d143b..77d12b268e7 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontFace.idl
+++ b/chromium/third_party/WebKit/Source/core/css/FontFace.idl
@@ -28,6 +28,8 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
+// http://dev.w3.org/csswg/css-font-loading/#dom-fontface
+
enum FontFaceLoadStatus {
"unloaded",
"loading",
@@ -36,21 +38,26 @@ enum FontFaceLoadStatus {
};
[
+ // FIXME: should be union type http://crbug.com/240176
+ Constructor(DOMString family, DOMString source, optional Dictionary descriptors),
+ Constructor(DOMString family, ArrayBuffer source, optional Dictionary descriptors),
+ Constructor(DOMString family, ArrayBufferView source, optional Dictionary descriptors),
+ ConstructorCallWith=ExecutionContext,
+ RaisesException=Constructor,
RuntimeEnabled=FontLoadEvents,
- Constructor(DOMString family, DOMString source, Dictionary descriptors),
- RaisesException=Constructor
+ WillBeGarbageCollected,
] interface FontFace {
- [RaisesException=Setter] attribute DOMString family;
- [RaisesException=Setter] attribute DOMString style;
- [RaisesException=Setter] attribute DOMString weight;
- [RaisesException=Setter] attribute DOMString stretch;
- [RaisesException=Setter] attribute DOMString unicodeRange;
- [RaisesException=Setter] attribute DOMString variant;
- [RaisesException=Setter] attribute DOMString featureSettings;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString family;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString style;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString weight;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString stretch;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString unicodeRange;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString variant;
+ [RaisesException=Setter, SetterCallWith=ExecutionContext] attribute DOMString featureSettings;
readonly attribute FontFaceLoadStatus status;
+ [CallWith=ScriptState] readonly attribute Promise loaded;
- void load();
- [CallWith=ExecutionContext] Promise ready();
+ [CallWith=ScriptState] Promise load();
};
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFaceCache.cpp b/chromium/third_party/WebKit/Source/core/css/FontFaceCache.cpp
new file mode 100644
index 00000000000..ad5dbdc8806
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceCache.cpp
@@ -0,0 +1,225 @@
+/*
+ * Copyright (C) 2007, 2008, 2011 Apple Inc. All rights reserved.
+ * Copyright (C) 2013 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+
+#include "config.h"
+#include "core/css/FontFaceCache.h"
+
+#include "core/css/CSSFontSelector.h"
+#include "core/css/CSSSegmentedFontFace.h"
+#include "core/css/CSSValueList.h"
+#include "core/css/FontFace.h"
+#include "core/css/StyleRule.h"
+#include "core/fetch/FontResource.h"
+#include "core/fetch/ResourceFetcher.h"
+#include "platform/FontFamilyNames.h"
+#include "platform/fonts/FontDescription.h"
+#include "wtf/text/AtomicString.h"
+
+namespace WebCore {
+
+FontFaceCache::FontFaceCache()
+ : m_version(0)
+{
+}
+
+void FontFaceCache::add(CSSFontSelector* cssFontSelector, const StyleRuleFontFace* fontFaceRule, PassRefPtrWillBeRawPtr<FontFace> prpFontFace)
+{
+ RefPtrWillBeRawPtr<FontFace> fontFace = prpFontFace;
+ if (!m_styleRuleToFontFace.add(fontFaceRule, fontFace).isNewEntry)
+ return;
+ addFontFace(cssFontSelector, fontFace, true);
+}
+
+void FontFaceCache::addFontFace(CSSFontSelector* cssFontSelector, PassRefPtrWillBeRawPtr<FontFace> prpFontFace, bool cssConnected)
+{
+ RefPtrWillBeRawPtr<FontFace> fontFace = prpFontFace;
+
+ FamilyToTraitsMap::AddResult traitsResult = m_fontFaces.add(fontFace->family(), nullptr);
+ if (!traitsResult.storedValue->value)
+ traitsResult.storedValue->value = adoptPtrWillBeNoop(new TraitsMap);
+
+ TraitsMap::AddResult segmentedFontFaceResult = traitsResult.storedValue->value->add(fontFace->traits().mask(), nullptr);
+ if (!segmentedFontFaceResult.storedValue->value)
+ segmentedFontFaceResult.storedValue->value = CSSSegmentedFontFace::create(cssFontSelector, fontFace->traits());
+
+ segmentedFontFaceResult.storedValue->value->addFontFace(fontFace, cssConnected);
+ if (cssConnected)
+ m_cssConnectedFontFaces.add(fontFace);
+
+ ++m_version;
+}
+
+void FontFaceCache::remove(const StyleRuleFontFace* fontFaceRule)
+{
+ StyleRuleToFontFace::iterator it = m_styleRuleToFontFace.find(fontFaceRule);
+ if (it != m_styleRuleToFontFace.end()) {
+ removeFontFace(it->value.get(), true);
+ m_styleRuleToFontFace.remove(it);
+ }
+}
+
+void FontFaceCache::removeFontFace(FontFace* fontFace, bool cssConnected)
+{
+ FamilyToTraitsMap::iterator fontFacesIter = m_fontFaces.find(fontFace->family());
+ if (fontFacesIter == m_fontFaces.end())
+ return;
+ TraitsMap* familyFontFaces = fontFacesIter->value.get();
+
+ TraitsMap::iterator familyFontFacesIter = familyFontFaces->find(fontFace->traits().mask());
+ if (familyFontFacesIter == familyFontFaces->end())
+ return;
+ RefPtrWillBeRawPtr<CSSSegmentedFontFace> segmentedFontFace = familyFontFacesIter->value;
+
+ segmentedFontFace->removeFontFace(fontFace);
+ if (segmentedFontFace->isEmpty()) {
+ familyFontFaces->remove(familyFontFacesIter);
+ if (familyFontFaces->isEmpty())
+ m_fontFaces.remove(fontFacesIter);
+ }
+ m_fonts.clear();
+ if (cssConnected)
+ m_cssConnectedFontFaces.remove(fontFace);
+
+ ++m_version;
+}
+
+void FontFaceCache::clear()
+{
+ for (StyleRuleToFontFace::iterator it = m_styleRuleToFontFace.begin(); it != m_styleRuleToFontFace.end(); ++it)
+ removeFontFace(it->value.get(), true);
+ m_styleRuleToFontFace.clear();
+}
+
+static inline bool compareFontFaces(CSSSegmentedFontFace* first, CSSSegmentedFontFace* second, FontTraits desiredTraits)
+{
+ const FontTraits& firstTraits = first->traits();
+ const FontTraits& secondTraits = second->traits();
+
+ bool firstHasDesiredVariant = firstTraits.variant() == desiredTraits.variant();
+ bool secondHasDesiredVariant = secondTraits.variant() == desiredTraits.variant();
+
+ if (firstHasDesiredVariant != secondHasDesiredVariant)
+ return firstHasDesiredVariant;
+
+ // We need to check font-variant css property for CSS2.1 compatibility.
+ if (desiredTraits.variant() == FontVariantSmallCaps) {
+ // Prefer a font that has indicated that it can only support small-caps to a font that claims to support
+ // all variants. The specialized font is more likely to be true small-caps and not require synthesis.
+ bool firstRequiresSmallCaps = firstTraits.variant() == FontVariantSmallCaps;
+ bool secondRequiresSmallCaps = secondTraits.variant() == FontVariantSmallCaps;
+ if (firstRequiresSmallCaps != secondRequiresSmallCaps)
+ return firstRequiresSmallCaps;
+ }
+
+ bool firstHasDesiredStyle = firstTraits.style() == desiredTraits.style();
+ bool secondHasDesiredStyle = secondTraits.style() == desiredTraits.style();
+
+ if (firstHasDesiredStyle != secondHasDesiredStyle)
+ return firstHasDesiredStyle;
+
+ if (desiredTraits.style() == FontStyleItalic) {
+ // Prefer a font that has indicated that it can only support italics to a font that claims to support
+ // all styles. The specialized font is more likely to be the one the author wants used.
+ bool firstRequiresItalics = firstTraits.style() == FontStyleItalic;
+ bool secondRequiresItalics = secondTraits.style() == FontStyleItalic;
+ if (firstRequiresItalics != secondRequiresItalics)
+ return firstRequiresItalics;
+ }
+ if (secondTraits.weight() == desiredTraits.weight())
+ return false;
+
+ if (firstTraits.weight() == desiredTraits.weight())
+ return true;
+
+ // http://www.w3.org/TR/2011/WD-css3-fonts-20111004/#font-matching-algorithm says :
+ // - If the desired weight is less than 400, weights below the desired weight are checked in descending order followed by weights above the desired weight in ascending order until a match is found.
+ // - If the desired weight is greater than 500, weights above the desired weight are checked in ascending order followed by weights below the desired weight in descending order until a match is found.
+ // - If the desired weight is 400, 500 is checked first and then the rule for desired weights less than 400 is used.
+ // - If the desired weight is 500, 400 is checked first and then the rule for desired weights less than 400 is used.
+ static const unsigned fallbackRuleSets = 9;
+ static const unsigned rulesPerSet = 8;
+ static const FontWeight weightFallbackRuleSets[fallbackRuleSets][rulesPerSet] = {
+ { FontWeight200, FontWeight300, FontWeight400, FontWeight500, FontWeight600, FontWeight700, FontWeight800, FontWeight900 },
+ { FontWeight100, FontWeight300, FontWeight400, FontWeight500, FontWeight600, FontWeight700, FontWeight800, FontWeight900 },
+ { FontWeight200, FontWeight100, FontWeight400, FontWeight500, FontWeight600, FontWeight700, FontWeight800, FontWeight900 },
+ { FontWeight500, FontWeight300, FontWeight200, FontWeight100, FontWeight600, FontWeight700, FontWeight800, FontWeight900 },
+ { FontWeight400, FontWeight300, FontWeight200, FontWeight100, FontWeight600, FontWeight700, FontWeight800, FontWeight900 },
+ { FontWeight700, FontWeight800, FontWeight900, FontWeight500, FontWeight400, FontWeight300, FontWeight200, FontWeight100 },
+ { FontWeight800, FontWeight900, FontWeight600, FontWeight500, FontWeight400, FontWeight300, FontWeight200, FontWeight100 },
+ { FontWeight900, FontWeight700, FontWeight600, FontWeight500, FontWeight400, FontWeight300, FontWeight200, FontWeight100 },
+ { FontWeight800, FontWeight700, FontWeight600, FontWeight500, FontWeight400, FontWeight300, FontWeight200, FontWeight100 }
+ };
+
+ unsigned ruleSetIndex = static_cast<unsigned>(desiredTraits.weight());
+ ASSERT(ruleSetIndex < fallbackRuleSets);
+ const FontWeight* weightFallbackRule = weightFallbackRuleSets[ruleSetIndex];
+ for (unsigned i = 0; i < rulesPerSet; ++i) {
+ if (secondTraits.weight() == weightFallbackRule[i])
+ return false;
+ if (firstTraits.weight() == weightFallbackRule[i])
+ return true;
+ }
+
+ return false;
+}
+
+CSSSegmentedFontFace* FontFaceCache::get(const FontDescription& fontDescription, const AtomicString& family)
+{
+ TraitsMap* familyFontFaces = m_fontFaces.get(family);
+ if (!familyFontFaces || familyFontFaces->isEmpty())
+ return 0;
+
+ FamilyToTraitsMap::AddResult traitsResult = m_fonts.add(family, nullptr);
+ if (!traitsResult.storedValue->value)
+ traitsResult.storedValue->value = adoptPtrWillBeNoop(new TraitsMap);
+
+ FontTraits traits = fontDescription.traits();
+ TraitsMap::AddResult faceResult = traitsResult.storedValue->value->add(traits.mask(), nullptr);
+ if (!faceResult.storedValue->value) {
+ for (TraitsMap::const_iterator i = familyFontFaces->begin(); i != familyFontFaces->end(); ++i) {
+ CSSSegmentedFontFace* candidate = i->value.get();
+ FontTraits candidateTraits = candidate->traits();
+ if (traits.style() == FontStyleNormal && candidateTraits.style() != FontStyleNormal)
+ continue;
+ if (traits.variant() == FontVariantNormal && candidateTraits.variant() != FontVariantNormal)
+ continue;
+ if (!faceResult.storedValue->value || compareFontFaces(candidate, faceResult.storedValue->value.get(), traits))
+ faceResult.storedValue->value = candidate;
+ }
+ }
+ return faceResult.storedValue->value.get();
+}
+
+void FontFaceCache::trace(Visitor* visitor)
+{
+ visitor->trace(m_fontFaces);
+ visitor->trace(m_fonts);
+ visitor->trace(m_styleRuleToFontFace);
+ visitor->trace(m_cssConnectedFontFaces);
+}
+
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.h b/chromium/third_party/WebKit/Source/core/css/FontFaceCache.h
index c18220906eb..457bc3b2919 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSSegmentedFontFaceCache.h
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceCache.h
@@ -24,42 +24,56 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef CSSSegmentedFontFaceCache_h
-#define CSSSegmentedFontFaceCache_h
+#ifndef FontFaceCache_h
+#define FontFaceCache_h
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/HashMap.h"
+#include "wtf/ListHashSet.h"
#include "wtf/text/StringHash.h"
namespace WebCore {
-class CSSFontFace;
+class FontFace;
class CSSFontSelector;
class CSSSegmentedFontFace;
class FontDescription;
class StyleRuleFontFace;
-class CSSSegmentedFontFaceCache {
+class FontFaceCache FINAL {
+ DISALLOW_ALLOCATION();
public:
- CSSSegmentedFontFaceCache();
+ FontFaceCache();
// FIXME: Remove CSSFontSelector as argument. Passing CSSFontSelector here is
- // a result of egregious spaghettification in CSSFontFace/FontFaceSet.
- void add(CSSFontSelector*, const StyleRuleFontFace*, PassRefPtr<CSSFontFace>);
+ // a result of egregious spaghettification in FontFace/FontFaceSet.
+ void add(CSSFontSelector*, const StyleRuleFontFace*, PassRefPtrWillBeRawPtr<FontFace>);
void remove(const StyleRuleFontFace*);
+ void clear();
+ void addFontFace(CSSFontSelector*, PassRefPtrWillBeRawPtr<FontFace>, bool cssConnected);
+ void removeFontFace(FontFace*, bool cssConnected);
+
// FIXME: It's sort of weird that add/remove uses StyleRuleFontFace* as key,
// but this function uses FontDescription/family pair.
CSSSegmentedFontFace* get(const FontDescription&, const AtomicString& family);
+ const ListHashSet<RefPtrWillBeMember<FontFace> >& cssConnectedFontFaces() const { return m_cssConnectedFontFaces; }
+
unsigned version() const { return m_version; }
+ void incrementVersion() { ++m_version; }
+
+ void trace(Visitor*);
private:
- typedef HashMap<unsigned, RefPtr<CSSSegmentedFontFace> > TraitsMap;
- typedef HashMap<String, OwnPtr<TraitsMap>, CaseFoldingHash> FamilyToTraitsMap;
- typedef HashMap<const StyleRuleFontFace*, RefPtr<CSSFontFace> > StyleRuleToFontFace;
+ typedef WillBeHeapHashMap<unsigned, RefPtrWillBeMember<CSSSegmentedFontFace> > TraitsMap;
+ typedef WillBeHeapHashMap<String, OwnPtrWillBeMember<TraitsMap>, CaseFoldingHash> FamilyToTraitsMap;
+ typedef WillBeHeapHashMap<const StyleRuleFontFace*, RefPtrWillBeMember<FontFace> > StyleRuleToFontFace;
FamilyToTraitsMap m_fontFaces;
FamilyToTraitsMap m_fonts;
StyleRuleToFontFace m_styleRuleToFontFace;
+ // FIXME: Oilpan: Replace by HeapLinkedHashSet or HeapListHashSet.
+ ListHashSet<RefPtrWillBeMember<FontFace> > m_cssConnectedFontFaces;
// FIXME: See if this could be ditched
// Used to compare Font instances, and the usage seems suspect.
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFaceSet.cpp b/chromium/third_party/WebKit/Source/core/css/FontFaceSet.cpp
index 38165b8a9aa..668f6efa4ca 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontFaceSet.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceSet.cpp
@@ -26,21 +26,22 @@
#include "config.h"
#include "core/css/FontFaceSet.h"
-#include "RuntimeEnabledFeatures.h"
#include "bindings/v8/Dictionary.h"
-#include "bindings/v8/ScriptPromiseResolver.h"
-#include "bindings/v8/ScriptScope.h"
+#include "bindings/v8/ScriptPromiseResolverWithContext.h"
#include "bindings/v8/ScriptState.h"
#include "core/css/CSSFontFaceLoadEvent.h"
-#include "core/css/CSSFontFaceSource.h"
#include "core/css/CSSFontSelector.h"
-#include "core/css/CSSParser.h"
#include "core/css/CSSSegmentedFontFace.h"
+#include "core/css/FontFaceCache.h"
#include "core/css/StylePropertySet.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/resolver/StyleResolver.h"
#include "core/dom/Document.h"
-#include "core/frame/Frame.h"
+#include "core/dom/StyleEngine.h"
#include "core/frame/FrameView.h"
+#include "core/frame/LocalFrame.h"
+#include "core/rendering/style/StyleInheritedData.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "public/platform/Platform.h"
namespace WebCore {
@@ -48,89 +49,96 @@ namespace WebCore {
static const int defaultFontSize = 10;
static const char defaultFontFamily[] = "sans-serif";
-class LoadFontPromiseResolver : public CSSSegmentedFontFace::LoadFontCallback {
+class LoadFontPromiseResolver FINAL : public FontFace::LoadFontCallback {
public:
- static PassRefPtr<LoadFontPromiseResolver> create(const FontFamily& family, ScriptPromise promise, ExecutionContext* context)
+ static PassRefPtrWillBeRawPtr<LoadFontPromiseResolver> create(FontFaceArray faces, ScriptState* scriptState)
{
- int numFamilies = 0;
- for (const FontFamily* f = &family; f; f = f->next())
- numFamilies++;
- return adoptRef<LoadFontPromiseResolver>(new LoadFontPromiseResolver(numFamilies, promise, context));
+ return adoptRefWillBeNoop(new LoadFontPromiseResolver(faces, scriptState));
}
- virtual void notifyLoaded(CSSSegmentedFontFace*) OVERRIDE;
- virtual void notifyError(CSSSegmentedFontFace*) OVERRIDE;
- void loaded(Document*);
- void error(Document*);
+ void loadFonts(ExecutionContext*);
+ ScriptPromise promise() { return m_resolver->promise(); }
+
+ virtual void notifyLoaded(FontFace*) OVERRIDE;
+ virtual void notifyError(FontFace*) OVERRIDE;
+
+ virtual void trace(Visitor*) OVERRIDE;
private:
- LoadFontPromiseResolver(int numLoading, ScriptPromise promise, ExecutionContext* context)
- : m_numLoading(numLoading)
+ LoadFontPromiseResolver(FontFaceArray faces, ScriptState* scriptState)
+ : m_numLoading(faces.size())
, m_errorOccured(false)
- , m_scriptState(ScriptState::current())
- , m_resolver(ScriptPromiseResolver::create(promise, context))
- { }
+ , m_resolver(ScriptPromiseResolverWithContext::create(scriptState))
+ {
+ m_fontFaces.swap(faces);
+ }
+ WillBeHeapVector<RefPtrWillBeMember<FontFace> > m_fontFaces;
int m_numLoading;
bool m_errorOccured;
- ScriptState* m_scriptState;
- RefPtr<ScriptPromiseResolver> m_resolver;
+ RefPtr<ScriptPromiseResolverWithContext> m_resolver;
};
-void LoadFontPromiseResolver::loaded(Document* document)
+void LoadFontPromiseResolver::loadFonts(ExecutionContext* context)
{
- m_numLoading--;
- if (m_numLoading || !document)
+ if (!m_numLoading) {
+ m_resolver->resolve(m_fontFaces);
return;
+ }
- ScriptScope scope(m_scriptState);
- if (m_errorOccured)
- m_resolver->reject(ScriptValue::createNull());
- else
- m_resolver->resolve(ScriptValue::createNull());
+ for (size_t i = 0; i < m_fontFaces.size(); i++)
+ m_fontFaces[i]->loadWithCallback(this, context);
}
-void LoadFontPromiseResolver::error(Document* document)
+void LoadFontPromiseResolver::notifyLoaded(FontFace* fontFace)
{
- m_errorOccured = true;
- loaded(document);
+ m_numLoading--;
+ if (m_numLoading || m_errorOccured)
+ return;
+
+ m_resolver->resolve(m_fontFaces);
}
-void LoadFontPromiseResolver::notifyLoaded(CSSSegmentedFontFace* face)
+void LoadFontPromiseResolver::notifyError(FontFace* fontFace)
{
- loaded(face->fontSelector()->document());
+ m_numLoading--;
+ if (!m_errorOccured) {
+ m_errorOccured = true;
+ m_resolver->reject(fontFace->error());
+ }
}
-void LoadFontPromiseResolver::notifyError(CSSSegmentedFontFace* face)
+void LoadFontPromiseResolver::trace(Visitor* visitor)
{
- error(face->fontSelector()->document());
+ visitor->trace(m_fontFaces);
+ LoadFontCallback::trace(visitor);
}
class FontsReadyPromiseResolver {
public:
- static PassOwnPtr<FontsReadyPromiseResolver> create(ScriptPromise promise, ExecutionContext* context)
+ static PassOwnPtr<FontsReadyPromiseResolver> create(ScriptState* scriptState)
{
- return adoptPtr(new FontsReadyPromiseResolver(promise, context));
+ return adoptPtr(new FontsReadyPromiseResolver(scriptState));
}
- void resolve(PassRefPtr<FontFaceSet> fontFaceSet)
+ void resolve(PassRefPtrWillBeRawPtr<FontFaceSet> fontFaceSet)
{
- ScriptScope scope(m_scriptState);
m_resolver->resolve(fontFaceSet);
}
+ ScriptPromise promise() { return m_resolver->promise(); }
+
private:
- FontsReadyPromiseResolver(ScriptPromise promise, ExecutionContext* context)
- : m_scriptState(ScriptState::current())
- , m_resolver(ScriptPromiseResolver::create(promise, context))
- { }
- ScriptState* m_scriptState;
- RefPtr<ScriptPromiseResolver> m_resolver;
+ explicit FontsReadyPromiseResolver(ScriptState* scriptState)
+ : m_resolver(ScriptPromiseResolverWithContext::create(scriptState))
+ {
+ }
+
+ RefPtr<ScriptPromiseResolverWithContext> m_resolver;
};
-FontFaceSet::FontFaceSet(Document* document)
- : ActiveDOMObject(document)
- , m_loadingCount(0)
+FontFaceSet::FontFaceSet(Document& document)
+ : ActiveDOMObject(&document)
, m_shouldFireLoadingEvent(false)
, m_asyncRunner(this, &FontFaceSet::handlePendingEventsAndPromises)
{
@@ -146,6 +154,18 @@ Document* FontFaceSet::document() const
return toDocument(executionContext());
}
+bool FontFaceSet::inActiveDocumentContext() const
+{
+ ExecutionContext* context = executionContext();
+ return context && toDocument(context)->isActive();
+}
+
+void FontFaceSet::addFontFacesToFontFaceCache(FontFaceCache* fontFaceCache, CSSFontSelector* fontSelector)
+{
+ for (ListHashSet<RefPtrWillBeMember<FontFace> >::iterator it = m_nonCSSConnectedFaces.begin(); it != m_nonCSSConnectedFaces.end(); ++it)
+ fontFaceCache->addFontFace(fontSelector, *it, false);
+}
+
const AtomicString& FontFaceSet::interfaceName() const
{
return EventTargetNames::FontFaceSet;
@@ -160,7 +180,7 @@ AtomicString FontFaceSet::status() const
{
DEFINE_STATIC_LOCAL(AtomicString, loading, ("loading", AtomicString::ConstructFromLiteral));
DEFINE_STATIC_LOCAL(AtomicString, loaded, ("loaded", AtomicString::ConstructFromLiteral));
- return (m_loadingCount > 0 || hasLoadedFonts()) ? loading : loaded;
+ return (!m_loadingFonts.isEmpty() || hasLoadedFonts()) ? loading : loaded;
}
void FontFaceSet::handlePendingEventsAndPromisesSoon()
@@ -172,11 +192,11 @@ void FontFaceSet::handlePendingEventsAndPromisesSoon()
void FontFaceSet::didLayout()
{
- if (document()->frame()->isMainFrame())
+ if (document()->frame()->isMainFrame() && m_loadingFonts.isEmpty())
m_histogram.record();
if (!RuntimeEnabledFeatures::fontLoadEventsEnabled())
return;
- if (m_loadingCount || (!hasLoadedFonts() && m_readyResolvers.isEmpty()))
+ if (!m_loadingFonts.isEmpty() || (!hasLoadedFonts() && m_readyResolvers.isEmpty()))
return;
handlePendingEventsAndPromisesSoon();
}
@@ -213,55 +233,178 @@ void FontFaceSet::stop()
void FontFaceSet::beginFontLoading(FontFace* fontFace)
{
m_histogram.incrementCount();
- if (!RuntimeEnabledFeatures::fontLoadEventsEnabled())
- return;
-
- if (!m_loadingCount && !hasLoadedFonts()) {
- ASSERT(!m_shouldFireLoadingEvent);
- m_shouldFireLoadingEvent = true;
- handlePendingEventsAndPromisesSoon();
- }
- ++m_loadingCount;
+ addToLoadingFonts(fontFace);
}
void FontFaceSet::fontLoaded(FontFace* fontFace)
{
- if (!RuntimeEnabledFeatures::fontLoadEventsEnabled())
- return;
- m_loadedFonts.append(fontFace);
- queueDoneEvent(fontFace);
+ m_histogram.updateStatus(fontFace);
+ if (RuntimeEnabledFeatures::fontLoadEventsEnabled())
+ m_loadedFonts.append(fontFace);
+ removeFromLoadingFonts(fontFace);
}
void FontFaceSet::loadError(FontFace* fontFace)
{
- if (!RuntimeEnabledFeatures::fontLoadEventsEnabled())
- return;
- m_failedFonts.append(fontFace);
- queueDoneEvent(fontFace);
+ m_histogram.updateStatus(fontFace);
+ if (RuntimeEnabledFeatures::fontLoadEventsEnabled())
+ m_failedFonts.append(fontFace);
+ removeFromLoadingFonts(fontFace);
+}
+
+void FontFaceSet::addToLoadingFonts(PassRefPtrWillBeRawPtr<FontFace> fontFace)
+{
+ if (RuntimeEnabledFeatures::fontLoadEventsEnabled() && m_loadingFonts.isEmpty() && !hasLoadedFonts()) {
+ m_shouldFireLoadingEvent = true;
+ handlePendingEventsAndPromisesSoon();
+ }
+ m_loadingFonts.add(fontFace);
}
-void FontFaceSet::queueDoneEvent(FontFace* fontFace)
+void FontFaceSet::removeFromLoadingFonts(PassRefPtrWillBeRawPtr<FontFace> fontFace)
{
- ASSERT(m_loadingCount > 0);
- --m_loadingCount;
- if (!m_loadingCount)
+ m_loadingFonts.remove(fontFace);
+ if (RuntimeEnabledFeatures::fontLoadEventsEnabled() && m_loadingFonts.isEmpty())
handlePendingEventsAndPromisesSoon();
}
-ScriptPromise FontFaceSet::ready()
+ScriptPromise FontFaceSet::ready(ScriptState* scriptState)
{
- ScriptPromise promise = ScriptPromise::createPending(executionContext());
- OwnPtr<FontsReadyPromiseResolver> resolver = FontsReadyPromiseResolver::create(promise, executionContext());
+ if (!inActiveDocumentContext())
+ return ScriptPromise();
+ OwnPtr<FontsReadyPromiseResolver> resolver = FontsReadyPromiseResolver::create(scriptState);
+ ScriptPromise promise = resolver->promise();
m_readyResolvers.append(resolver.release());
handlePendingEventsAndPromisesSoon();
return promise;
}
+void FontFaceSet::add(FontFace* fontFace, ExceptionState& exceptionState)
+{
+ if (!inActiveDocumentContext())
+ return;
+ if (!fontFace) {
+ exceptionState.throwTypeError("The argument is not a FontFace.");
+ return;
+ }
+ if (m_nonCSSConnectedFaces.contains(fontFace))
+ return;
+ if (isCSSConnectedFontFace(fontFace)) {
+ exceptionState.throwDOMException(InvalidModificationError, "Cannot add a CSS-connected FontFace.");
+ return;
+ }
+ CSSFontSelector* fontSelector = document()->styleEngine()->fontSelector();
+ m_nonCSSConnectedFaces.add(fontFace);
+ fontSelector->fontFaceCache()->addFontFace(fontSelector, fontFace, false);
+ if (fontFace->loadStatus() == FontFace::Loading)
+ addToLoadingFonts(fontFace);
+ fontSelector->fontFaceInvalidated();
+}
+
+void FontFaceSet::clear()
+{
+ if (!inActiveDocumentContext() || m_nonCSSConnectedFaces.isEmpty())
+ return;
+ CSSFontSelector* fontSelector = document()->styleEngine()->fontSelector();
+ FontFaceCache* fontFaceCache = fontSelector->fontFaceCache();
+ for (ListHashSet<RefPtrWillBeMember<FontFace> >::iterator it = m_nonCSSConnectedFaces.begin(); it != m_nonCSSConnectedFaces.end(); ++it) {
+ fontFaceCache->removeFontFace(it->get(), false);
+ if ((*it)->loadStatus() == FontFace::Loading)
+ removeFromLoadingFonts(*it);
+ }
+ m_nonCSSConnectedFaces.clear();
+ fontSelector->fontFaceInvalidated();
+}
+
+bool FontFaceSet::remove(FontFace* fontFace, ExceptionState& exceptionState)
+{
+ if (!inActiveDocumentContext())
+ return false;
+ if (!fontFace) {
+ exceptionState.throwTypeError("The argument is not a FontFace.");
+ return false;
+ }
+ ListHashSet<RefPtrWillBeMember<FontFace> >::iterator it = m_nonCSSConnectedFaces.find(fontFace);
+ if (it != m_nonCSSConnectedFaces.end()) {
+ m_nonCSSConnectedFaces.remove(it);
+ CSSFontSelector* fontSelector = document()->styleEngine()->fontSelector();
+ fontSelector->fontFaceCache()->removeFontFace(fontFace, false);
+ if (fontFace->loadStatus() == FontFace::Loading)
+ removeFromLoadingFonts(fontFace);
+ fontSelector->fontFaceInvalidated();
+ return true;
+ }
+ if (isCSSConnectedFontFace(fontFace))
+ exceptionState.throwDOMException(InvalidModificationError, "Cannot delete a CSS-connected FontFace.");
+ return false;
+}
+
+bool FontFaceSet::has(FontFace* fontFace, ExceptionState& exceptionState) const
+{
+ if (!inActiveDocumentContext())
+ return false;
+ if (!fontFace) {
+ exceptionState.throwTypeError("The argument is not a FontFace.");
+ return false;
+ }
+ return m_nonCSSConnectedFaces.contains(fontFace) || isCSSConnectedFontFace(fontFace);
+}
+
+const ListHashSet<RefPtrWillBeMember<FontFace> >& FontFaceSet::cssConnectedFontFaceList() const
+{
+ Document* d = document();
+ d->ensureStyleResolver(); // Flush pending style changes.
+ return d->styleEngine()->fontSelector()->fontFaceCache()->cssConnectedFontFaces();
+}
+
+bool FontFaceSet::isCSSConnectedFontFace(FontFace* fontFace) const
+{
+ return cssConnectedFontFaceList().contains(fontFace);
+}
+
+void FontFaceSet::forEach(PassOwnPtr<FontFaceSetForEachCallback> callback, ScriptValue& thisArg) const
+{
+ forEachInternal(callback, &thisArg);
+}
+
+void FontFaceSet::forEach(PassOwnPtr<FontFaceSetForEachCallback> callback) const
+{
+ forEachInternal(callback, 0);
+}
+
+void FontFaceSet::forEachInternal(PassOwnPtr<FontFaceSetForEachCallback> callback, ScriptValue* thisArg) const
+{
+ if (!inActiveDocumentContext())
+ return;
+ const ListHashSet<RefPtrWillBeMember<FontFace> >& cssConnectedFaces = cssConnectedFontFaceList();
+ WillBeHeapVector<RefPtrWillBeMember<FontFace> > fontFaces;
+ fontFaces.reserveInitialCapacity(cssConnectedFaces.size() + m_nonCSSConnectedFaces.size());
+ for (ListHashSet<RefPtrWillBeMember<FontFace> >::const_iterator it = cssConnectedFaces.begin(); it != cssConnectedFaces.end(); ++it)
+ fontFaces.append(*it);
+ for (ListHashSet<RefPtrWillBeMember<FontFace> >::const_iterator it = m_nonCSSConnectedFaces.begin(); it != m_nonCSSConnectedFaces.end(); ++it)
+ fontFaces.append(*it);
+
+ for (size_t i = 0; i < fontFaces.size(); ++i) {
+ FontFace* face = fontFaces[i].get();
+ if (thisArg)
+ callback->handleItem(*thisArg, face, face, const_cast<FontFaceSet*>(this));
+ else
+ callback->handleItem(face, face, const_cast<FontFaceSet*>(this));
+ }
+}
+
+unsigned long FontFaceSet::size() const
+{
+ if (!inActiveDocumentContext())
+ return m_nonCSSConnectedFaces.size();
+ return cssConnectedFontFaceList().size() + m_nonCSSConnectedFaces.size();
+}
+
void FontFaceSet::fireDoneEventIfPossible()
{
if (m_shouldFireLoadingEvent)
return;
- if (m_loadingCount || (!hasLoadedFonts() && m_readyResolvers.isEmpty()))
+ if (!m_loadingFonts.isEmpty() || (!hasLoadedFonts() && m_readyResolvers.isEmpty()))
return;
// If the layout was invalidated in between when we thought layout
@@ -272,8 +415,8 @@ void FontFaceSet::fireDoneEventIfPossible()
return;
if (hasLoadedFonts()) {
- RefPtr<CSSFontFaceLoadEvent> doneEvent;
- RefPtr<CSSFontFaceLoadEvent> errorEvent;
+ RefPtrWillBeRawPtr<CSSFontFaceLoadEvent> doneEvent = nullptr;
+ RefPtrWillBeRawPtr<CSSFontFaceLoadEvent> errorEvent = nullptr;
doneEvent = CSSFontFaceLoadEvent::createForFontFaces(EventTypeNames::loadingdone, m_loadedFonts);
m_loadedFonts.clear();
if (!m_failedFonts.isEmpty()) {
@@ -299,60 +442,63 @@ static const String& nullToSpace(const String& s)
return s.isNull() ? space : s;
}
-Vector<RefPtr<FontFace> > FontFaceSet::match(const String& fontString, const String& text, ExceptionState& exceptionState)
+ScriptPromise FontFaceSet::load(ScriptState* scriptState, const String& fontString, const String& text)
{
- Vector<RefPtr<FontFace> > matchedFonts;
+ if (!inActiveDocumentContext())
+ return ScriptPromise();
Font font;
if (!resolveFontStyle(fontString, font)) {
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
- return matchedFonts;
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState);
+ ScriptPromise promise = resolver->promise();
+ resolver->reject(DOMError::create(SyntaxError, "Could not resolve '" + fontString + "' as a font."));
+ return promise;
}
- for (const FontFamily* f = &font.family(); f; f = f->next()) {
- CSSSegmentedFontFace* face = document()->styleEngine()->fontSelector()->getFontFace(font.fontDescription(), f->family());
- if (face)
- matchedFonts.append(face->fontFaces(nullToSpace(text)));
- }
- return matchedFonts;
-}
-
-ScriptPromise FontFaceSet::load(const String& fontString, const String& text, ExceptionState& exceptionState)
-{
- Font font;
- if (!resolveFontStyle(fontString, font)) {
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
- return ScriptPromise();
+ FontFaceCache* fontFaceCache = document()->styleEngine()->fontSelector()->fontFaceCache();
+ FontFaceArray faces;
+ for (const FontFamily* f = &font.fontDescription().family(); f; f = f->next()) {
+ CSSSegmentedFontFace* segmentedFontFace = fontFaceCache->get(font.fontDescription(), f->family());
+ if (segmentedFontFace)
+ segmentedFontFace->match(nullToSpace(text), faces);
}
- Document* d = document();
- ScriptPromise promise = ScriptPromise::createPending(executionContext());
- RefPtr<LoadFontPromiseResolver> resolver = LoadFontPromiseResolver::create(font.family(), promise, executionContext());
- for (const FontFamily* f = &font.family(); f; f = f->next()) {
- CSSSegmentedFontFace* face = d->styleEngine()->fontSelector()->getFontFace(font.fontDescription(), f->family());
- if (!face) {
- resolver->error(d);
- continue;
- }
- face->loadFont(font.fontDescription(), nullToSpace(text), resolver);
- }
+ RefPtrWillBeRawPtr<LoadFontPromiseResolver> resolver = LoadFontPromiseResolver::create(faces, scriptState);
+ ScriptPromise promise = resolver->promise();
+ resolver->loadFonts(executionContext()); // After this, resolver->promise() may return null.
return promise;
}
bool FontFaceSet::check(const String& fontString, const String& text, ExceptionState& exceptionState)
{
+ if (!inActiveDocumentContext())
+ return false;
+
Font font;
if (!resolveFontStyle(fontString, font)) {
- exceptionState.throwUninformativeAndGenericDOMException(SyntaxError);
+ exceptionState.throwDOMException(SyntaxError, "Could not resolve '" + fontString + "' as a font.");
return false;
}
- for (const FontFamily* f = &font.family(); f; f = f->next()) {
- CSSSegmentedFontFace* face = document()->styleEngine()->fontSelector()->getFontFace(font.fontDescription(), f->family());
- if (!face || !face->checkFont(nullToSpace(text)))
- return false;
+ CSSFontSelector* fontSelector = document()->styleEngine()->fontSelector();
+ FontFaceCache* fontFaceCache = fontSelector->fontFaceCache();
+
+ bool hasLoadedFaces = false;
+ for (const FontFamily* f = &font.fontDescription().family(); f; f = f->next()) {
+ CSSSegmentedFontFace* face = fontFaceCache->get(font.fontDescription(), f->family());
+ if (face) {
+ if (!face->checkFont(nullToSpace(text)))
+ return false;
+ hasLoadedFaces = true;
+ }
}
- return true;
+ if (hasLoadedFaces)
+ return true;
+ for (const FontFamily* f = &font.fontDescription().family(); f; f = f->next()) {
+ if (fontSelector->isPlatformFontAvailable(font.fontDescription(), f->family()))
+ return true;
+ }
+ return false;
}
bool FontFaceSet::resolveFontStyle(const String& fontString, Font& font)
@@ -361,8 +507,8 @@ bool FontFaceSet::resolveFontStyle(const String& fontString, Font& font)
return false;
// Interpret fontString in the same way as the 'font' attribute of CanvasRenderingContext2D.
- RefPtr<MutableStylePropertySet> parsedStyle = MutableStylePropertySet::create();
- CSSParser::parseValue(parsedStyle.get(), CSSPropertyFont, fontString, true, HTMLStandardMode, 0);
+ RefPtrWillBeRawPtr<MutableStylePropertySet> parsedStyle = MutableStylePropertySet::create();
+ BisonCSSParser::parseValue(parsedStyle.get(), CSSPropertyFont, fontString, true, HTMLStandardMode, 0);
if (parsedStyle->isEmpty())
return false;
@@ -401,12 +547,26 @@ bool FontFaceSet::resolveFontStyle(const String& fontString, Font& font)
return true;
}
-void FontFaceSet::FontLoadHistogram::record()
+void FontFaceSet::FontLoadHistogram::updateStatus(FontFace* fontFace)
{
- if (m_recorded)
+ if (m_status == Reported)
return;
- m_recorded = true;
- blink::Platform::current()->histogramCustomCounts("WebFont.WebFontsInPage", m_count, 1, 100, 50);
+ if (fontFace->hadBlankText())
+ m_status = HadBlankText;
+ else if (m_status == NoWebFonts)
+ m_status = DidNotHaveBlankText;
+}
+
+void FontFaceSet::FontLoadHistogram::record()
+{
+ if (!m_recorded) {
+ m_recorded = true;
+ blink::Platform::current()->histogramCustomCounts("WebFont.WebFontsInPage", m_count, 1, 100, 50);
+ }
+ if (m_status == HadBlankText || m_status == DidNotHaveBlankText) {
+ blink::Platform::current()->histogramEnumeration("WebFont.HadBlankText", m_status == HadBlankText ? 1 : 0, 2);
+ m_status = Reported;
+ }
}
static const char* supplementName()
@@ -414,9 +574,9 @@ static const char* supplementName()
return "FontFaceSet";
}
-PassRefPtr<FontFaceSet> FontFaceSet::from(Document* document)
+PassRefPtrWillBeRawPtr<FontFaceSet> FontFaceSet::from(Document& document)
{
- RefPtr<FontFaceSet> fonts = static_cast<FontFaceSet*>(SupplementType::from(document, supplementName()));
+ RefPtrWillBeRawPtr<FontFaceSet> fonts = static_cast<FontFaceSet*>(SupplementType::from(document, supplementName()));
if (!fonts) {
fonts = FontFaceSet::create(document);
SupplementType::provideTo(document, supplementName(), fonts);
@@ -425,11 +585,22 @@ PassRefPtr<FontFaceSet> FontFaceSet::from(Document* document)
return fonts.release();
}
-void FontFaceSet::didLayout(Document* document)
+void FontFaceSet::didLayout(Document& document)
{
if (FontFaceSet* fonts = static_cast<FontFaceSet*>(SupplementType::from(document, supplementName())))
fonts->didLayout();
}
+#if ENABLE(OILPAN)
+void FontFaceSet::trace(Visitor* visitor)
+{
+ visitor->trace(m_loadingFonts);
+ visitor->trace(m_loadedFonts);
+ visitor->trace(m_failedFonts);
+ visitor->trace(m_nonCSSConnectedFaces);
+ DocumentSupplement::trace(visitor);
+ EventTargetWithInlineData::trace(visitor);
+}
+#endif
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFaceSet.h b/chromium/third_party/WebKit/Source/core/css/FontFaceSet.h
index ebad1329e07..5e1f54347ea 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontFaceSet.h
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceSet.h
@@ -28,10 +28,10 @@
#include "bindings/v8/ScriptPromise.h"
#include "core/css/FontFace.h"
+#include "core/css/FontFaceSetForEachCallback.h"
#include "core/dom/ActiveDOMObject.h"
#include "core/events/EventListener.h"
#include "core/events/EventTarget.h"
-#include "core/events/ThreadLocalEventNames.h"
#include "platform/AsyncMethodRunner.h"
#include "platform/RefCountedSupplement.h"
#include "wtf/PassRefPtr.h"
@@ -45,17 +45,27 @@
namespace WebCore {
+class CSSFontFace;
class CSSFontFaceSource;
+class CSSFontSelector;
class Dictionary;
class Document;
class ExceptionState;
class Font;
+class FontFaceCache;
class FontResource;
class FontsReadyPromiseResolver;
class ExecutionContext;
-class FontFaceSet : public RefCountedSupplement<Document, FontFaceSet>, public ActiveDOMObject, public EventTargetWithInlineData {
- REFCOUNTED_EVENT_TARGET(FontFaceSet);
+#if ENABLE(OILPAN)
+class FontFaceSet FINAL : public GarbageCollectedFinalized<FontFaceSet>, public HeapSupplement<Document>, public ActiveDOMObject, public EventTargetWithInlineData {
+ USING_GARBAGE_COLLECTED_MIXIN(FontFaceSet);
+ typedef HeapSupplement<Document> SupplementType;
+#else
+class FontFaceSet FINAL : public RefCountedSupplement<Document, FontFaceSet>, public ActiveDOMObject, public EventTargetWithInlineData {
+ DEFINE_EVENT_TARGET_REFCOUNTING(RefCounted<FontFaceSet>);
+ typedef RefCountedSupplement<Document, FontFaceSet> SupplementType;
+#endif
public:
virtual ~FontFaceSet();
@@ -63,11 +73,18 @@ public:
DEFINE_ATTRIBUTE_EVENT_LISTENER(loadingdone);
DEFINE_ATTRIBUTE_EVENT_LISTENER(loadingerror);
- Vector<RefPtr<FontFace> > match(const String& font, const String& text, ExceptionState&);
bool check(const String& font, const String& text, ExceptionState&);
- ScriptPromise load(const String& font, const String& text, ExceptionState&);
- ScriptPromise ready();
+ ScriptPromise load(ScriptState*, const String& font, const String& text);
+ ScriptPromise ready(ScriptState*);
+ void add(FontFace*, ExceptionState&);
+ void clear();
+ bool remove(FontFace*, ExceptionState&);
+ void forEach(PassOwnPtr<FontFaceSetForEachCallback>, ScriptValue& thisArg) const;
+ void forEach(PassOwnPtr<FontFaceSetForEachCallback>) const;
+ bool has(FontFace*, ExceptionState&) const;
+
+ unsigned long size() const;
AtomicString status() const;
virtual ExecutionContext* executionContext() const OVERRIDE;
@@ -85,44 +102,58 @@ public:
virtual void resume() OVERRIDE;
virtual void stop() OVERRIDE;
- static PassRefPtr<FontFaceSet> from(Document*);
- static void didLayout(Document*);
+ static PassRefPtrWillBeRawPtr<FontFaceSet> from(Document&);
+ static void didLayout(Document&);
-private:
- typedef RefCountedSupplement<Document, FontFaceSet> SupplementType;
+ void addFontFacesToFontFaceCache(FontFaceCache*, CSSFontSelector*);
+
+#if ENABLE(OILPAN)
+ virtual void trace(Visitor*) OVERRIDE;
+#endif
- static PassRefPtr<FontFaceSet> create(Document* document)
+private:
+ static PassRefPtrWillBeRawPtr<FontFaceSet> create(Document& document)
{
- return adoptRef<FontFaceSet>(new FontFaceSet(document));
+ return adoptRefWillBeNoop(new FontFaceSet(document));
}
class FontLoadHistogram {
public:
- FontLoadHistogram() : m_count(0), m_recorded(false) { }
+ enum Status { NoWebFonts, HadBlankText, DidNotHaveBlankText, Reported };
+ FontLoadHistogram() : m_status(NoWebFonts), m_count(0), m_recorded(false) { }
void incrementCount() { m_count++; }
+ void updateStatus(FontFace*);
void record();
private:
+ Status m_status;
int m_count;
bool m_recorded;
};
- FontFaceSet(Document*);
+ FontFaceSet(Document&);
bool hasLoadedFonts() const { return !m_loadedFonts.isEmpty() || !m_failedFonts.isEmpty(); }
- void queueDoneEvent(FontFace*);
+ bool inActiveDocumentContext() const;
+ void forEachInternal(PassOwnPtr<FontFaceSetForEachCallback>, ScriptValue* thisArg) const;
+ void addToLoadingFonts(PassRefPtrWillBeRawPtr<FontFace>);
+ void removeFromLoadingFonts(PassRefPtrWillBeRawPtr<FontFace>);
void fireLoadingEvent();
void fireDoneEventIfPossible();
bool resolveFontStyle(const String&, Font&);
void handlePendingEventsAndPromisesSoon();
void handlePendingEventsAndPromises();
+ const ListHashSet<RefPtrWillBeMember<FontFace> >& cssConnectedFontFaceList() const;
+ bool isCSSConnectedFontFace(FontFace*) const;
- unsigned m_loadingCount;
+ WillBeHeapHashSet<RefPtrWillBeMember<FontFace> > m_loadingFonts;
bool m_shouldFireLoadingEvent;
Vector<OwnPtr<FontsReadyPromiseResolver> > m_readyResolvers;
FontFaceArray m_loadedFonts;
FontFaceArray m_failedFonts;
+ // FIXME: Oilpan: replace with a HeapListHashSet or HeapLinkedHashSet.
+ ListHashSet<RefPtrWillBeMember<FontFace> > m_nonCSSConnectedFaces;
AsyncMethodRunner<FontFaceSet> m_asyncRunner;
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFaceSet.idl b/chromium/third_party/WebKit/Source/core/css/FontFaceSet.idl
index 643c335b562..10bc2f71838 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontFaceSet.idl
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceSet.idl
@@ -32,7 +32,7 @@ enum FontFaceSetLoadStatus { "loading", "loaded" };
[
ActiveDOMObject,
- GenerateVisitDOMWrapper=document,
+ SetWrapperReferenceFrom=document,
NoInterfaceObject,
RuntimeEnabled=FontLoadEvents,
] interface FontFaceSet : EventTarget {
@@ -41,10 +41,16 @@ enum FontFaceSetLoadStatus { "loading", "loaded" };
attribute EventHandler onloadingdone;
attribute EventHandler onloadingerror;
- [RaisesException] sequence<FontFace> match(DOMString font, [Default=NullString] optional DOMString text);
- [RaisesException] boolean check(DOMString font, [Default=NullString] optional DOMString text);
- [RaisesException] Promise load(DOMString font, [Default=NullString] optional DOMString text);
- Promise ready();
+ [RaisesException] boolean check(DOMString font, optional DOMString text = null);
+ [CallWith=ScriptState] Promise load(DOMString font, optional DOMString text = null);
+ [MeasureAs=FontFaceSetReady, CallWith=ScriptState] Promise ready();
+ [RaisesException] void add(FontFace fontFace);
+ void clear();
+ [RaisesException, ImplementedAs=remove] boolean delete(FontFace fontFace);
+ void forEach(FontFaceSetForEachCallback callback, optional any thisArg);
+ [RaisesException] boolean has(FontFace fontFace);
+
+ readonly attribute unsigned long size;
readonly attribute FontFaceSetLoadStatus status;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.h b/chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.h
new file mode 100644
index 00000000000..8550e24bbaf
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2013 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
+ * DAMAGE.
+ */
+
+#ifndef FontFaceSetForEachCallback_h
+#define FontFaceSetForEachCallback_h
+
+#include "bindings/v8/ScriptValue.h"
+
+namespace WebCore {
+
+class FontFace;
+class FontFaceSet;
+
+class FontFaceSetForEachCallback {
+public:
+ virtual ~FontFaceSetForEachCallback() { }
+ virtual bool handleItem(ScriptValue thisValue, FontFace*, FontFace*, FontFaceSet*) = 0;
+ virtual bool handleItem(FontFace*, FontFace*, FontFaceSet*) = 0;
+};
+
+} // namespace WebCore
+
+#endif // FontFaceSetForEachCallback_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.idl b/chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.idl
index 3c88025beb9..6b9fdab7731 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMap.idl
+++ b/chromium/third_party/WebKit/Source/core/css/FontFaceSetForEachCallback.idl
@@ -11,6 +11,9 @@
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@@ -25,12 +28,7 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-interface CSSVariablesMap {
- readonly attribute unsigned long size;
- DOMString get(DOMString name);
- boolean has(DOMString name);
- [RaisesException] void set(DOMString name, DOMString value);
- [ImplementedAs=remove] boolean delete(DOMString name);
- [RaisesException] void clear();
- void forEach(CSSVariablesMapForEachCallback callback, optional any thisArg);
+callback interface FontFaceSetForEachCallback {
+ [CallWith=ThisValue] boolean handleItem(FontFace fontFace, FontFace fontFaceAgain, FontFaceSet set);
+ boolean handleItem(FontFace fontFace, FontFace fontFaceAgain, FontFaceSet set);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/FontLoader.cpp b/chromium/third_party/WebKit/Source/core/css/FontLoader.cpp
new file mode 100644
index 00000000000..189c37cf93c
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/FontLoader.cpp
@@ -0,0 +1,95 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/FontLoader.h"
+
+#include "core/css/CSSFontSelector.h"
+#include "core/fetch/FontResource.h"
+#include "core/fetch/ResourceFetcher.h"
+
+namespace WebCore {
+
+FontLoader::FontLoader(CSSFontSelector* fontSelector, ResourceFetcher* resourceFetcher)
+ : m_beginLoadingTimer(this, &FontLoader::beginLoadTimerFired)
+ , m_fontSelector(fontSelector)
+ , m_resourceFetcher(resourceFetcher)
+{
+}
+
+FontLoader::~FontLoader()
+{
+#if ENABLE(OILPAN)
+ if (!m_resourceFetcher) {
+ ASSERT(m_fontsToBeginLoading.isEmpty());
+ return;
+ }
+ m_beginLoadingTimer.stop();
+
+ // When the m_fontsToBeginLoading vector is destroyed it will decrement the
+ // request counts on the ResourceFetcher for all the fonts that were pending
+ // at the time the FontLoader dies.
+#endif
+}
+
+void FontLoader::addFontToBeginLoading(FontResource* fontResource)
+{
+ if (!m_resourceFetcher || !fontResource->stillNeedsLoad())
+ return;
+
+ m_fontsToBeginLoading.append(
+ std::make_pair(fontResource, ResourceLoader::RequestCountTracker(m_resourceFetcher, fontResource)));
+ if (!m_beginLoadingTimer.isActive())
+ m_beginLoadingTimer.startOneShot(0, FROM_HERE);
+}
+
+void FontLoader::beginLoadTimerFired(Timer<WebCore::FontLoader>*)
+{
+ loadPendingFonts();
+}
+
+void FontLoader::loadPendingFonts()
+{
+ ASSERT(m_resourceFetcher);
+
+ FontsToLoadVector fontsToBeginLoading;
+ fontsToBeginLoading.swap(m_fontsToBeginLoading);
+ for (FontsToLoadVector::iterator it = fontsToBeginLoading.begin(); it != fontsToBeginLoading.end(); ++it) {
+ FontResource* fontResource = it->first.get();
+ fontResource->beginLoadIfNeeded(m_resourceFetcher);
+ }
+
+ // When the local fontsToBeginLoading vector goes out of scope it will
+ // decrement the request counts on the ResourceFetcher for all the fonts
+ // that were just loaded.
+}
+
+void FontLoader::fontFaceInvalidated()
+{
+ if (m_fontSelector)
+ m_fontSelector->fontFaceInvalidated();
+}
+
+#if !ENABLE(OILPAN)
+void FontLoader::clearResourceFetcherAndFontSelector()
+{
+ if (!m_resourceFetcher) {
+ ASSERT(m_fontsToBeginLoading.isEmpty());
+ return;
+ }
+
+ m_beginLoadingTimer.stop();
+ m_fontsToBeginLoading.clear();
+ m_resourceFetcher = nullptr;
+ m_fontSelector = nullptr;
+}
+#endif
+
+void FontLoader::trace(Visitor* visitor)
+{
+ visitor->trace(m_resourceFetcher);
+ visitor->trace(m_fontSelector);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/FontLoader.h b/chromium/third_party/WebKit/Source/core/css/FontLoader.h
new file mode 100644
index 00000000000..92f37275730
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/FontLoader.h
@@ -0,0 +1,51 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef FontLoader_h
+#define FontLoader_h
+
+#include "core/fetch/ResourceLoader.h"
+#include "core/fetch/ResourcePtr.h"
+#include "platform/Timer.h"
+#include "platform/heap/Handle.h"
+#include "wtf/Vector.h"
+
+namespace WebCore {
+
+class CSSFontSelector;
+class FontResource;
+
+class FontLoader : public RefCountedWillBeGarbageCollectedFinalized<FontLoader> {
+public:
+ static PassRefPtrWillBeRawPtr<FontLoader> create(CSSFontSelector* fontSelector, ResourceFetcher* fetcher)
+ {
+ return adoptRefWillBeNoop(new FontLoader(fontSelector, fetcher));
+ }
+ ~FontLoader();
+
+ void addFontToBeginLoading(FontResource*);
+ void loadPendingFonts();
+ void fontFaceInvalidated();
+
+#if !ENABLE(OILPAN)
+ void clearResourceFetcherAndFontSelector();
+#endif
+
+ void trace(Visitor*);
+
+private:
+ FontLoader(CSSFontSelector*, ResourceFetcher*);
+ void beginLoadTimerFired(Timer<FontLoader>*);
+
+ Timer<FontLoader> m_beginLoadingTimer;
+
+ typedef Vector<std::pair<ResourcePtr<FontResource>, ResourceLoader::RequestCountTracker> > FontsToLoadVector;
+ FontsToLoadVector m_fontsToBeginLoading;
+ RawPtrWillBeMember<CSSFontSelector> m_fontSelector;
+ RawPtrWillBeMember<ResourceFetcher> m_resourceFetcher;
+};
+
+} // namespace WebCore
+
+#endif // FontLoader_h
diff --git a/chromium/third_party/WebKit/Source/core/css/FontSize.cpp b/chromium/third_party/WebKit/Source/core/css/FontSize.cpp
index 4b545c458a8..6c1b53c5282 100644
--- a/chromium/third_party/WebKit/Source/core/css/FontSize.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/FontSize.cpp
@@ -29,7 +29,7 @@
#include "config.h"
#include "core/css/FontSize.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
#include "core/dom/Document.h"
#include "core/frame/Settings.h"
diff --git a/chromium/third_party/WebKit/Source/core/css/HashTools.h b/chromium/third_party/WebKit/Source/core/css/HashTools.h
index c86f62d3343..309ab164218 100644
--- a/chromium/third_party/WebKit/Source/core/css/HashTools.h
+++ b/chromium/third_party/WebKit/Source/core/css/HashTools.h
@@ -32,8 +32,8 @@ struct Value {
int id;
};
-const Property* findProperty(register const char* str, register unsigned int len);
-const Value* findValue(register const char* str, register unsigned int len);
+const Property* findProperty(register const char* str, register unsigned len);
+const Value* findValue(register const char* str, register unsigned len);
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.cpp b/chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.cpp
deleted file mode 100644
index 5a99c072010..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.cpp
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
- * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com)
- * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com)
- * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved.
- * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org>
- * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org>
- * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
- * Copyright (c) 2011, Code Aurora Forum. All rights reserved.
- * Copyright (C) Research In Motion Limited 2011. All rights reserved.
- * Copyright (C) 2012 Google Inc. All rights reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#include "config.h"
-#include "core/css/InspectorCSSOMWrappers.h"
-
-#include "core/css/CSSDefaultStyleSheets.h"
-#include "core/css/CSSImportRule.h"
-#include "core/css/CSSMediaRule.h"
-#include "core/css/CSSRegionRule.h"
-#include "core/css/CSSRule.h"
-#include "core/css/CSSStyleRule.h"
-#include "core/css/CSSStyleSheet.h"
-#include "core/css/CSSSupportsRule.h"
-#include "core/css/StyleSheetContents.h"
-#include "core/dom/StyleEngine.h"
-
-namespace WebCore {
-
-void InspectorCSSOMWrappers::collectFromStyleSheetIfNeeded(CSSStyleSheet* styleSheet)
-{
- if (!m_styleRuleToCSSOMWrapperMap.isEmpty())
- collect(styleSheet);
-}
-
-void InspectorCSSOMWrappers::reset()
-{
- m_styleRuleToCSSOMWrapperMap.clear();
- m_styleSheetCSSOMWrapperSet.clear();
-}
-
-template <class ListType>
-void InspectorCSSOMWrappers::collect(ListType* listType)
-{
- if (!listType)
- return;
- unsigned size = listType->length();
- for (unsigned i = 0; i < size; ++i) {
- CSSRule* cssRule = listType->item(i);
- switch (cssRule->type()) {
- case CSSRule::IMPORT_RULE:
- collect(toCSSImportRule(cssRule)->styleSheet());
- break;
- case CSSRule::MEDIA_RULE:
- collect(toCSSMediaRule(cssRule));
- break;
- case CSSRule::SUPPORTS_RULE:
- collect(toCSSSupportsRule(cssRule));
- break;
- case CSSRule::WEBKIT_REGION_RULE:
- collect(toCSSRegionRule(cssRule));
- break;
- case CSSRule::STYLE_RULE:
- m_styleRuleToCSSOMWrapperMap.add(toCSSStyleRule(cssRule)->styleRule(), toCSSStyleRule(cssRule));
- break;
- default:
- break;
- }
- }
-}
-
-void InspectorCSSOMWrappers::collectFromStyleSheetContents(HashSet<RefPtr<CSSStyleSheet> >& sheetWrapperSet, StyleSheetContents* styleSheet)
-{
- if (!styleSheet)
- return;
- RefPtr<CSSStyleSheet> styleSheetWrapper = CSSStyleSheet::create(styleSheet);
- sheetWrapperSet.add(styleSheetWrapper);
- collect(styleSheetWrapper.get());
-}
-
-void InspectorCSSOMWrappers::collectFromStyleSheets(const Vector<RefPtr<CSSStyleSheet> >& sheets)
-{
- for (unsigned i = 0; i < sheets.size(); ++i)
- collect(sheets[i].get());
-}
-
-void InspectorCSSOMWrappers::collectFromStyleEngine(StyleEngine* styleSheetCollection)
-{
- Vector<const Vector<RefPtr<CSSStyleSheet> >*> activeAuthorStyleSheets;
- styleSheetCollection->getActiveAuthorStyleSheets(activeAuthorStyleSheets);
- for (size_t i = 0; i < activeAuthorStyleSheets.size(); ++i)
- collectFromStyleSheets(*activeAuthorStyleSheets[i]);
-}
-
-CSSStyleRule* InspectorCSSOMWrappers::getWrapperForRuleInSheets(StyleRule* rule, StyleEngine* styleSheetCollection)
-{
- if (m_styleRuleToCSSOMWrapperMap.isEmpty()) {
- collectFromStyleSheetContents(m_styleSheetCSSOMWrapperSet, CSSDefaultStyleSheets::defaultStyleSheet);
- collectFromStyleSheetContents(m_styleSheetCSSOMWrapperSet, CSSDefaultStyleSheets::viewportStyleSheet);
- collectFromStyleSheetContents(m_styleSheetCSSOMWrapperSet, CSSDefaultStyleSheets::quirksStyleSheet);
- collectFromStyleSheetContents(m_styleSheetCSSOMWrapperSet, CSSDefaultStyleSheets::svgStyleSheet);
- collectFromStyleSheetContents(m_styleSheetCSSOMWrapperSet, CSSDefaultStyleSheets::mediaControlsStyleSheet);
- collectFromStyleSheetContents(m_styleSheetCSSOMWrapperSet, CSSDefaultStyleSheets::fullscreenStyleSheet);
-
- collectFromStyleEngine(styleSheetCollection);
- }
- return m_styleRuleToCSSOMWrapperMap.get(rule);
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.h b/chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.h
deleted file mode 100644
index fda87899fe7..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/InspectorCSSOMWrappers.h
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
- * Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- *
- */
-
-#ifndef InspectorCSSOMWrappers_h
-#define InspectorCSSOMWrappers_h
-
-#include "wtf/Forward.h"
-#include "wtf/HashMap.h"
-#include "wtf/HashSet.h"
-#include "wtf/Vector.h"
-
-namespace WebCore {
-
-class CSSStyleRule;
-class CSSStyleSheet;
-class StyleRule;
-class StyleEngine;
-class StyleSheetContents;
-
-class InspectorCSSOMWrappers {
-public:
- // WARNING. This will construct CSSOM wrappers for all style rules and cache them in a map for significant memory cost.
- // It is here to support inspector. Don't use for any regular engine functions.
- CSSStyleRule* getWrapperForRuleInSheets(StyleRule*, StyleEngine*);
- void collectFromStyleSheetIfNeeded(CSSStyleSheet*);
- void reset();
-
-private:
- template <class ListType>
- void collect(ListType*);
-
- void collectFromStyleSheetContents(HashSet<RefPtr<CSSStyleSheet> >& sheetWrapperSet, StyleSheetContents*);
- void collectFromStyleSheets(const Vector<RefPtr<CSSStyleSheet> >&);
- void collectFromStyleEngine(StyleEngine*);
-
- HashMap<StyleRule*, RefPtr<CSSStyleRule> > m_styleRuleToCSSOMWrapperMap;
- HashSet<RefPtr<CSSStyleSheet> > m_styleSheetCSSOMWrapperSet;
-};
-
-} // namespace WebCore
-
-#endif // InspectorCSSOMWrappers_h
diff --git a/chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.cpp b/chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.cpp
new file mode 100644
index 00000000000..a920bdfd0bc
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.cpp
@@ -0,0 +1,36 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/LocalFontFaceSource.h"
+
+#include "platform/fonts/FontCache.h"
+#include "platform/fonts/FontDescription.h"
+#include "platform/fonts/SimpleFontData.h"
+#include "public/platform/Platform.h"
+
+namespace WebCore {
+
+bool LocalFontFaceSource::isLocalFontAvailable(const FontDescription& fontDescription)
+{
+ return FontCache::fontCache()->isPlatformFontAvailable(fontDescription, m_fontName);
+}
+
+PassRefPtr<SimpleFontData> LocalFontFaceSource::createFontData(const FontDescription& fontDescription)
+{
+ // We don't want to check alternate font family names here, so pass true as the checkingAlternateName parameter.
+ RefPtr<SimpleFontData> fontData = FontCache::fontCache()->getFontData(fontDescription, m_fontName, true);
+ m_histograms.record(fontData);
+ return fontData.release();
+}
+
+void LocalFontFaceSource::LocalFontHistograms::record(bool loadSuccess)
+{
+ if (m_reported)
+ return;
+ m_reported = true;
+ blink::Platform::current()->histogramEnumeration("WebFont.LocalFontUsed", loadSuccess ? 1 : 0, 2);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.h b/chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.h
new file mode 100644
index 00000000000..3036e4f9723
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/LocalFontFaceSource.h
@@ -0,0 +1,36 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef LocalFontFaceSource_h
+#define LocalFontFaceSource_h
+
+#include "core/css/CSSFontFaceSource.h"
+#include "wtf/text/AtomicString.h"
+
+namespace WebCore {
+
+class LocalFontFaceSource : public CSSFontFaceSource {
+public:
+ LocalFontFaceSource(const String& fontName) : m_fontName(fontName) { }
+ virtual bool isLocal() const { return true; }
+ virtual bool isLocalFontAvailable(const FontDescription&) OVERRIDE;
+
+private:
+ virtual PassRefPtr<SimpleFontData> createFontData(const FontDescription&) OVERRIDE;
+
+ class LocalFontHistograms {
+ public:
+ LocalFontHistograms() : m_reported(false) { }
+ void record(bool loadSuccess);
+ private:
+ bool m_reported;
+ };
+
+ AtomicString m_fontName;
+ LocalFontHistograms m_histograms;
+};
+
+} // namespace WebCore
+
+#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.h b/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.h
deleted file mode 100644
index b249625420a..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.h
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * Copyright (C) 2005, 2013 Apple Inc. All rights reserved.
- * Copyright (C) 2013 Intel Corporation. All rights reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- *
- */
-#ifndef MediaFeatureNames_h
-#define MediaFeatureNames_h
-
-#include "wtf/text/AtomicString.h"
-
-namespace WebCore {
-namespace MediaFeatureNames {
-
-#define CSS_MEDIAQUERY_NAMES_FOR_EACH_MEDIAFEATURE(macro) \
- macro(deprecatedTransition, "-webkit-transition") \
- macro(color, "color") \
- macro(colorIndex, "color-index") \
- macro(grid, "grid") \
- macro(monochrome, "monochrome") \
- macro(height, "height") \
- macro(hover, "hover") \
- macro(width, "width") \
- macro(orientation, "orientation") \
- macro(aspectRatio, "aspect-ratio") \
- macro(deviceAspectRatio, "device-aspect-ratio") \
- macro(devicePixelRatio, "-webkit-device-pixel-ratio") \
- macro(deviceHeight, "device-height") \
- macro(deviceWidth, "device-width") \
- macro(maxColor, "max-color") \
- macro(maxColorIndex, "max-color-index") \
- macro(maxAspectRatio, "max-aspect-ratio") \
- macro(maxDeviceAspectRatio, "max-device-aspect-ratio") \
- macro(maxDevicePixelRatio, "-webkit-max-device-pixel-ratio") \
- macro(maxDeviceHeight, "max-device-height") \
- macro(maxDeviceWidth, "max-device-width") \
- macro(maxHeight, "max-height") \
- macro(maxMonochrome, "max-monochrome") \
- macro(maxWidth, "max-width") \
- macro(maxResolution, "max-resolution") \
- macro(minColor, "min-color") \
- macro(minColorIndex, "min-color-index") \
- macro(minAspectRatio, "min-aspect-ratio") \
- macro(minDeviceAspectRatio, "min-device-aspect-ratio") \
- macro(minDevicePixelRatio, "-webkit-min-device-pixel-ratio") \
- macro(minDeviceHeight, "min-device-height") \
- macro(minDeviceWidth, "min-device-width") \
- macro(minHeight, "min-height") \
- macro(minMonochrome, "min-monochrome") \
- macro(minWidth, "min-width") \
- macro(minResolution, "min-resolution") \
- macro(pointer, "pointer") \
- macro(resolution, "resolution") \
- macro(transform2d, "-webkit-transform-2d") \
- macro(transform3d, "-webkit-transform-3d") \
- macro(scan, "scan") \
- macro(animation, "-webkit-animation") \
- macro(viewMode, "-webkit-view-mode")
-
-// end of macro
-
-#ifndef CSS_MEDIAQUERY_NAMES_HIDE_GLOBALS
-#define CSS_MEDIAQUERY_NAMES_DECLARE(name, str) extern const AtomicString name##MediaFeature;
-CSS_MEDIAQUERY_NAMES_FOR_EACH_MEDIAFEATURE(CSS_MEDIAQUERY_NAMES_DECLARE)
-#undef CSS_MEDIAQUERY_NAMES_DECLARE
-#endif
-
- void init();
-
-} // namespace MediaFeatureNames
-} // namespace WebCore
-
-#endif // MediaFeatureNames_h
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.in b/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.in
new file mode 100644
index 00000000000..f94bd9bdadd
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaFeatureNames.in
@@ -0,0 +1,42 @@
+namespace="MediaFeature"
+export=""
+
+color
+color-index
+grid
+monochrome
+height
+hover
+width
+orientation
+aspect-ratio
+device-aspect-ratio
+-webkit-device-pixel-ratio
+device-height
+device-width
+max-color
+max-color-index
+max-aspect-ratio
+max-device-aspect-ratio
+-webkit-max-device-pixel-ratio
+max-device-height
+max-device-width
+max-height
+max-monochrome
+max-width
+max-resolution
+min-color
+min-color-index
+min-aspect-ratio
+min-device-aspect-ratio
+-webkit-min-device-pixel-ratio
+min-device-height
+min-device-width
+min-height
+min-monochrome
+min-width
+min-resolution
+pointer
+resolution
+-webkit-transform-3d
+scan
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaList.cpp b/chromium/third_party/WebKit/Source/core/css/MediaList.cpp
index 4a4442fb83d..69fe9145188 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaList.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaList.cpp
@@ -21,13 +21,14 @@
#include "core/css/MediaList.h"
#include "bindings/v8/ExceptionState.h"
-#include "core/css/CSSParser.h"
+#include "core/MediaFeatureNames.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSStyleSheet.h"
-#include "core/css/MediaFeatureNames.h"
#include "core/css/MediaQuery.h"
#include "core/css/MediaQueryExp.h"
+#include "core/css/parser/MediaQueryParser.h"
#include "core/dom/Document.h"
-#include "core/frame/DOMWindow.h"
+#include "core/frame/LocalDOMWindow.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
@@ -57,29 +58,37 @@ MediaQuerySet::MediaQuerySet()
}
MediaQuerySet::MediaQuerySet(const MediaQuerySet& o)
- : RefCounted<MediaQuerySet>()
- , m_queries(o.m_queries.size())
+ : m_queries(o.m_queries.size())
{
for (unsigned i = 0; i < m_queries.size(); ++i)
m_queries[i] = o.m_queries[i]->copy();
}
-MediaQuerySet::~MediaQuerySet()
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(MediaQuerySet)
+
+PassRefPtrWillBeRawPtr<MediaQuerySet> MediaQuerySet::create(const String& mediaString)
{
+ if (mediaString.isEmpty())
+ return MediaQuerySet::create();
+
+ if (RuntimeEnabledFeatures::mediaQueryParserEnabled())
+ return MediaQueryParser::parseMediaQuerySet(mediaString);
+
+ BisonCSSParser parser(strictCSSParserContext());
+ return parser.parseMediaQueryList(mediaString);
}
-PassRefPtr<MediaQuerySet> MediaQuerySet::create(const String& mediaString)
+PassRefPtrWillBeRawPtr<MediaQuerySet> MediaQuerySet::createOffMainThread(const String& mediaString)
{
if (mediaString.isEmpty())
return MediaQuerySet::create();
- CSSParser parser(HTMLStandardMode);
- return parser.parseMediaQueryList(mediaString);
+ return MediaQueryParser::parseMediaQuerySet(mediaString);
}
bool MediaQuerySet::set(const String& mediaString)
{
- RefPtr<MediaQuerySet> result = create(mediaString);
+ RefPtrWillBeRawPtr<MediaQuerySet> result = create(mediaString);
m_queries.swap(result->m_queries);
return true;
}
@@ -89,13 +98,13 @@ bool MediaQuerySet::add(const String& queryString)
// To "parse a media query" for a given string means to follow "the parse
// a media query list" steps and return "null" if more than one media query
// is returned, or else the returned media query.
- RefPtr<MediaQuerySet> result = create(queryString);
+ RefPtrWillBeRawPtr<MediaQuerySet> result = create(queryString);
// Only continue if exactly one media query is found, as described above.
if (result->m_queries.size() != 1)
return true;
- OwnPtr<MediaQuery> newQuery = result->m_queries[0].release();
+ OwnPtrWillBeRawPtr<MediaQuery> newQuery = result->m_queries[0].release();
ASSERT(newQuery);
// If comparing with any of the media queries in the collection of media
@@ -115,13 +124,13 @@ bool MediaQuerySet::remove(const String& queryStringToRemove)
// To "parse a media query" for a given string means to follow "the parse
// a media query list" steps and return "null" if more than one media query
// is returned, or else the returned media query.
- RefPtr<MediaQuerySet> result = create(queryStringToRemove);
+ RefPtrWillBeRawPtr<MediaQuerySet> result = create(queryStringToRemove);
// Only continue if exactly one media query is found, as described above.
if (result->m_queries.size() != 1)
return true;
- OwnPtr<MediaQuery> newQuery = result->m_queries[0].release();
+ OwnPtrWillBeRawPtr<MediaQuery> newQuery = result->m_queries[0].release();
ASSERT(newQuery);
// Remove any media query from the collection of media queries for which
@@ -139,7 +148,7 @@ bool MediaQuerySet::remove(const String& queryStringToRemove)
return found;
}
-void MediaQuerySet::addMediaQuery(PassOwnPtr<MediaQuery> mediaQuery)
+void MediaQuerySet::addMediaQuery(PassOwnPtrWillBeRawPtr<MediaQuery> mediaQuery)
{
m_queries.append(mediaQuery);
}
@@ -159,16 +168,25 @@ String MediaQuerySet::mediaText() const
return text.toString();
}
+void MediaQuerySet::trace(Visitor* visitor)
+{
+ // We don't support tracing of vectors of OwnPtrs (ie. OwnPtr<Vector<OwnPtr<MediaQuery> > >).
+ // Since this is a transitional object we are just ifdef'ing it out when oilpan is not enabled.
+#if ENABLE(OILPAN)
+ visitor->trace(m_queries);
+#endif
+}
+
MediaList::MediaList(MediaQuerySet* mediaQueries, CSSStyleSheet* parentSheet)
: m_mediaQueries(mediaQueries)
, m_parentStyleSheet(parentSheet)
- , m_parentRule(0)
+ , m_parentRule(nullptr)
{
}
MediaList::MediaList(MediaQuerySet* mediaQueries, CSSRule* parentRule)
: m_mediaQueries(mediaQueries)
- , m_parentStyleSheet(0)
+ , m_parentStyleSheet(nullptr)
, m_parentRule(parentRule)
{
}
@@ -189,7 +207,7 @@ void MediaList::setMediaText(const String& value)
String MediaList::item(unsigned index) const
{
- const Vector<OwnPtr<MediaQuery> >& queries = m_mediaQueries->queryVector();
+ const WillBeHeapVector<OwnPtrWillBeMember<MediaQuery> >& queries = m_mediaQueries->queryVector();
if (index < queries.size())
return queries[index]->cssText();
return String();
@@ -201,7 +219,7 @@ void MediaList::deleteMedium(const String& medium, ExceptionState& exceptionStat
bool success = m_mediaQueries->remove(medium);
if (!success) {
- exceptionState.throwUninformativeAndGenericDOMException(NotFoundError);
+ exceptionState.throwDOMException(NotFoundError, "Failed to delete '" + medium + "'.");
return;
}
if (m_parentStyleSheet)
@@ -214,7 +232,7 @@ void MediaList::appendMedium(const String& medium, ExceptionState& exceptionStat
bool success = m_mediaQueries->add(medium);
if (!success) {
- exceptionState.throwUninformativeAndGenericDOMException(InvalidCharacterError);
+ exceptionState.throwDOMException(InvalidCharacterError, "The value provided ('" + medium + "') is not a valid medium.");
return;
}
@@ -228,31 +246,37 @@ void MediaList::reattach(MediaQuerySet* mediaQueries)
m_mediaQueries = mediaQueries;
}
-static void addResolutionWarningMessageToConsole(Document* document, const String& serializedExpression, const CSSPrimitiveValue* value)
+void MediaList::trace(Visitor* visitor)
+{
+ visitor->trace(m_mediaQueries);
+ visitor->trace(m_parentStyleSheet);
+ visitor->trace(m_parentRule);
+}
+
+static void addResolutionWarningMessageToConsole(Document* document, const String& serializedExpression, CSSPrimitiveValue::UnitType type)
{
ASSERT(document);
- ASSERT(value);
- DEFINE_STATIC_LOCAL(String, mediaQueryMessage, ("Consider using 'dppx' units instead of '%replacementUnits%', as in CSS '%replacementUnits%' means dots-per-CSS-%lengthUnit%, not dots-per-physical-%lengthUnit%, so does not correspond to the actual '%replacementUnits%' of a screen. In media query expression: "));
+ DEFINE_STATIC_LOCAL(String, mediaQueryMessage, ("Consider using 'dppx' units, as in CSS '%replacementUnits%' means dots-per-CSS-%lengthUnit%, not dots-per-physical-%lengthUnit%, so does not correspond to the actual '%replacementUnits%' of a screen. In media query expression: "));
DEFINE_STATIC_LOCAL(String, mediaValueDPI, ("dpi"));
DEFINE_STATIC_LOCAL(String, mediaValueDPCM, ("dpcm"));
DEFINE_STATIC_LOCAL(String, lengthUnitInch, ("inch"));
DEFINE_STATIC_LOCAL(String, lengthUnitCentimeter, ("centimeter"));
- String message;
- if (value->isDotsPerInch())
- message = String(mediaQueryMessage).replace("%replacementUnits%", mediaValueDPI).replace("%lengthUnit%", lengthUnitInch);
- else if (value->isDotsPerCentimeter())
- message = String(mediaQueryMessage).replace("%replacementUnits%", mediaValueDPCM).replace("%lengthUnit%", lengthUnitCentimeter);
+ StringBuilder message;
+ if (CSSPrimitiveValue::isDotsPerInch(type))
+ message.append(String(mediaQueryMessage).replace("%replacementUnits%", mediaValueDPI).replace("%lengthUnit%", lengthUnitInch));
+ else if (CSSPrimitiveValue::isDotsPerCentimeter(type))
+ message.append(String(mediaQueryMessage).replace("%replacementUnits%", mediaValueDPCM).replace("%lengthUnit%", lengthUnitCentimeter));
else
ASSERT_NOT_REACHED();
message.append(serializedExpression);
- document->addConsoleMessage(CSSMessageSource, DebugMessageLevel, message);
+ document->addConsoleMessage(CSSMessageSource, DebugMessageLevel, message.toString());
}
-static inline bool isResolutionMediaFeature(const AtomicString& mediaFeature)
+static inline bool isResolutionMediaFeature(const String& mediaFeature)
{
return mediaFeature == MediaFeatureNames::resolutionMediaFeature
|| mediaFeature == MediaFeatureNames::maxResolutionMediaFeature
@@ -264,30 +288,36 @@ void reportMediaQueryWarningIfNeeded(Document* document, const MediaQuerySet* me
if (!mediaQuerySet || !document)
return;
- const Vector<OwnPtr<MediaQuery> >& mediaQueries = mediaQuerySet->queryVector();
+ const WillBeHeapVector<OwnPtrWillBeMember<MediaQuery> >& mediaQueries = mediaQuerySet->queryVector();
const size_t queryCount = mediaQueries.size();
if (!queryCount)
return;
+ CSSPrimitiveValue::UnitType suspiciousType = CSSPrimitiveValue::CSS_UNKNOWN;
+ bool dotsPerPixelUsed = false;
for (size_t i = 0; i < queryCount; ++i) {
const MediaQuery* query = mediaQueries[i].get();
if (equalIgnoringCase(query->mediaType(), "print"))
continue;
- const ExpressionVector& expressions = query->expressions();
+ const ExpressionHeapVector& expressions = query->expressions();
for (size_t j = 0; j < expressions.size(); ++j) {
const MediaQueryExp* expression = expressions.at(j).get();
if (isResolutionMediaFeature(expression->mediaFeature())) {
- CSSValue* cssValue = expression->value();
- if (cssValue && cssValue->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(cssValue);
- if (primitiveValue->isDotsPerInch() || primitiveValue->isDotsPerCentimeter())
- addResolutionWarningMessageToConsole(document, mediaQuerySet->mediaText(), primitiveValue);
+ MediaQueryExpValue expValue = expression->expValue();
+ if (expValue.isValue) {
+ if (CSSPrimitiveValue::isDotsPerPixel(expValue.unit))
+ dotsPerPixelUsed = true;
+ else if (CSSPrimitiveValue::isDotsPerInch(expValue.unit) || CSSPrimitiveValue::isDotsPerCentimeter(expValue.unit))
+ suspiciousType = expValue.unit;
}
}
}
}
+
+ if (suspiciousType && !dotsPerPixelUsed)
+ addResolutionWarningMessageToConsole(document, mediaQuerySet->mediaText(), suspiciousType);
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaList.h b/chromium/third_party/WebKit/Source/core/css/MediaList.h
index 80223b03421..1e32424fa54 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaList.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaList.h
@@ -22,6 +22,7 @@
#define MediaList_h
#include "core/dom/ExceptionCode.h"
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefCounted.h"
@@ -37,43 +38,46 @@ class ExceptionState;
class MediaList;
class MediaQuery;
-class MediaQuerySet : public RefCounted<MediaQuerySet> {
+class MediaQuerySet : public RefCountedWillBeGarbageCollected<MediaQuerySet> {
+ DECLARE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(MediaQuerySet);
public:
- static PassRefPtr<MediaQuerySet> create()
+ static PassRefPtrWillBeRawPtr<MediaQuerySet> create()
{
- return adoptRef(new MediaQuerySet());
+ return adoptRefWillBeNoop(new MediaQuerySet());
}
- static PassRefPtr<MediaQuerySet> create(const String& mediaString);
- ~MediaQuerySet();
+ static PassRefPtrWillBeRawPtr<MediaQuerySet> create(const String& mediaString);
+ static PassRefPtrWillBeRawPtr<MediaQuerySet> createOffMainThread(const String& mediaString);
bool set(const String&);
bool add(const String&);
bool remove(const String&);
- void addMediaQuery(PassOwnPtr<MediaQuery>);
+ void addMediaQuery(PassOwnPtrWillBeRawPtr<MediaQuery>);
- const Vector<OwnPtr<MediaQuery> >& queryVector() const { return m_queries; }
+ const WillBeHeapVector<OwnPtrWillBeMember<MediaQuery> >& queryVector() const { return m_queries; }
String mediaText() const;
- PassRefPtr<MediaQuerySet> copy() const { return adoptRef(new MediaQuerySet(*this)); }
+ PassRefPtrWillBeRawPtr<MediaQuerySet> copy() const { return adoptRefWillBeNoop(new MediaQuerySet(*this)); }
+
+ void trace(Visitor*);
private:
MediaQuerySet();
MediaQuerySet(const MediaQuerySet&);
- Vector<OwnPtr<MediaQuery> > m_queries;
+ WillBeHeapVector<OwnPtrWillBeMember<MediaQuery> > m_queries;
};
-class MediaList : public RefCounted<MediaList> {
+class MediaList : public RefCountedWillBeGarbageCollectedFinalized<MediaList> {
public:
- static PassRefPtr<MediaList> create(MediaQuerySet* mediaQueries, CSSStyleSheet* parentSheet)
+ static PassRefPtrWillBeRawPtr<MediaList> create(MediaQuerySet* mediaQueries, CSSStyleSheet* parentSheet)
{
- return adoptRef(new MediaList(mediaQueries, parentSheet));
+ return adoptRefWillBeNoop(new MediaList(mediaQueries, parentSheet));
}
- static PassRefPtr<MediaList> create(MediaQuerySet* mediaQueries, CSSRule* parentRule)
+ static PassRefPtrWillBeRawPtr<MediaList> create(MediaQuerySet* mediaQueries, CSSRule* parentRule)
{
- return adoptRef(new MediaList(mediaQueries, parentRule));
+ return adoptRefWillBeNoop(new MediaList(mediaQueries, parentRule));
}
~MediaList();
@@ -89,20 +93,28 @@ public:
// Not part of CSSOM.
CSSRule* parentRule() const { return m_parentRule; }
CSSStyleSheet* parentStyleSheet() const { return m_parentStyleSheet; }
- void clearParentStyleSheet() { ASSERT(m_parentStyleSheet); m_parentStyleSheet = 0; }
- void clearParentRule() { ASSERT(m_parentRule); m_parentRule = 0; }
+
+#if !ENABLE(OILPAN)
+ void clearParentStyleSheet() { ASSERT(m_parentStyleSheet); m_parentStyleSheet = nullptr; }
+ void clearParentRule() { ASSERT(m_parentRule); m_parentRule = nullptr; }
+#endif
+
const MediaQuerySet* queries() const { return m_mediaQueries.get(); }
void reattach(MediaQuerySet*);
+ void trace(Visitor*);
+
private:
MediaList();
MediaList(MediaQuerySet*, CSSStyleSheet* parentSheet);
MediaList(MediaQuerySet*, CSSRule* parentRule);
- RefPtr<MediaQuerySet> m_mediaQueries;
- CSSStyleSheet* m_parentStyleSheet;
- CSSRule* m_parentRule;
+ RefPtrWillBeMember<MediaQuerySet> m_mediaQueries;
+ // Cleared in ~CSSStyleSheet destructor when oilpan is not enabled.
+ RawPtrWillBeMember<CSSStyleSheet> m_parentStyleSheet;
+ // Cleared in the ~CSSMediaRule and ~CSSImportRule destructors when oilpan is not enabled.
+ RawPtrWillBeMember<CSSRule> m_parentRule;
};
// Adds message to inspector console whenever dpi or dpcm values are used for "screen" media.
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaList.idl b/chromium/third_party/WebKit/Source/core/css/MediaList.idl
index 20ef3ec8835..8db9886f3f5 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaList.idl
+++ b/chromium/third_party/WebKit/Source/core/css/MediaList.idl
@@ -25,6 +25,7 @@
// Introduced in DOM Level 2:
[
+ WillBeGarbageCollected
] interface MediaList {
[TreatNullAs=NullString, TreatReturnedNullStringAs=Null] attribute DOMString mediaText;
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQuery.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQuery.cpp
index 681ac137fa2..ab20c2145d9 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQuery.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQuery.cpp
@@ -29,7 +29,9 @@
#include "config.h"
#include "core/css/MediaQuery.h"
+#include "core/MediaTypeNames.h"
#include "core/css/MediaQueryExp.h"
+#include "core/html/parser/HTMLParserIdioms.h"
#include "wtf/NonCopyingSort.h"
#include "wtf/text/StringBuilder.h"
@@ -55,7 +57,7 @@ String MediaQuery::serialize() const
return result.toString();
}
- if (m_mediaType != "all" || m_restrictor != None) {
+ if (m_mediaType != MediaTypeNames::all || m_restrictor != None) {
result.append(m_mediaType);
result.append(" and ");
}
@@ -68,18 +70,23 @@ String MediaQuery::serialize() const
return result.toString();
}
-static bool expressionCompare(const OwnPtr<MediaQueryExp>& a, const OwnPtr<MediaQueryExp>& b)
+static bool expressionCompare(const OwnPtrWillBeMember<MediaQueryExp>& a, const OwnPtrWillBeMember<MediaQueryExp>& b)
{
return codePointCompare(a->serialize(), b->serialize()) < 0;
}
-MediaQuery::MediaQuery(Restrictor r, const AtomicString& mediaType, PassOwnPtr<ExpressionVector> expressions)
+PassOwnPtrWillBeRawPtr<MediaQuery> MediaQuery::createNotAll()
+{
+ return adoptPtrWillBeNoop(new MediaQuery(MediaQuery::Not, MediaTypeNames::all, nullptr));
+}
+
+MediaQuery::MediaQuery(Restrictor r, const String& mediaType, PassOwnPtrWillBeRawPtr<ExpressionHeapVector> expressions)
: m_restrictor(r)
- , m_mediaType(mediaType.lower())
+ , m_mediaType(attemptStaticStringCreation(mediaType.lower()))
, m_expressions(expressions)
{
if (!m_expressions) {
- m_expressions = adoptPtr(new ExpressionVector);
+ m_expressions = adoptPtrWillBeNoop(new ExpressionHeapVector);
return;
}
@@ -100,7 +107,7 @@ MediaQuery::MediaQuery(Restrictor r, const AtomicString& mediaType, PassOwnPtr<E
MediaQuery::MediaQuery(const MediaQuery& o)
: m_restrictor(o.m_restrictor)
, m_mediaType(o.m_mediaType)
- , m_expressions(adoptPtr(new ExpressionVector(o.m_expressions->size())))
+ , m_expressions(adoptPtrWillBeNoop(new ExpressionHeapVector(o.m_expressions->size())))
, m_serializationCache(o.m_serializationCache)
{
for (unsigned i = 0; i < m_expressions->size(); ++i)
@@ -126,4 +133,13 @@ String MediaQuery::cssText() const
return m_serializationCache;
}
+void MediaQuery::trace(Visitor* visitor)
+{
+ // We don't support tracing of vectors of OwnPtrs (ie. OwnPtr<Vector<OwnPtr<MediaQuery> > >).
+ // Since this is a transitional object we are just ifdef'ing it out when oilpan is not enabled.
+#if ENABLE(OILPAN)
+ visitor->trace(m_expressions);
+#endif
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQuery.h b/chromium/third_party/WebKit/Source/core/css/MediaQuery.h
index fa5463ee7df..6a5197578a7 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQuery.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQuery.h
@@ -29,6 +29,7 @@
#ifndef MediaQuery_h
#define MediaQuery_h
+#include "platform/heap/Handle.h"
#include "wtf/PassOwnPtr.h"
#include "wtf/Vector.h"
#include "wtf/text/StringHash.h"
@@ -37,32 +38,36 @@
namespace WebCore {
class MediaQueryExp;
-typedef Vector<OwnPtr<MediaQueryExp> > ExpressionVector;
+typedef WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > ExpressionHeapVector;
-class MediaQuery {
- WTF_MAKE_FAST_ALLOCATED;
+class MediaQuery : public NoBaseWillBeGarbageCollectedFinalized<MediaQuery> {
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
enum Restrictor {
Only, Not, None
};
- MediaQuery(Restrictor, const AtomicString& mediaType, PassOwnPtr<ExpressionVector> exprs);
+ static PassOwnPtrWillBeRawPtr<MediaQuery> createNotAll();
+
+ MediaQuery(Restrictor, const String& mediaType, PassOwnPtrWillBeRawPtr<ExpressionHeapVector> exprs);
~MediaQuery();
Restrictor restrictor() const { return m_restrictor; }
- const ExpressionVector& expressions() const { return *m_expressions; }
- const AtomicString& mediaType() const { return m_mediaType; }
+ const ExpressionHeapVector& expressions() const { return *m_expressions; }
+ const String& mediaType() const { return m_mediaType; }
bool operator==(const MediaQuery& other) const;
String cssText() const;
- PassOwnPtr<MediaQuery> copy() const { return adoptPtr(new MediaQuery(*this)); }
+ PassOwnPtrWillBeRawPtr<MediaQuery> copy() const { return adoptPtrWillBeNoop(new MediaQuery(*this)); }
+
+ void trace(Visitor*);
private:
MediaQuery(const MediaQuery&);
Restrictor m_restrictor;
- AtomicString m_mediaType;
- OwnPtr<ExpressionVector> m_expressions;
+ String m_mediaType;
+ OwnPtrWillBeMember<ExpressionHeapVector> m_expressions;
String m_serializationCache;
String serialize() const;
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.cpp
index 5673e6e98fc..51a48409071 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.cpp
@@ -30,23 +30,26 @@
#include "config.h"
#include "core/css/MediaQueryEvaluator.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
+#include "core/MediaFeatureNames.h"
+#include "core/MediaFeatures.h"
+#include "core/MediaTypeNames.h"
#include "core/css/CSSAspectRatioValue.h"
#include "core/css/CSSHelper.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSToLengthConversionData.h"
-#include "core/css/MediaFeatureNames.h"
#include "core/css/MediaList.h"
#include "core/css/MediaQuery.h"
+#include "core/css/MediaValuesDynamic.h"
#include "core/css/resolver/MediaQueryResult.h"
#include "core/dom/NodeRenderStyle.h"
-#include "core/inspector/InspectorInstrumentation.h"
-#include "core/frame/Frame.h"
+#include "core/frame/FrameHost.h"
#include "core/frame/FrameView.h"
-#include "core/page/Page.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
-#include "core/rendering/RenderLayerCompositor.h"
+#include "core/inspector/InspectorInstrumentation.h"
#include "core/rendering/RenderView.h"
+#include "core/rendering/compositing/RenderLayerCompositor.h"
#include "core/rendering/style/RenderStyle.h"
#include "platform/PlatformScreen.h"
#include "platform/geometry/FloatRect.h"
@@ -58,38 +61,38 @@ using namespace MediaFeatureNames;
enum MediaFeaturePrefix { MinPrefix, MaxPrefix, NoPrefix };
-typedef bool (*EvalFunc)(CSSValue*, RenderStyle*, Frame*, MediaFeaturePrefix);
+typedef bool (*EvalFunc)(const MediaQueryExpValue&, MediaFeaturePrefix, const MediaValues&);
typedef HashMap<StringImpl*, EvalFunc> FunctionMap;
static FunctionMap* gFunctionMap;
MediaQueryEvaluator::MediaQueryEvaluator(bool mediaFeatureResult)
- : m_frame(0)
- , m_style(0)
- , m_expResult(mediaFeatureResult)
+ : m_expectedResult(mediaFeatureResult)
{
}
-MediaQueryEvaluator::MediaQueryEvaluator(const AtomicString& acceptedMediaType, bool mediaFeatureResult)
+MediaQueryEvaluator::MediaQueryEvaluator(const String& acceptedMediaType, bool mediaFeatureResult)
: m_mediaType(acceptedMediaType)
- , m_frame(0)
- , m_style(0)
- , m_expResult(mediaFeatureResult)
+ , m_expectedResult(mediaFeatureResult)
{
}
MediaQueryEvaluator::MediaQueryEvaluator(const char* acceptedMediaType, bool mediaFeatureResult)
: m_mediaType(acceptedMediaType)
- , m_frame(0)
- , m_style(0)
- , m_expResult(mediaFeatureResult)
+ , m_expectedResult(mediaFeatureResult)
{
}
-MediaQueryEvaluator::MediaQueryEvaluator(const AtomicString& acceptedMediaType, Frame* frame, RenderStyle* style)
+MediaQueryEvaluator::MediaQueryEvaluator(const String& acceptedMediaType, LocalFrame* frame)
: m_mediaType(acceptedMediaType)
- , m_frame(frame)
- , m_style(style)
- , m_expResult(false) // Doesn't matter when we have m_frame and m_style.
+ , m_expectedResult(false) // Doesn't matter when we have m_frame and m_style.
+ , m_mediaValues(MediaValues::createDynamicIfFrameExists(frame))
+{
+}
+
+MediaQueryEvaluator::MediaQueryEvaluator(const String& acceptedMediaType, const MediaValues& mediaValues)
+ : m_mediaType(acceptedMediaType)
+ , m_expectedResult(false) // Doesn't matter when we have mediaValues.
+ , m_mediaValues(mediaValues.copy())
{
}
@@ -97,10 +100,10 @@ MediaQueryEvaluator::~MediaQueryEvaluator()
{
}
-bool MediaQueryEvaluator::mediaTypeMatch(const AtomicString& mediaTypeToMatch) const
+bool MediaQueryEvaluator::mediaTypeMatch(const String& mediaTypeToMatch) const
{
return mediaTypeToMatch.isEmpty()
- || equalIgnoringCase(mediaTypeToMatch, "all")
+ || equalIgnoringCase(mediaTypeToMatch, MediaTypeNames::all)
|| equalIgnoringCase(mediaTypeToMatch, m_mediaType);
}
@@ -109,7 +112,7 @@ bool MediaQueryEvaluator::mediaTypeMatchSpecific(const char* mediaTypeToMatch) c
// Like mediaTypeMatch, but without the special cases for "" and "all".
ASSERT(mediaTypeToMatch);
ASSERT(mediaTypeToMatch[0] != '\0');
- ASSERT(!equalIgnoringCase(mediaTypeToMatch, AtomicString("all")));
+ ASSERT(!equalIgnoringCase(mediaTypeToMatch, MediaTypeNames::all));
return equalIgnoringCase(mediaTypeToMatch, m_mediaType);
}
@@ -123,7 +126,7 @@ bool MediaQueryEvaluator::eval(const MediaQuerySet* querySet, MediaQueryResultLi
if (!querySet)
return true;
- const Vector<OwnPtr<MediaQuery> >& queries = querySet->queryVector();
+ const WillBeHeapVector<OwnPtrWillBeMember<MediaQuery> >& queries = querySet->queryVector();
if (!queries.size())
return true; // Empty query list evaluates to true.
@@ -133,21 +136,22 @@ bool MediaQueryEvaluator::eval(const MediaQuerySet* querySet, MediaQueryResultLi
MediaQuery* query = queries[i].get();
if (mediaTypeMatch(query->mediaType())) {
- const ExpressionVector& expressions = query->expressions();
+ const ExpressionHeapVector& expressions = query->expressions();
// Iterate through expressions, stop if any of them eval to false (AND semantics).
size_t j = 0;
for (; j < expressions.size(); ++j) {
bool exprResult = eval(expressions.at(j).get());
if (viewportDependentMediaQueryResults && expressions.at(j)->isViewportDependent())
- viewportDependentMediaQueryResults->append(adoptRef(new MediaQueryResult(*expressions.at(j), exprResult)));
+ viewportDependentMediaQueryResults->append(adoptRefWillBeNoop(new MediaQueryResult(*expressions.at(j), exprResult)));
if (!exprResult)
break;
}
// Assume true if we are at the end of the list, otherwise assume false.
result = applyRestrictor(query->restrictor(), expressions.size() == j);
- } else
+ } else {
result = applyRestrictor(query->restrictor(), false);
+ }
}
return result;
@@ -167,41 +171,38 @@ bool compareValue(T a, T b, MediaFeaturePrefix op)
return false;
}
-static bool compareAspectRatioValue(CSSValue* value, int width, int height, MediaFeaturePrefix op)
+static bool compareAspectRatioValue(const MediaQueryExpValue& value, int width, int height, MediaFeaturePrefix op)
{
- if (value->isAspectRatioValue()) {
- CSSAspectRatioValue* aspectRatio = toCSSAspectRatioValue(value);
- return compareValue(width * static_cast<int>(aspectRatio->denominatorValue()), height * static_cast<int>(aspectRatio->numeratorValue()), op);
- }
+ if (value.isRatio)
+ return compareValue(width * static_cast<int>(value.denominator), height * static_cast<int>(value.numerator), op);
return false;
}
-static bool numberValue(CSSValue* value, float& result)
+static bool numberValue(const MediaQueryExpValue& value, float& result)
{
- if (value->isPrimitiveValue()
- && toCSSPrimitiveValue(value)->isNumber()) {
- result = toCSSPrimitiveValue(value)->getFloatValue(CSSPrimitiveValue::CSS_NUMBER);
+ if (value.isValue && value.unit == CSSPrimitiveValue::CSS_NUMBER) {
+ result = value.value;
return true;
}
return false;
}
-static bool colorMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
+static bool colorMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- int bitsPerComponent = screenDepthPerComponent(frame->view());
float number;
- if (value)
+ int bitsPerComponent = mediaValues.colorBitsPerComponent();
+ if (value.isValid())
return numberValue(value, number) && compareValue(bitsPerComponent, static_cast<int>(number), op);
return bitsPerComponent != 0;
}
-static bool colorIndexMediaFeatureEval(CSSValue* value, RenderStyle*, Frame*, MediaFeaturePrefix op)
+static bool colorIndexMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues&)
{
// FIXME: We currently assume that we do not support indexed displays, as it is unknown
// how to retrieve the information if the display mode is indexed. This matches Firefox.
- if (!value)
+ if (!value.isValid())
return false;
// Acording to spec, if the device does not use a color lookup table, the value is zero.
@@ -209,65 +210,55 @@ static bool colorIndexMediaFeatureEval(CSSValue* value, RenderStyle*, Frame*, Me
return numberValue(value, number) && compareValue(0, static_cast<int>(number), op);
}
-static bool monochromeMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix op)
+static bool monochromeMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- if (!screenIsMonochrome(frame->view())) {
- if (value) {
+ if (!mediaValues.monochromeBitsPerComponent()) {
+ if (value.isValid()) {
float number;
return numberValue(value, number) && compareValue(0, static_cast<int>(number), op);
}
return false;
}
- return colorMediaFeatureEval(value, style, frame, op);
+ return colorMediaFeatureEval(value, op, mediaValues);
}
-static IntSize viewportSize(FrameView* view)
+static bool orientationMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return view->layoutSize(ScrollableArea::IncludeScrollbars);
-}
+ int width = mediaValues.viewportWidth();
+ int height = mediaValues.viewportHeight();
-static bool orientationMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix)
-{
- FrameView* view = frame->view();
- int width = viewportSize(view).width();
- int height = viewportSize(view).height();
- if (value && value->isPrimitiveValue()) {
- const CSSValueID id = toCSSPrimitiveValue(value)->getValueID();
+ if (value.isID) {
if (width > height) // Square viewport is portrait.
- return CSSValueLandscape == id;
- return CSSValuePortrait == id;
+ return CSSValueLandscape == value.id;
+ return CSSValuePortrait == value.id;
}
// Expression (orientation) evaluates to true if width and height >= 0.
return height >= 0 && width >= 0;
}
-static bool aspectRatioMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
+static bool aspectRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- if (value) {
- FrameView* view = frame->view();
- return compareAspectRatioValue(value, viewportSize(view).width(), viewportSize(view).height(), op);
- }
+ if (value.isValid())
+ return compareAspectRatioValue(value, mediaValues.viewportWidth(), mediaValues.viewportHeight(), op);
// ({,min-,max-}aspect-ratio)
// assume if we have a device, its aspect ratio is non-zero.
return true;
}
-static bool deviceAspectRatioMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
+static bool deviceAspectRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- if (value) {
- FloatRect sg = screenRect(frame->view());
- return compareAspectRatioValue(value, static_cast<int>(sg.width()), static_cast<int>(sg.height()), op);
- }
+ if (value.isValid())
+ return compareAspectRatioValue(value, mediaValues.deviceWidth(), mediaValues.deviceHeight(), op);
// ({,min-,max-}device-aspect-ratio)
// assume if we have a device, its aspect ratio is non-zero.
return true;
}
-static bool evalResolution(CSSValue* value, Frame* frame, MediaFeaturePrefix op)
+static bool evalResolution(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
// According to MQ4, only 'screen', 'print' and 'speech' may match.
// FIXME: What should speech match? https://www.w3.org/Style/CSS/Tracker/issues/348
@@ -277,31 +268,31 @@ static bool evalResolution(CSSValue* value, Frame* frame, MediaFeaturePrefix op)
// this method only got called if this media type matches the one defined
// in the query. Thus, if if the document's media type is "print", the
// media type of the query will either be "print" or "all".
- String mediaType = frame->view()->mediaType();
- if (equalIgnoringCase(mediaType, "screen"))
- actualResolution = clampTo<float>(frame->devicePixelRatio());
- else if (equalIgnoringCase(mediaType, "print")) {
+ if (mediaValues.screenMediaType()) {
+ actualResolution = clampTo<float>(mediaValues.devicePixelRatio());
+ } else if (mediaValues.printMediaType()) {
// The resolution of images while printing should not depend on the DPI
// of the screen. Until we support proper ways of querying this info
// we use 300px which is considered minimum for current printers.
actualResolution = 300 / cssPixelsPerInch;
}
- if (!value)
+ if (!value.isValid())
return !!actualResolution;
- if (!value->isPrimitiveValue())
+ if (!value.isValue)
return false;
- CSSPrimitiveValue* resolution = toCSSPrimitiveValue(value);
-
- if (resolution->isNumber())
- return compareValue(actualResolution, resolution->getFloatValue(), op);
+ if (value.unit == CSSPrimitiveValue::CSS_NUMBER)
+ return compareValue(actualResolution, clampTo<float>(value.value), op);
- if (!resolution->isResolution())
+ if (!CSSPrimitiveValue::isResolution(value.unit))
return false;
- if (resolution->isDotsPerCentimeter()) {
+ double canonicalFactor = CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(value.unit);
+ double dppxFactor = CSSPrimitiveValue::conversionToCanonicalUnitsScaleFactor(CSSPrimitiveValue::CSS_DPPX);
+ float valueInDppx = clampTo<float>(value.value * (canonicalFactor / dppxFactor));
+ if (CSSPrimitiveValue::isDotsPerCentimeter(value.unit)) {
// To match DPCM to DPPX values, we limit to 2 decimal points.
// The http://dev.w3.org/csswg/css3-values/#absolute-lengths recommends
// "that the pixel unit refer to the whole number of device pixels that best
@@ -309,111 +300,88 @@ static bool evalResolution(CSSValue* value, Frame* frame, MediaFeaturePrefix op)
// point precision seems appropriate.
return compareValue(
floorf(0.5 + 100 * actualResolution) / 100,
- floorf(0.5 + 100 * resolution->getFloatValue(CSSPrimitiveValue::CSS_DPPX)) / 100, op);
+ floorf(0.5 + 100 * valueInDppx) / 100, op);
}
- return compareValue(actualResolution, resolution->getFloatValue(CSSPrimitiveValue::CSS_DPPX), op);
+ return compareValue(actualResolution, valueInDppx, op);
}
-static bool devicePixelRatioMediaFeatureEval(CSSValue *value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
+static bool devicePixelRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- return (!value || toCSSPrimitiveValue(value)->isNumber()) && evalResolution(value, frame, op);
+ UseCounter::count(mediaValues.document(), UseCounter::PrefixedDevicePixelRatioMediaFeature);
+
+ return (!value.isValid() || value.unit == CSSPrimitiveValue::CSS_NUMBER) && evalResolution(value, op, mediaValues);
}
-static bool resolutionMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
+static bool resolutionMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& MediaValues)
{
- return (!value || toCSSPrimitiveValue(value)->isResolution()) && evalResolution(value, frame, op);
+ return (!value.isValid() || CSSPrimitiveValue::isResolution(value.unit)) && evalResolution(value, op, MediaValues);
}
-static bool gridMediaFeatureEval(CSSValue* value, RenderStyle*, Frame*, MediaFeaturePrefix op)
+static bool gridMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues&)
{
// if output device is bitmap, grid: 0 == true
// assume we have bitmap device
float number;
- if (value && numberValue(value, number))
+ if (value.isValid() && numberValue(value, number))
return compareValue(static_cast<int>(number), 0, op);
return false;
}
-static bool computeLength(CSSValue* value, bool strict, RenderStyle* initialStyle, int& result)
+static bool computeLength(const MediaQueryExpValue& value, const MediaValues& mediaValues, int& result)
{
- if (!value->isPrimitiveValue())
+ if (!value.isValue)
return false;
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
-
- if (primitiveValue->isNumber()) {
- result = primitiveValue->getIntValue();
- return !strict || !result;
- }
-
- if (primitiveValue->isLength()) {
- // Relative (like EM) and root relative (like REM) units are always resolved against
- // the initial values for media queries, hence the two initialStyle parameters.
- result = primitiveValue->computeLength<int>(CSSToLengthConversionData(initialStyle, initialStyle, 1.0 /* zoom */, true /* computingFontSize */));
- return true;
+ if (value.unit == CSSPrimitiveValue::CSS_NUMBER) {
+ result = clampTo<int>(value.value);
+ return !mediaValues.strictMode() || !result;
}
+ if (CSSPrimitiveValue::isLength(value.unit))
+ return mediaValues.computeLength(value.value, value.unit, result);
return false;
}
-static bool deviceHeightMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix op)
+static bool deviceHeightMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- if (value) {
+ if (value.isValid()) {
int length;
- if (!computeLength(value, !frame->document()->inQuirksMode(), style, length))
- return false;
- int height = static_cast<int>(screenRect(frame->view()).height());
- if (frame->settings()->reportScreenSizeInPhysicalPixelsQuirk())
- height = lroundf(height * frame->page()->deviceScaleFactor());
- return compareValue(height, length, op);
+ return computeLength(value, mediaValues, length) && compareValue(static_cast<int>(mediaValues.deviceHeight()), length, op);
}
// ({,min-,max-}device-height)
// assume if we have a device, assume non-zero
return true;
}
-static bool deviceWidthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix op)
+static bool deviceWidthMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- if (value) {
+ if (value.isValid()) {
int length;
- if (!computeLength(value, !frame->document()->inQuirksMode(), style, length))
- return false;
- int width = static_cast<int>(screenRect(frame->view()).width());
- if (frame->settings()->reportScreenSizeInPhysicalPixelsQuirk())
- width = lroundf(width * frame->page()->deviceScaleFactor());
- return compareValue(width, length, op);
+ return computeLength(value, mediaValues, length) && compareValue(static_cast<int>(mediaValues.deviceWidth()), length, op);
}
// ({,min-,max-}device-width)
// assume if we have a device, assume non-zero
return true;
}
-static bool heightMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix op)
+static bool heightMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- FrameView* view = frame->view();
-
- int height = viewportSize(view).height();
- if (value) {
- if (RenderView* renderView = frame->document()->renderView())
- height = adjustForAbsoluteZoom(height, renderView);
+ int height = mediaValues.viewportHeight();
+ if (value.isValid()) {
int length;
- return computeLength(value, !frame->document()->inQuirksMode(), style, length) && compareValue(height, length, op);
+ return computeLength(value, mediaValues, length) && compareValue(height, length, op);
}
return height;
}
-static bool widthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix op)
+static bool widthMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- FrameView* view = frame->view();
-
- int width = viewportSize(view).width();
- if (value) {
- if (RenderView* renderView = frame->document()->renderView())
- width = adjustForAbsoluteZoom(width, renderView);
+ int width = mediaValues.viewportWidth();
+ if (value.isValid()) {
int length;
- return computeLength(value, !frame->document()->inQuirksMode(), style, length) && compareValue(width, length, op);
+ return computeLength(value, mediaValues, length) && compareValue(width, length, op);
}
return width;
@@ -421,255 +389,203 @@ static bool widthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* fr
// Rest of the functions are trampolines which set the prefix according to the media feature expression used.
-static bool minColorMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minColorMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return colorMediaFeatureEval(value, style, frame, MinPrefix);
+ return colorMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxColorMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxColorMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return colorMediaFeatureEval(value, style, frame, MaxPrefix);
+ return colorMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minColorIndexMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minColorIndexMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return colorIndexMediaFeatureEval(value, style, frame, MinPrefix);
+ return colorIndexMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxColorIndexMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxColorIndexMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return colorIndexMediaFeatureEval(value, style, frame, MaxPrefix);
+ return colorIndexMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minMonochromeMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minMonochromeMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return monochromeMediaFeatureEval(value, style, frame, MinPrefix);
+ return monochromeMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxMonochromeMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxMonochromeMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return monochromeMediaFeatureEval(value, style, frame, MaxPrefix);
+ return monochromeMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minAspectRatioMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minAspectRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return aspectRatioMediaFeatureEval(value, style, frame, MinPrefix);
+ return aspectRatioMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxAspectRatioMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxAspectRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return aspectRatioMediaFeatureEval(value, style, frame, MaxPrefix);
+ return aspectRatioMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minDeviceAspectRatioMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minDeviceAspectRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return deviceAspectRatioMediaFeatureEval(value, style, frame, MinPrefix);
+ return deviceAspectRatioMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxDeviceAspectRatioMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxDeviceAspectRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return deviceAspectRatioMediaFeatureEval(value, style, frame, MaxPrefix);
+ return deviceAspectRatioMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minDevicePixelRatioMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minDevicePixelRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return devicePixelRatioMediaFeatureEval(value, style, frame, MinPrefix);
-}
+ UseCounter::count(mediaValues.document(), UseCounter::PrefixedMinDevicePixelRatioMediaFeature);
-static bool maxDevicePixelRatioMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
-{
- return devicePixelRatioMediaFeatureEval(value, style, frame, MaxPrefix);
+ return devicePixelRatioMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool minHeightMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxDevicePixelRatioMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return heightMediaFeatureEval(value, style, frame, MinPrefix);
-}
+ UseCounter::count(mediaValues.document(), UseCounter::PrefixedMaxDevicePixelRatioMediaFeature);
-static bool maxHeightMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
-{
- return heightMediaFeatureEval(value, style, frame, MaxPrefix);
+ return devicePixelRatioMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minWidthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minHeightMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return widthMediaFeatureEval(value, style, frame, MinPrefix);
+ return heightMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxWidthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxHeightMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return widthMediaFeatureEval(value, style, frame, MaxPrefix);
+ return heightMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minDeviceHeightMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minWidthMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return deviceHeightMediaFeatureEval(value, style, frame, MinPrefix);
+ return widthMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxDeviceHeightMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxWidthMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return deviceHeightMediaFeatureEval(value, style, frame, MaxPrefix);
+ return widthMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minDeviceWidthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minDeviceHeightMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return deviceWidthMediaFeatureEval(value, style, frame, MinPrefix);
+ return deviceHeightMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxDeviceWidthMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxDeviceHeightMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return deviceWidthMediaFeatureEval(value, style, frame, MaxPrefix);
+ return deviceHeightMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool minResolutionMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool minDeviceWidthMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return resolutionMediaFeatureEval(value, style, frame, MinPrefix);
+ return deviceWidthMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool maxResolutionMediaFeatureEval(CSSValue* value, RenderStyle* style, Frame* frame, MediaFeaturePrefix)
+static bool maxDeviceWidthMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- return resolutionMediaFeatureEval(value, style, frame, MaxPrefix);
+ return deviceWidthMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool animationMediaFeatureEval(CSSValue* value, RenderStyle*, Frame*, MediaFeaturePrefix op)
+static bool minResolutionMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- if (value) {
- float number;
- return numberValue(value, number) && compareValue(1, static_cast<int>(number), op);
- }
- return true;
+ return resolutionMediaFeatureEval(value, MinPrefix, mediaValues);
}
-static bool deprecatedTransitionMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
+static bool maxResolutionMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- UseCounter::countDeprecation(frame->document(), UseCounter::PrefixedTransitionMediaFeature);
-
- if (value) {
- float number;
- return numberValue(value, number) && compareValue(1, static_cast<int>(number), op);
- }
- return true;
+ return resolutionMediaFeatureEval(value, MaxPrefix, mediaValues);
}
-static bool transform2dMediaFeatureEval(CSSValue* value, RenderStyle*, Frame*, MediaFeaturePrefix op)
+static bool transform3dMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix op, const MediaValues& mediaValues)
{
- if (value) {
- float number;
- return numberValue(value, number) && compareValue(1, static_cast<int>(number), op);
- }
- return true;
-}
+ UseCounter::count(mediaValues.document(), UseCounter::PrefixedTransform3dMediaFeature);
-static bool transform3dMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix op)
-{
bool returnValueIfNoParameter;
int have3dRendering;
- bool threeDEnabled = false;
- if (RenderView* view = frame->contentRenderer())
- threeDEnabled = view->compositor()->canRender3DTransforms();
+ bool threeDEnabled = mediaValues.threeDEnabled();
returnValueIfNoParameter = threeDEnabled;
have3dRendering = threeDEnabled ? 1 : 0;
- if (value) {
+ if (value.isValid()) {
float number;
return numberValue(value, number) && compareValue(have3dRendering, static_cast<int>(number), op);
}
return returnValueIfNoParameter;
}
-static bool viewModeMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix)
-{
- if (!value)
- return true;
-
- return toCSSPrimitiveValue(value)->getValueID() == CSSValueWindowed;
-}
-
-enum PointerDeviceType { TouchPointer, MousePointer, NoPointer, UnknownPointer };
-
-static PointerDeviceType leastCapablePrimaryPointerDeviceType(Frame* frame)
-{
- if (frame->settings()->deviceSupportsTouch())
- return TouchPointer;
-
- // FIXME: We should also try to determine if we know we have a mouse.
- // When we do this, we'll also need to differentiate between known not to
- // have mouse or touch screen (NoPointer) and unknown (UnknownPointer).
- // We could also take into account other preferences like accessibility
- // settings to decide which of the available pointers should be considered
- // "primary".
-
- return UnknownPointer;
-}
-
-static bool hoverMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix)
+static bool hoverMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- PointerDeviceType pointer = leastCapablePrimaryPointerDeviceType(frame);
+ MediaValues::PointerDeviceType pointer = mediaValues.pointer();
// If we're on a port that hasn't explicitly opted into providing pointer device information
// (or otherwise can't be confident in the pointer hardware available), then behave exactly
// as if this feature feature isn't supported.
- if (pointer == UnknownPointer)
+ if (pointer == MediaValues::UnknownPointer)
return false;
float number = 1;
- if (value) {
+ if (value.isValid()) {
if (!numberValue(value, number))
return false;
}
- return (pointer == NoPointer && !number)
- || (pointer == TouchPointer && !number)
- || (pointer == MousePointer && number == 1);
+ return (pointer == MediaValues::NoPointer && !number)
+ || (pointer == MediaValues::TouchPointer && !number)
+ || (pointer == MediaValues::MousePointer && number == 1);
}
-static bool pointerMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix)
+static bool pointerMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- PointerDeviceType pointer = leastCapablePrimaryPointerDeviceType(frame);
+ MediaValues::PointerDeviceType pointer = mediaValues.pointer();
// If we're on a port that hasn't explicitly opted into providing pointer device information
// (or otherwise can't be confident in the pointer hardware available), then behave exactly
// as if this feature feature isn't supported.
- if (pointer == UnknownPointer)
+ if (pointer == MediaValues::UnknownPointer)
return false;
- if (!value)
- return pointer != NoPointer;
+ if (!value.isValid())
+ return pointer != MediaValues::NoPointer;
- if (!value->isPrimitiveValue())
+ if (!value.isID)
return false;
- const CSSValueID id = toCSSPrimitiveValue(value)->getValueID();
- return (pointer == NoPointer && id == CSSValueNone)
- || (pointer == TouchPointer && id == CSSValueCoarse)
- || (pointer == MousePointer && id == CSSValueFine);
+ return (pointer == MediaValues::NoPointer && value.id == CSSValueNone)
+ || (pointer == MediaValues::TouchPointer && value.id == CSSValueCoarse)
+ || (pointer == MediaValues::MousePointer && value.id == CSSValueFine);
}
-static bool scanMediaFeatureEval(CSSValue* value, RenderStyle*, Frame* frame, MediaFeaturePrefix)
+static bool scanMediaFeatureEval(const MediaQueryExpValue& value, MediaFeaturePrefix, const MediaValues& mediaValues)
{
- // Scan only applies to 'tv' media.
- if (!equalIgnoringCase(frame->view()->mediaType(), "tv"))
+ if (!mediaValues.scanMediaType())
return false;
- if (!value)
+ if (!value.isValid())
return true;
- if (!value->isPrimitiveValue())
+ if (!value.isID)
return false;
// If a platform interface supplies progressive/interlace info for TVs in the
// future, it needs to be handled here. For now, assume a modern TV with
// progressive display.
- return toCSSPrimitiveValue(value)->getValueID() == CSSValueProgressive;
+ return (value.id == CSSValueProgressive);
}
static void createFunctionMap()
{
// Create the table.
gFunctionMap = new FunctionMap;
-#define ADD_TO_FUNCTIONMAP(name, str) \
+#define ADD_TO_FUNCTIONMAP(name) \
gFunctionMap->set(name##MediaFeature.impl(), name##MediaFeatureEval);
CSS_MEDIAQUERY_NAMES_FOR_EACH_MEDIAFEATURE(ADD_TO_FUNCTIONMAP);
#undef ADD_TO_FUNCTIONMAP
@@ -677,8 +593,8 @@ static void createFunctionMap()
bool MediaQueryEvaluator::eval(const MediaQueryExp* expr) const
{
- if (!m_frame || !m_style)
- return m_expResult;
+ if (!m_mediaValues || !m_mediaValues->hasValues())
+ return m_expectedResult;
if (!gFunctionMap)
createFunctionMap();
@@ -687,7 +603,7 @@ bool MediaQueryEvaluator::eval(const MediaQueryExp* expr) const
// trampoline functions override the prefix if prefix is used.
EvalFunc func = gFunctionMap->get(expr->mediaFeature().impl());
if (func)
- return func(expr->value(), m_style.get(), m_frame, NoPrefix);
+ return func(expr->expValue(), NoPrefix, *m_mediaValues);
return false;
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.h b/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.h
index 60bd9cd78f2..64f1894e507 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluator.h
@@ -28,64 +28,67 @@
#ifndef MediaQueryEvaluator_h
#define MediaQueryEvaluator_h
+#include "platform/heap/Handle.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
-class Frame;
+class LocalFrame;
class MediaQueryExp;
class MediaQueryResult;
class MediaQuerySet;
class RenderStyle;
+class MediaValues;
-typedef Vector<RefPtr<MediaQueryResult> > MediaQueryResultList;
+typedef WillBeHeapVector<RefPtrWillBeMember<MediaQueryResult> > MediaQueryResultList;
+
+// Class that evaluates css media queries as defined in
+// CSS3 Module "Media Queries" (http://www.w3.org/TR/css3-mediaqueries/)
+// Special constructors are needed, if simple media queries are to be
+// evaluated without knowledge of the medium features. This can happen
+// for example when parsing UA stylesheets, if evaluation is done
+// right after parsing.
+//
+// the boolean parameter is used to approximate results of evaluation, if
+// the device characteristics are not known. This can be used to prune the loading
+// of stylesheets to only those which are probable to match.
-/**
- * Class that evaluates css media queries as defined in
- * CSS3 Module "Media Queries" (http://www.w3.org/TR/css3-mediaqueries/)
- * Special constructors are needed, if simple media queries are to be
- * evaluated without knowledge of the medium features. This can happen
- * for example when parsing UA stylesheets, if evaluation is done
- * right after parsing.
- *
- * the boolean parameter is used to approximate results of evaluation, if
- * the device characteristics are not known. This can be used to prune the loading
- * of stylesheets to only those which are probable to match.
- */
class MediaQueryEvaluator {
WTF_MAKE_NONCOPYABLE(MediaQueryEvaluator); WTF_MAKE_FAST_ALLOCATED;
public:
- /** Creates evaluator which evaluates only simple media queries
- * Evaluator returns true for "all", and returns value of \mediaFeatureResult
- * for any media features
- */
+ // Creates evaluator which evaluates only simple media queries
+ // Evaluator returns true for "all", and returns value of \mediaFeatureResult
+ // for any media features
+
explicit MediaQueryEvaluator(bool mediaFeatureResult = false);
- /** Creates evaluator which evaluates only simple media queries
- * Evaluator returns true for acceptedMediaType and returns value of \mediafeatureResult
- * for any media features
- */
- MediaQueryEvaluator(const AtomicString& acceptedMediaType, bool mediaFeatureResult = false);
+ // Creates evaluator which evaluates only simple media queries
+ // Evaluator returns true for acceptedMediaType and returns value of \mediafeatureResult
+ // for any media features
+
+ MediaQueryEvaluator(const String& acceptedMediaType, bool mediaFeatureResult = false);
MediaQueryEvaluator(const char* acceptedMediaType, bool mediaFeatureResult = false);
- /** Creates evaluator which evaluates full media queries */
- MediaQueryEvaluator(const AtomicString& acceptedMediaType, Frame*, RenderStyle*);
+ // Creates evaluator which evaluates full media queries
+ MediaQueryEvaluator(const String& acceptedMediaType, LocalFrame*);
+
+ // Creates evaluator which evaluates in a thread-safe manner a subset of media values
+ MediaQueryEvaluator(const String& acceptedMediaType, const MediaValues&);
~MediaQueryEvaluator();
- bool mediaTypeMatch(const AtomicString& mediaTypeToMatch) const;
+ bool mediaTypeMatch(const String& mediaTypeToMatch) const;
bool mediaTypeMatchSpecific(const char* mediaTypeToMatch) const;
- /** Evaluates a list of media queries */
+ // Evaluates a list of media queries
bool eval(const MediaQuerySet*, MediaQueryResultList* = 0) const;
- /** Evaluates media query subexpression, ie "and (media-feature: value)" part */
+ // Evaluates media query subexpression, ie "and (media-feature: value)" part
bool eval(const MediaQueryExp*) const;
private:
- AtomicString m_mediaType;
- Frame* m_frame; // Not owned.
- RefPtr<RenderStyle> m_style;
- bool m_expResult;
+ String m_mediaType;
+ bool m_expectedResult;
+ RefPtr<MediaValues> m_mediaValues;
};
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluatorTest.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluatorTest.cpp
new file mode 100644
index 00000000000..668077ef683
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryEvaluatorTest.cpp
@@ -0,0 +1,102 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/MediaQueryEvaluator.h"
+
+#include "core/css/MediaList.h"
+#include "core/css/MediaValuesCached.h"
+#include "wtf/PassOwnPtr.h"
+#include "wtf/text/StringBuilder.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+typedef struct {
+ const char* input;
+ const bool output;
+} TestCase;
+
+TEST(MediaQueryEvaluatorTest, Basic)
+{
+ // The first string represents the input string.
+ // The second string represents the output string, if present.
+ // Otherwise, the output string is identical to the first string.
+ TestCase screenTestCases[] = {
+ {"", 1},
+ {" ", 1},
+ {"screen", 1},
+ {"screen and (color)", 1},
+ {"all and (min-width: 500px)", 1},
+ {"not screen and (color)", 0},
+ {"(min-width: 500px)", 1},
+ {"(min-width: 501px)", 0},
+ {"(max-width: 500px)", 1},
+ {"(max-width: 499px)", 0},
+ {"(width: 500px)", 1},
+ {"(width: 501px)", 0},
+ {"(min-height: 500px)", 1},
+ {"(min-height: 501px)", 0},
+ {"(max-height: 500px)", 1},
+ {"(max-height: 499px)", 0},
+ {"(height: 500px)", 1},
+ {"(height: 501px)", 0},
+ {"screen and (min-width: 400px) and (max-width: 700px)", 1},
+ {"screen and (device-aspect-ratio: 16/9)", 0},
+ {"screen and (device-aspect-ratio: 1/1)", 1},
+ {"all and (min-color: 2)", 1},
+ {"all and (min-color: 32)", 0},
+ {"all and (min-color-index: 0)", 1},
+ {"all and (min-color-index: 1)", 0},
+ {"all and (monochrome)", 0},
+ {"all and (min-monochrome: 0)", 1},
+ {"all and (grid: 0)", 1},
+ {"(resolution: 2dppx)", 1},
+ {"(resolution: 1dppx)", 0},
+ {"(orientation: portrait)", 1},
+ {"(orientation: landscape)", 0},
+ {"tv and (scan: progressive)", 0},
+ {"(pointer: coarse)", 0},
+ {"(pointer: fine)", 1},
+ {"(hover: 1)", 1},
+ {"(hover: 0)", 0},
+ {0, 0} // Do not remove the terminator line.
+ };
+ TestCase printTestCases[] = {
+ {"print and (min-resolution: 1dppx)", 1},
+ {"print and (min-resolution: 118dpcm)", 0},
+ {0, 0} // Do not remove the terminator line.
+ };
+
+ MediaValuesCached::MediaValuesCachedData data;
+ data.viewportWidth = 500;
+ data.viewportHeight = 500;
+ data.deviceWidth = 500;
+ data.deviceHeight = 500;
+ data.devicePixelRatio = 2.0;
+ data.colorBitsPerComponent = 24;
+ data.monochromeBitsPerComponent = 0;
+ data.pointer = MediaValues::MousePointer;
+ data.defaultFontSize = 16;
+ data.threeDEnabled = true;
+ data.scanMediaType = false;
+ data.screenMediaType = true;
+ data.printMediaType = false;
+ data.strictMode = true;
+ RefPtr<MediaValues> mediaValues = MediaValuesCached::create(data);
+
+ for (unsigned i = 0; screenTestCases[i].input; ++i) {
+ RefPtrWillBeRawPtr<MediaQuerySet> querySet = MediaQuerySet::create(screenTestCases[i].input);
+ MediaQueryEvaluator mediaQueryEvaluator("screen", *mediaValues);
+ ASSERT_EQ(screenTestCases[i].output, mediaQueryEvaluator.eval(querySet.get()));
+ }
+ for (unsigned i = 0; printTestCases[i].input; ++i) {
+ RefPtrWillBeRawPtr<MediaQuerySet> querySet = MediaQuerySet::create(printTestCases[i].input);
+ MediaQueryEvaluator mediaQueryEvaluator("print", *mediaValues);
+ ASSERT_EQ(printTestCases[i].output, mediaQueryEvaluator.eval(querySet.get()));
+ }
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.cpp
index 05c0e5cffd7..14348dfeaad 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.cpp
@@ -30,214 +30,211 @@
#include "config.h"
#include "core/css/MediaQueryExp.h"
-#include "CSSValueKeywords.h"
#include "core/css/CSSAspectRatioValue.h"
-#include "core/css/CSSParser.h"
+#include "core/css/CSSParserValues.h"
#include "core/css/CSSPrimitiveValue.h"
+#include "core/html/parser/HTMLParserIdioms.h"
+#include "platform/Decimal.h"
+#include "wtf/text/StringBuffer.h"
#include "wtf/text/StringBuilder.h"
namespace WebCore {
-static inline bool featureWithCSSValueID(const AtomicString& mediaFeature, const CSSParserValue* value)
+using namespace MediaFeatureNames;
+
+static inline bool featureWithCSSValueID(const String& mediaFeature, const CSSParserValue* value)
{
if (!value->id)
return false;
- return mediaFeature == MediaFeatureNames::orientationMediaFeature
- || mediaFeature == MediaFeatureNames::viewModeMediaFeature
- || mediaFeature == MediaFeatureNames::pointerMediaFeature
- || mediaFeature == MediaFeatureNames::scanMediaFeature;
+ return mediaFeature == orientationMediaFeature
+ || mediaFeature == pointerMediaFeature
+ || mediaFeature == scanMediaFeature;
}
-static inline bool featureWithValidIdent(const AtomicString& mediaFeature, CSSValueID ident)
+static inline bool featureWithValidIdent(const String& mediaFeature, CSSValueID ident)
{
- if (mediaFeature == MediaFeatureNames::orientationMediaFeature)
+ if (mediaFeature == orientationMediaFeature)
return ident == CSSValuePortrait || ident == CSSValueLandscape;
- if (mediaFeature == MediaFeatureNames::viewModeMediaFeature) {
- switch (ident) {
- case CSSValueWindowed:
- case CSSValueFloating:
- case CSSValueFullscreen:
- case CSSValueMaximized:
- case CSSValueMinimized:
- return true;
- default:
- return false;
- }
- }
-
- if (mediaFeature == MediaFeatureNames::pointerMediaFeature)
+ if (mediaFeature == pointerMediaFeature)
return ident == CSSValueNone || ident == CSSValueCoarse || ident == CSSValueFine;
- if (mediaFeature == MediaFeatureNames::scanMediaFeature)
+ if (mediaFeature == scanMediaFeature)
return ident == CSSValueInterlace || ident == CSSValueProgressive;
ASSERT_NOT_REACHED();
return false;
}
-static inline bool featureWithValidPositiveLenghtOrNumber(const AtomicString& mediaFeature, const CSSParserValue* value)
+static inline bool featureWithValidPositiveLength(const String& mediaFeature, const CSSParserValue* value)
{
- if (!(((value->unit >= CSSPrimitiveValue::CSS_EMS && value->unit <= CSSPrimitiveValue::CSS_PC) || value->unit == CSSPrimitiveValue::CSS_REMS) || value->unit == CSSPrimitiveValue::CSS_NUMBER) || value->fValue < 0)
+ if (!(((value->unit >= CSSPrimitiveValue::CSS_EMS && value->unit <= CSSPrimitiveValue::CSS_PC) || value->unit == CSSPrimitiveValue::CSS_REMS) || (value->unit == CSSPrimitiveValue::CSS_NUMBER && !(value->fValue))) || value->fValue < 0)
return false;
- return mediaFeature == MediaFeatureNames::heightMediaFeature
- || mediaFeature == MediaFeatureNames::maxHeightMediaFeature
- || mediaFeature == MediaFeatureNames::minHeightMediaFeature
- || mediaFeature == MediaFeatureNames::widthMediaFeature
- || mediaFeature == MediaFeatureNames::maxWidthMediaFeature
- || mediaFeature == MediaFeatureNames::minWidthMediaFeature
- || mediaFeature == MediaFeatureNames::deviceHeightMediaFeature
- || mediaFeature == MediaFeatureNames::maxDeviceHeightMediaFeature
- || mediaFeature == MediaFeatureNames::minDeviceHeightMediaFeature
- || mediaFeature == MediaFeatureNames::deviceWidthMediaFeature
- || mediaFeature == MediaFeatureNames::maxDeviceWidthMediaFeature
- || mediaFeature == MediaFeatureNames::minDeviceWidthMediaFeature;
+
+ return mediaFeature == heightMediaFeature
+ || mediaFeature == maxHeightMediaFeature
+ || mediaFeature == minHeightMediaFeature
+ || mediaFeature == widthMediaFeature
+ || mediaFeature == maxWidthMediaFeature
+ || mediaFeature == minWidthMediaFeature
+ || mediaFeature == deviceHeightMediaFeature
+ || mediaFeature == maxDeviceHeightMediaFeature
+ || mediaFeature == minDeviceHeightMediaFeature
+ || mediaFeature == deviceWidthMediaFeature
+ || mediaFeature == minDeviceWidthMediaFeature
+ || mediaFeature == maxDeviceWidthMediaFeature;
}
-static inline bool featureWithValidDensity(const AtomicString& mediaFeature, const CSSParserValue* value)
+static inline bool featureWithValidDensity(const String& mediaFeature, const CSSParserValue* value)
{
if ((value->unit != CSSPrimitiveValue::CSS_DPPX && value->unit != CSSPrimitiveValue::CSS_DPI && value->unit != CSSPrimitiveValue::CSS_DPCM) || value->fValue <= 0)
return false;
- return mediaFeature == MediaFeatureNames::resolutionMediaFeature
- || mediaFeature == MediaFeatureNames::maxResolutionMediaFeature
- || mediaFeature == MediaFeatureNames::minResolutionMediaFeature;
+ return mediaFeature == resolutionMediaFeature
+ || mediaFeature == minResolutionMediaFeature
+ || mediaFeature == maxResolutionMediaFeature;
}
-static inline bool featureWithPositiveInteger(const AtomicString& mediaFeature, const CSSParserValue* value)
+static inline bool featureWithPositiveInteger(const String& mediaFeature, const CSSParserValue* value)
{
if (!value->isInt || value->fValue < 0)
return false;
- return mediaFeature == MediaFeatureNames::colorMediaFeature
- || mediaFeature == MediaFeatureNames::maxColorMediaFeature
- || mediaFeature == MediaFeatureNames::minColorMediaFeature
- || mediaFeature == MediaFeatureNames::colorIndexMediaFeature
- || mediaFeature == MediaFeatureNames::maxColorIndexMediaFeature
- || mediaFeature == MediaFeatureNames::minColorIndexMediaFeature
- || mediaFeature == MediaFeatureNames::monochromeMediaFeature
- || mediaFeature == MediaFeatureNames::minMonochromeMediaFeature
- || mediaFeature == MediaFeatureNames::maxMonochromeMediaFeature;
+ return mediaFeature == colorMediaFeature
+ || mediaFeature == maxColorMediaFeature
+ || mediaFeature == minColorMediaFeature
+ || mediaFeature == colorIndexMediaFeature
+ || mediaFeature == maxColorIndexMediaFeature
+ || mediaFeature == minColorIndexMediaFeature
+ || mediaFeature == monochromeMediaFeature
+ || mediaFeature == maxMonochromeMediaFeature
+ || mediaFeature == minMonochromeMediaFeature;
}
-static inline bool featureWithPositiveNumber(const AtomicString& mediaFeature, const CSSParserValue* value)
+static inline bool featureWithPositiveNumber(const String& mediaFeature, const CSSParserValue* value)
{
if (value->unit != CSSPrimitiveValue::CSS_NUMBER || value->fValue < 0)
return false;
- return mediaFeature == MediaFeatureNames::transform2dMediaFeature
- || mediaFeature == MediaFeatureNames::transform3dMediaFeature
- || mediaFeature == MediaFeatureNames::deprecatedTransitionMediaFeature
- || mediaFeature == MediaFeatureNames::animationMediaFeature
- || mediaFeature == MediaFeatureNames::devicePixelRatioMediaFeature
- || mediaFeature == MediaFeatureNames::maxDevicePixelRatioMediaFeature
- || mediaFeature == MediaFeatureNames::minDevicePixelRatioMediaFeature;
+ return mediaFeature == transform3dMediaFeature
+ || mediaFeature == devicePixelRatioMediaFeature
+ || mediaFeature == maxDevicePixelRatioMediaFeature
+ || mediaFeature == minDevicePixelRatioMediaFeature;
}
-static inline bool featureWithZeroOrOne(const AtomicString& mediaFeature, const CSSParserValue* value)
+static inline bool featureWithZeroOrOne(const String& mediaFeature, const CSSParserValue* value)
{
if (!value->isInt || !(value->fValue == 1 || !value->fValue))
return false;
- return mediaFeature == MediaFeatureNames::gridMediaFeature
- || mediaFeature == MediaFeatureNames::hoverMediaFeature;
+ return mediaFeature == gridMediaFeature
+ || mediaFeature == hoverMediaFeature;
}
-static inline bool featureWithAspectRatio(const AtomicString& mediaFeature)
+static inline bool featureWithAspectRatio(const String& mediaFeature)
{
- return mediaFeature == MediaFeatureNames::aspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::deviceAspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::minAspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::maxAspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::minDeviceAspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::maxDeviceAspectRatioMediaFeature;
+ return mediaFeature == aspectRatioMediaFeature
+ || mediaFeature == deviceAspectRatioMediaFeature
+ || mediaFeature == minAspectRatioMediaFeature
+ || mediaFeature == maxAspectRatioMediaFeature
+ || mediaFeature == minDeviceAspectRatioMediaFeature
+ || mediaFeature == maxDeviceAspectRatioMediaFeature;
}
-static inline bool featureWithoutValue(const AtomicString& mediaFeature)
+static inline bool featureWithoutValue(const String& mediaFeature)
{
// Media features that are prefixed by min/max cannot be used without a value.
- return mediaFeature == MediaFeatureNames::monochromeMediaFeature
- || mediaFeature == MediaFeatureNames::colorMediaFeature
- || mediaFeature == MediaFeatureNames::colorIndexMediaFeature
- || mediaFeature == MediaFeatureNames::gridMediaFeature
- || mediaFeature == MediaFeatureNames::heightMediaFeature
- || mediaFeature == MediaFeatureNames::widthMediaFeature
- || mediaFeature == MediaFeatureNames::deviceHeightMediaFeature
- || mediaFeature == MediaFeatureNames::deviceWidthMediaFeature
- || mediaFeature == MediaFeatureNames::orientationMediaFeature
- || mediaFeature == MediaFeatureNames::aspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::deviceAspectRatioMediaFeature
- || mediaFeature == MediaFeatureNames::hoverMediaFeature
- || mediaFeature == MediaFeatureNames::transform2dMediaFeature
- || mediaFeature == MediaFeatureNames::transform3dMediaFeature
- || mediaFeature == MediaFeatureNames::deprecatedTransitionMediaFeature
- || mediaFeature == MediaFeatureNames::animationMediaFeature
- || mediaFeature == MediaFeatureNames::viewModeMediaFeature
- || mediaFeature == MediaFeatureNames::pointerMediaFeature
- || mediaFeature == MediaFeatureNames::devicePixelRatioMediaFeature
- || mediaFeature == MediaFeatureNames::resolutionMediaFeature
- || mediaFeature == MediaFeatureNames::scanMediaFeature;
+ return mediaFeature == monochromeMediaFeature
+ || mediaFeature == colorMediaFeature
+ || mediaFeature == colorIndexMediaFeature
+ || mediaFeature == gridMediaFeature
+ || mediaFeature == heightMediaFeature
+ || mediaFeature == widthMediaFeature
+ || mediaFeature == deviceHeightMediaFeature
+ || mediaFeature == deviceWidthMediaFeature
+ || mediaFeature == orientationMediaFeature
+ || mediaFeature == aspectRatioMediaFeature
+ || mediaFeature == deviceAspectRatioMediaFeature
+ || mediaFeature == hoverMediaFeature
+ || mediaFeature == transform3dMediaFeature
+ || mediaFeature == pointerMediaFeature
+ || mediaFeature == devicePixelRatioMediaFeature
+ || mediaFeature == resolutionMediaFeature
+ || mediaFeature == scanMediaFeature;
}
bool MediaQueryExp::isViewportDependent() const
{
- return m_mediaFeature == MediaFeatureNames::widthMediaFeature
- || m_mediaFeature == MediaFeatureNames::heightMediaFeature
- || m_mediaFeature == MediaFeatureNames::minWidthMediaFeature
- || m_mediaFeature == MediaFeatureNames::minHeightMediaFeature
- || m_mediaFeature == MediaFeatureNames::maxWidthMediaFeature
- || m_mediaFeature == MediaFeatureNames::maxHeightMediaFeature
- || m_mediaFeature == MediaFeatureNames::orientationMediaFeature
- || m_mediaFeature == MediaFeatureNames::aspectRatioMediaFeature
- || m_mediaFeature == MediaFeatureNames::minAspectRatioMediaFeature
- || m_mediaFeature == MediaFeatureNames::devicePixelRatioMediaFeature
- || m_mediaFeature == MediaFeatureNames::resolutionMediaFeature
- || m_mediaFeature == MediaFeatureNames::maxAspectRatioMediaFeature;
+ return m_mediaFeature == widthMediaFeature
+ || m_mediaFeature == heightMediaFeature
+ || m_mediaFeature == minWidthMediaFeature
+ || m_mediaFeature == minHeightMediaFeature
+ || m_mediaFeature == maxWidthMediaFeature
+ || m_mediaFeature == maxHeightMediaFeature
+ || m_mediaFeature == orientationMediaFeature
+ || m_mediaFeature == aspectRatioMediaFeature
+ || m_mediaFeature == minAspectRatioMediaFeature
+ || m_mediaFeature == devicePixelRatioMediaFeature
+ || m_mediaFeature == resolutionMediaFeature
+ || m_mediaFeature == maxAspectRatioMediaFeature;
}
-MediaQueryExp::MediaQueryExp(const AtomicString& mediaFeature, PassRefPtr<CSSValue> value)
+MediaQueryExp::MediaQueryExp(const MediaQueryExp& other)
+ : m_mediaFeature(other.mediaFeature())
+ , m_expValue(other.expValue())
+{
+}
+
+MediaQueryExp::MediaQueryExp(const String& mediaFeature, const MediaQueryExpValue& expValue)
: m_mediaFeature(mediaFeature)
- , m_value(value)
+ , m_expValue(expValue)
{
}
-PassOwnPtr<MediaQueryExp> MediaQueryExp::create(const AtomicString& mediaFeature, CSSParserValueList* valueList)
+PassOwnPtrWillBeRawPtr<MediaQueryExp> MediaQueryExp::createIfValid(const String& mediaFeature, CSSParserValueList* valueList)
{
- RefPtr<CSSValue> cssValue;
+ ASSERT(!mediaFeature.isNull());
+
+ MediaQueryExpValue expValue;
bool isValid = false;
+ String lowerMediaFeature = attemptStaticStringCreation(mediaFeature.lower());
// Create value for media query expression that must have 1 or more values.
- if (valueList) {
+ if (valueList && valueList->size() > 0) {
if (valueList->size() == 1) {
CSSParserValue* value = valueList->current();
+ ASSERT(value);
- if (featureWithCSSValueID(mediaFeature, value)) {
+ if (featureWithCSSValueID(lowerMediaFeature, value) && featureWithValidIdent(lowerMediaFeature, value->id)) {
// Media features that use CSSValueIDs.
- cssValue = CSSPrimitiveValue::createIdentifier(value->id);
- if (!featureWithValidIdent(mediaFeature, toCSSPrimitiveValue(cssValue.get())->getValueID()))
- cssValue.clear();
- } else if (featureWithValidDensity(mediaFeature, value)) {
- // Media features that must have non-negative <density>, ie. dppx, dpi or dpcm.
- cssValue = CSSPrimitiveValue::create(value->fValue, (CSSPrimitiveValue::UnitTypes) value->unit);
- } else if (featureWithValidPositiveLenghtOrNumber(mediaFeature, value)) {
- // Media features that must have non-negative <lenght> or number value.
- cssValue = CSSPrimitiveValue::create(value->fValue, (CSSPrimitiveValue::UnitTypes) value->unit);
- } else if (featureWithPositiveInteger(mediaFeature, value)) {
- // Media features that must have non-negative integer value.
- cssValue = CSSPrimitiveValue::create(value->fValue, CSSPrimitiveValue::CSS_NUMBER);
- } else if (featureWithPositiveNumber(mediaFeature, value)) {
- // Media features that must have non-negative number value.
- cssValue = CSSPrimitiveValue::create(value->fValue, CSSPrimitiveValue::CSS_NUMBER);
- } else if (featureWithZeroOrOne(mediaFeature, value)) {
- // Media features that must have (0|1) value.
- cssValue = CSSPrimitiveValue::create(value->fValue, CSSPrimitiveValue::CSS_NUMBER);
+ expValue.id = value->id;
+ expValue.unit = CSSPrimitiveValue::CSS_VALUE_ID;
+ expValue.isID = true;
+ } else if (featureWithValidDensity(lowerMediaFeature, value)
+ || featureWithValidPositiveLength(lowerMediaFeature, value)) {
+ // Media features that must have non-negative <density>, ie. dppx, dpi or dpcm,
+ // or Media features that must have non-negative <length> or number value.
+ expValue.value = value->fValue;
+ expValue.unit = (CSSPrimitiveValue::UnitType)value->unit;
+ expValue.isValue = true;
+ expValue.isInteger = value->isInt;
+ } else if (featureWithPositiveInteger(lowerMediaFeature, value)
+ || featureWithPositiveNumber(lowerMediaFeature, value)
+ || featureWithZeroOrOne(lowerMediaFeature, value)) {
+ // Media features that must have non-negative integer value,
+ // or media features that must have non-negative number value,
+ // or media features that must have (0|1) value.
+ expValue.value = value->fValue;
+ expValue.unit = CSSPrimitiveValue::CSS_NUMBER;
+ expValue.isValue = true;
+ expValue.isInteger = value->isInt;
}
- isValid = cssValue;
+ isValid = (expValue.isID || expValue.isValue);
- } else if (valueList->size() == 3 && featureWithAspectRatio(mediaFeature)) {
+ } else if (valueList->size() == 3 && featureWithAspectRatio(lowerMediaFeature)) {
// Create list of values.
// Currently accepts only <integer>/<integer>.
// Applicable to device-aspect-ratio and aspec-ratio.
@@ -260,35 +257,67 @@ PassOwnPtr<MediaQueryExp> MediaQueryExp::create(const AtomicString& mediaFeature
}
}
- if (isValid)
- cssValue = CSSAspectRatioValue::create(numeratorValue, denominatorValue);
+ if (isValid) {
+ expValue.numerator = (unsigned)numeratorValue;
+ expValue.denominator = (unsigned)denominatorValue;
+ expValue.isRatio = true;
+ }
}
- } else if (featureWithoutValue(mediaFeature)) {
+ } else if (featureWithoutValue(lowerMediaFeature)) {
isValid = true;
}
if (!isValid)
return nullptr;
- return adoptPtr(new MediaQueryExp(mediaFeature, cssValue));
+ return adoptPtrWillBeNoop(new MediaQueryExp(lowerMediaFeature, expValue));
}
MediaQueryExp::~MediaQueryExp()
{
}
+bool MediaQueryExp::operator==(const MediaQueryExp& other) const
+{
+ return (other.m_mediaFeature == m_mediaFeature)
+ && ((!other.m_expValue.isValid() && !m_expValue.isValid())
+ || (other.m_expValue.isValid() && m_expValue.isValid() && other.m_expValue.equals(m_expValue)));
+}
+
String MediaQueryExp::serialize() const
{
StringBuilder result;
result.append("(");
result.append(m_mediaFeature.lower());
- if (m_value) {
+ if (m_expValue.isValid()) {
result.append(": ");
- result.append(m_value->cssText());
+ result.append(m_expValue.cssText());
}
result.append(")");
return result.toString();
}
+static inline String printNumber(double number)
+{
+ return Decimal::fromDouble(number).toString();
+}
+
+String MediaQueryExpValue::cssText() const
+{
+ StringBuilder output;
+ if (isValue) {
+ output.append(printNumber(value));
+ output.append(CSSPrimitiveValue::unitTypeToString(unit));
+ } else if (isRatio) {
+ output.append(printNumber(numerator));
+ output.append("/");
+ output.append(printNumber(denominator));
+ } else if (isID) {
+ output.append(getValueName(id));
+ }
+
+ return output.toString();
+}
+
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.h b/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.h
index 0586b0a6bb3..1ca45c2fa70 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryExp.h
@@ -29,43 +29,82 @@
#ifndef MediaQueryExp_h
#define MediaQueryExp_h
+#include "core/CSSValueKeywords.h"
+#include "core/MediaFeatureNames.h"
+#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSValue.h"
-#include "core/css/MediaFeatureNames.h"
#include "wtf/PassOwnPtr.h"
#include "wtf/RefPtr.h"
-#include "wtf/text/AtomicString.h"
namespace WebCore {
class CSSParserValueList;
-class MediaQueryExp {
- WTF_MAKE_FAST_ALLOCATED;
-public:
- static PassOwnPtr<MediaQueryExp> create(const AtomicString& mediaFeature, CSSParserValueList*);
- ~MediaQueryExp();
+struct MediaQueryExpValue {
+ CSSValueID id;
+ double value;
+ CSSPrimitiveValue::UnitType unit;
+ unsigned numerator;
+ unsigned denominator;
- AtomicString mediaFeature() const { return m_mediaFeature; }
+ bool isID;
+ bool isValue;
+ bool isRatio;
+ bool isInteger;
- CSSValue* value() const { return m_value.get(); }
+ MediaQueryExpValue()
+ : id(CSSValueInvalid)
+ , value(0)
+ , unit(CSSPrimitiveValue::CSS_UNKNOWN)
+ , numerator(0)
+ , denominator(1)
+ , isID(false)
+ , isValue(false)
+ , isRatio(false)
+ , isInteger(false)
+ {
+ }
- bool operator==(const MediaQueryExp& other) const
+ bool isValid() const { return (isID || isValue || isRatio); }
+ String cssText() const;
+ bool equals(const MediaQueryExpValue& expValue) const
{
- return (other.m_mediaFeature == m_mediaFeature)
- && ((!other.m_value && !m_value)
- || (other.m_value && m_value && other.m_value->equals(*m_value)));
+ if (isID)
+ return (id == expValue.id);
+ if (isValue)
+ return (value == expValue.value);
+ if (isRatio)
+ return (numerator == expValue.numerator && denominator == expValue.denominator);
+ return !expValue.isValid();
}
+};
+
+class MediaQueryExp : public NoBaseWillBeGarbageCollectedFinalized<MediaQueryExp> {
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
+public:
+ static PassOwnPtrWillBeRawPtr<MediaQueryExp> createIfValid(const String& mediaFeature, CSSParserValueList*);
+ ~MediaQueryExp();
+
+ const String& mediaFeature() const { return m_mediaFeature; }
+
+ MediaQueryExpValue expValue() const { return m_expValue; }
+
+ bool operator==(const MediaQueryExp& other) const;
bool isViewportDependent() const;
String serialize() const;
- PassOwnPtr<MediaQueryExp> copy() const { return adoptPtr(new MediaQueryExp(*this)); }
+ PassOwnPtrWillBeRawPtr<MediaQueryExp> copy() const { return adoptPtrWillBeNoop(new MediaQueryExp(*this)); }
+
+ MediaQueryExp(const MediaQueryExp& other);
+
+ void trace(Visitor* visitor) { }
private:
- MediaQueryExp(const AtomicString& mediaFeature, PassRefPtr<CSSValue>);
+ MediaQueryExp(const String&, const MediaQueryExpValue&);
- AtomicString m_mediaFeature;
- RefPtr<CSSValue> m_value;
+ String m_mediaFeature;
+ MediaQueryExpValue m_expValue;
};
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryList.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQueryList.cpp
index b55f3fb482d..d76b5bbec15 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryList.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryList.cpp
@@ -27,12 +27,12 @@
namespace WebCore {
-PassRefPtr<MediaQueryList> MediaQueryList::create(PassRefPtr<MediaQueryMatcher> vector, PassRefPtr<MediaQuerySet> media, bool matches)
+PassRefPtrWillBeRawPtr<MediaQueryList> MediaQueryList::create(PassRefPtrWillBeRawPtr<MediaQueryMatcher> vector, PassRefPtrWillBeRawPtr<MediaQuerySet> media, bool matches)
{
- return adoptRef(new MediaQueryList(vector, media, matches));
+ return adoptRefWillBeNoop(new MediaQueryList(vector, media, matches));
}
-MediaQueryList::MediaQueryList(PassRefPtr<MediaQueryMatcher> vector, PassRefPtr<MediaQuerySet> media, bool matches)
+MediaQueryList::MediaQueryList(PassRefPtrWillBeRawPtr<MediaQueryMatcher> vector, PassRefPtrWillBeRawPtr<MediaQuerySet> media, bool matches)
: m_matcher(vector)
, m_media(media)
, m_evaluationRound(m_matcher->evaluationRound())
@@ -41,16 +41,14 @@ MediaQueryList::MediaQueryList(PassRefPtr<MediaQueryMatcher> vector, PassRefPtr<
{
}
-MediaQueryList::~MediaQueryList()
-{
-}
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(MediaQueryList)
String MediaQueryList::media() const
{
return m_media->mediaText();
}
-void MediaQueryList::addListener(PassRefPtr<MediaQueryListListener> listener)
+void MediaQueryList::addListener(PassRefPtrWillBeRawPtr<MediaQueryListListener> listener)
{
if (!listener)
return;
@@ -58,7 +56,7 @@ void MediaQueryList::addListener(PassRefPtr<MediaQueryListListener> listener)
m_matcher->addListener(listener, this);
}
-void MediaQueryList::removeListener(PassRefPtr<MediaQueryListListener> listener)
+void MediaQueryList::removeListener(PassRefPtrWillBeRawPtr<MediaQueryListListener> listener)
{
if (!listener)
return;
@@ -66,11 +64,11 @@ void MediaQueryList::removeListener(PassRefPtr<MediaQueryListListener> listener)
m_matcher->removeListener(listener.get(), this);
}
-void MediaQueryList::evaluate(MediaQueryEvaluator* evaluator, bool& notificationNeeded)
+bool MediaQueryList::evaluate(MediaQueryEvaluator* evaluator)
{
if (m_evaluationRound != m_matcher->evaluationRound() && evaluator)
setMatches(evaluator->eval(m_media.get()));
- notificationNeeded = m_changeRound == m_matcher->evaluationRound();
+ return m_changeRound == m_matcher->evaluationRound();
}
void MediaQueryList::setMatches(bool newValue)
@@ -91,4 +89,10 @@ bool MediaQueryList::matches()
return m_matches;
}
+void MediaQueryList::trace(Visitor* visitor)
+{
+ visitor->trace(m_matcher);
+ visitor->trace(m_media);
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryList.h b/chromium/third_party/WebKit/Source/core/css/MediaQueryList.h
index a15bc6a304f..ba04100cc72 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryList.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryList.h
@@ -20,6 +20,7 @@
#ifndef MediaQueryList_h
#define MediaQueryList_h
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/RefCounted.h"
#include "wtf/RefPtr.h"
@@ -36,25 +37,26 @@ class MediaQuerySet;
// retrieve the current value of the given media query and to add/remove listeners that
// will be called whenever the value of the query changes.
-class MediaQueryList : public RefCounted<MediaQueryList> {
+class MediaQueryList FINAL : public RefCountedWillBeGarbageCollected<MediaQueryList> {
+ DECLARE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(MediaQueryList);
public:
- static PassRefPtr<MediaQueryList> create(PassRefPtr<MediaQueryMatcher>, PassRefPtr<MediaQuerySet>, bool);
- ~MediaQueryList();
-
+ static PassRefPtrWillBeRawPtr<MediaQueryList> create(PassRefPtrWillBeRawPtr<MediaQueryMatcher>, PassRefPtrWillBeRawPtr<MediaQuerySet>, bool);
String media() const;
bool matches();
- void addListener(PassRefPtr<MediaQueryListListener>);
- void removeListener(PassRefPtr<MediaQueryListListener>);
+ void addListener(PassRefPtrWillBeRawPtr<MediaQueryListListener>);
+ void removeListener(PassRefPtrWillBeRawPtr<MediaQueryListListener>);
+
+ bool evaluate(MediaQueryEvaluator*);
- void evaluate(MediaQueryEvaluator*, bool& notificationNeeded);
+ void trace(Visitor*);
private:
- MediaQueryList(PassRefPtr<MediaQueryMatcher>, PassRefPtr<MediaQuerySet>, bool matches);
+ MediaQueryList(PassRefPtrWillBeRawPtr<MediaQueryMatcher>, PassRefPtrWillBeRawPtr<MediaQuerySet>, bool matches);
void setMatches(bool);
- RefPtr<MediaQueryMatcher> m_matcher;
- RefPtr<MediaQuerySet> m_media;
+ RefPtrWillBeMember<MediaQueryMatcher> m_matcher;
+ RefPtrWillBeMember<MediaQuerySet> m_media;
unsigned m_evaluationRound; // Indicates if the query has been evaluated after the last style selector change.
unsigned m_changeRound; // Used to know if the query has changed in the last style selector change.
bool m_matches;
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryList.idl b/chromium/third_party/WebKit/Source/core/css/MediaQueryList.idl
index 7785d8dc2c6..c60c692ac79 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryList.idl
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryList.idl
@@ -17,7 +17,8 @@
* Boston, MA 02110-1301, USA.
*/
[
- NoInterfaceObject
+ NoInterfaceObject,
+ WillBeGarbageCollected
] interface MediaQueryList {
readonly attribute DOMString media;
readonly attribute boolean matches;
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.cpp
index 494883e7ed8..7cda1b4dc65 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.cpp
@@ -20,23 +20,26 @@
#include "config.h"
#include "core/css/MediaQueryListListener.h"
-#include "V8MediaQueryList.h"
-#include "bindings/v8/ScriptFunctionCall.h"
+#include "bindings/core/v8/V8MediaQueryList.h"
+#include "bindings/v8/V8Callback.h"
+#include <v8.h>
namespace WebCore {
-void MediaQueryListListener::queryChanged(ScriptState* state, MediaQueryList* query)
+MediaQueryListListener::MediaQueryListListener(ScriptState* scriptState, const ScriptValue& function)
+ : m_scriptState(scriptState)
+ , m_function(function)
{
- ScriptCallback callback(state, m_value);
- v8::HandleScope handleScope(state->isolate());
-
- v8::Handle<v8::Context> context = state->context();
- if (context.IsEmpty())
- return; // JS may not be enabled.
+ ASSERT(m_function.isFunction());
+}
- v8::Context::Scope scope(context);
- callback.appendArgument(ScriptValue(toV8(query, v8::Handle<v8::Object>(), context->GetIsolate()), context->GetIsolate()));
- callback.call();
+void MediaQueryListListener::queryChanged(MediaQueryList* query)
+{
+ if (m_scriptState->contextIsEmpty())
+ return;
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Handle<v8::Value> args[] = { toV8(query, m_scriptState->context()->Global(), m_scriptState->isolate()) };
+ invokeCallback(m_scriptState.get(), v8::Handle<v8::Function>::Cast(m_function.v8Value()), WTF_ARRAY_LENGTH(args), args);
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.h b/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.h
index fccf99dbef1..26a921f77db 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryListListener.h
@@ -22,6 +22,7 @@
#include "bindings/v8/ScriptState.h"
#include "bindings/v8/ScriptValue.h"
+#include "platform/heap/Handle.h"
#include "wtf/RefCounted.h"
namespace WebCore {
@@ -30,22 +31,25 @@ class MediaQueryList;
// See http://dev.w3.org/csswg/cssom-view/#the-mediaquerylist-interface
-class MediaQueryListListener : public RefCounted<MediaQueryListListener> {
+class MediaQueryListListener : public RefCountedWillBeGarbageCollectedFinalized<MediaQueryListListener> {
public:
- static PassRefPtr<MediaQueryListListener> create(const ScriptValue& value)
+ static PassRefPtrWillBeRawPtr<MediaQueryListListener> create(ScriptState* scriptState, const ScriptValue& value)
{
if (!value.isFunction())
- return 0;
- return adoptRef(new MediaQueryListListener(value));
+ return nullptr;
+ return adoptRefWillBeNoop(new MediaQueryListListener(scriptState, value));
}
- void queryChanged(ScriptState*, MediaQueryList*);
+ void queryChanged(MediaQueryList*);
- bool operator==(const MediaQueryListListener& other) const { return m_value == other.m_value; }
+ bool operator==(const MediaQueryListListener& other) const { return m_function == other.m_function; }
+
+ void trace(Visitor*) { }
private:
- MediaQueryListListener(const ScriptValue& value) : m_value(value) { }
+ MediaQueryListListener(ScriptState*, const ScriptValue&);
- ScriptValue m_value;
+ RefPtr<ScriptState> m_scriptState;
+ ScriptValue m_function;
};
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.cpp
index 9051099e17c..1821634634a 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.cpp
@@ -26,27 +26,27 @@
#include "core/css/MediaQueryListListener.h"
#include "core/css/resolver/StyleResolver.h"
#include "core/dom/Document.h"
-#include "core/frame/Frame.h"
#include "core/frame/FrameView.h"
+#include "core/frame/LocalFrame.h"
namespace WebCore {
-MediaQueryMatcher::Listener::Listener(PassRefPtr<MediaQueryListListener> listener, PassRefPtr<MediaQueryList> query)
+MediaQueryMatcher::Listener::Listener(PassRefPtrWillBeRawPtr<MediaQueryListListener> listener, PassRefPtrWillBeRawPtr<MediaQueryList> query)
: m_listener(listener)
, m_query(query)
{
}
-MediaQueryMatcher::Listener::~Listener()
+void MediaQueryMatcher::Listener::evaluate(MediaQueryEvaluator* evaluator)
{
+ if (m_query->evaluate(evaluator))
+ m_listener->queryChanged(m_query.get());
}
-void MediaQueryMatcher::Listener::evaluate(ScriptState* state, MediaQueryEvaluator* evaluator)
+void MediaQueryMatcher::Listener::trace(Visitor* visitor)
{
- bool notify;
- m_query->evaluate(evaluator, notify);
- if (notify)
- m_listener->queryChanged(state, m_query.get());
+ visitor->trace(m_listener);
+ visitor->trace(m_query);
}
MediaQueryMatcher::MediaQueryMatcher(Document* document)
@@ -56,14 +56,12 @@ MediaQueryMatcher::MediaQueryMatcher(Document* document)
ASSERT(m_document);
}
-MediaQueryMatcher::~MediaQueryMatcher()
-{
-}
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(MediaQueryMatcher)
void MediaQueryMatcher::documentDestroyed()
{
m_listeners.clear();
- m_document = 0;
+ m_document = nullptr;
}
AtomicString MediaQueryMatcher::mediaType() const
@@ -79,14 +77,7 @@ PassOwnPtr<MediaQueryEvaluator> MediaQueryMatcher::prepareEvaluator() const
if (!m_document || !m_document->frame())
return nullptr;
- Element* documentElement = m_document->documentElement();
- if (!documentElement)
- return nullptr;
-
- StyleResolver& styleResolver = m_document->ensureStyleResolver();
- RefPtr<RenderStyle> rootStyle = styleResolver.styleForElement(documentElement, 0 /*defaultParent*/, DisallowStyleSharing, MatchOnlyUserAgentRules);
-
- return adoptPtr(new MediaQueryEvaluator(mediaType(), m_document->frame(), rootStyle.get()));
+ return adoptPtr(new MediaQueryEvaluator(mediaType(), m_document->frame()));
}
bool MediaQueryMatcher::evaluate(const MediaQuerySet* media)
@@ -98,18 +89,18 @@ bool MediaQueryMatcher::evaluate(const MediaQuerySet* media)
return evaluator && evaluator->eval(media);
}
-PassRefPtr<MediaQueryList> MediaQueryMatcher::matchMedia(const String& query)
+PassRefPtrWillBeRawPtr<MediaQueryList> MediaQueryMatcher::matchMedia(const String& query)
{
if (!m_document)
- return 0;
+ return nullptr;
- RefPtr<MediaQuerySet> media = MediaQuerySet::create(query);
+ RefPtrWillBeRawPtr<MediaQuerySet> media = MediaQuerySet::create(query);
// Add warning message to inspector whenever dpi/dpcm values are used for "screen" media.
reportMediaQueryWarningIfNeeded(m_document, media.get());
return MediaQueryList::create(this, media, evaluate(media.get()));
}
-void MediaQueryMatcher::addListener(PassRefPtr<MediaQueryListListener> listener, PassRefPtr<MediaQueryList> query)
+void MediaQueryMatcher::addListener(PassRefPtrWillBeRawPtr<MediaQueryListListener> listener, PassRefPtrWillBeRawPtr<MediaQueryList> query)
{
if (!m_document)
return;
@@ -119,7 +110,7 @@ void MediaQueryMatcher::addListener(PassRefPtr<MediaQueryListListener> listener,
return;
}
- m_listeners.append(adoptPtr(new Listener(listener, query)));
+ m_listeners.append(adoptPtrWillBeNoop(new Listener(listener, query)));
}
void MediaQueryMatcher::removeListener(MediaQueryListListener* listener, MediaQueryList* query)
@@ -140,17 +131,23 @@ void MediaQueryMatcher::styleResolverChanged()
if (!m_document)
return;
- ScriptState* scriptState = m_document->frame() ? mainWorldScriptState(m_document->frame()) : 0;
- if (!scriptState)
- return;
-
++m_evaluationRound;
OwnPtr<MediaQueryEvaluator> evaluator = prepareEvaluator();
if (!evaluator)
return;
for (size_t i = 0; i < m_listeners.size(); ++i)
- m_listeners[i]->evaluate(scriptState, evaluator.get());
+ m_listeners[i]->evaluate(evaluator.get());
+}
+
+void MediaQueryMatcher::trace(Visitor* visitor)
+{
+ visitor->trace(m_document);
+ // We don't support tracing of vectors of OwnPtrs (ie. Vector<OwnPtr<Listener> >).
+ // Since this is a transitional object we are just ifdef'ing it out when oilpan is not enabled.
+#if ENABLE(OILPAN)
+ visitor->trace(m_listeners);
+#endif
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.h b/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.h
index 42945b485a1..abe862883b5 100644
--- a/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.h
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQueryMatcher.h
@@ -20,7 +20,7 @@
#ifndef MediaQueryMatcher_h
#define MediaQueryMatcher_h
-#include "bindings/v8/ScriptState.h"
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/RefCounted.h"
#include "wtf/Vector.h"
@@ -38,43 +38,45 @@ class MediaQuerySet;
// whenever it is needed and to call the listeners if the corresponding query has changed.
// The listeners must be called in the very same order in which they have been added.
-class MediaQueryMatcher : public RefCounted<MediaQueryMatcher> {
+class MediaQueryMatcher FINAL : public RefCountedWillBeGarbageCollected<MediaQueryMatcher> {
+ DECLARE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(MediaQueryMatcher);
public:
- static PassRefPtr<MediaQueryMatcher> create(Document* document) { return adoptRef(new MediaQueryMatcher(document)); }
- ~MediaQueryMatcher();
+ static PassRefPtrWillBeRawPtr<MediaQueryMatcher> create(Document* document) { return adoptRefWillBeNoop(new MediaQueryMatcher(document)); }
void documentDestroyed();
- void addListener(PassRefPtr<MediaQueryListListener>, PassRefPtr<MediaQueryList>);
+ void addListener(PassRefPtrWillBeRawPtr<MediaQueryListListener>, PassRefPtrWillBeRawPtr<MediaQueryList>);
void removeListener(MediaQueryListListener*, MediaQueryList*);
- PassRefPtr<MediaQueryList> matchMedia(const String&);
+ PassRefPtrWillBeRawPtr<MediaQueryList> matchMedia(const String&);
unsigned evaluationRound() const { return m_evaluationRound; }
void styleResolverChanged();
bool evaluate(const MediaQuerySet*);
+ void trace(Visitor*);
+
private:
- class Listener {
+ class Listener FINAL : public NoBaseWillBeGarbageCollected<Listener> {
public:
- Listener(PassRefPtr<MediaQueryListListener>, PassRefPtr<MediaQueryList>);
- ~Listener();
-
- void evaluate(ScriptState*, MediaQueryEvaluator*);
+ Listener(PassRefPtrWillBeRawPtr<MediaQueryListListener>, PassRefPtrWillBeRawPtr<MediaQueryList>);
+ void evaluate(MediaQueryEvaluator*);
MediaQueryListListener* listener() { return m_listener.get(); }
MediaQueryList* query() { return m_query.get(); }
+ void trace(Visitor*);
+
private:
- RefPtr<MediaQueryListListener> m_listener;
- RefPtr<MediaQueryList> m_query;
+ RefPtrWillBeMember<MediaQueryListListener> m_listener;
+ RefPtrWillBeMember<MediaQueryList> m_query;
};
MediaQueryMatcher(Document*);
PassOwnPtr<MediaQueryEvaluator> prepareEvaluator() const;
AtomicString mediaType() const;
- Document* m_document;
- Vector<OwnPtr<Listener> > m_listeners;
+ RawPtrWillBeMember<Document> m_document;
+ WillBeHeapVector<OwnPtrWillBeMember<Listener> > m_listeners;
// This value is incremented at style selector changes.
// It is used to avoid evaluating queries more then once and to make sure
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaQuerySetTest.cpp b/chromium/third_party/WebKit/Source/core/css/MediaQuerySetTest.cpp
new file mode 100644
index 00000000000..834625e3ece
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaQuerySetTest.cpp
@@ -0,0 +1,171 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/MediaQuery.h"
+
+#include "core/css/MediaList.h"
+#include "wtf/PassOwnPtr.h"
+#include "wtf/text/StringBuilder.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+typedef struct {
+ const char* input;
+ const char* output;
+ bool shouldWorkOnOldParser;
+} TestCase;
+
+static void testMediaQuery(TestCase test, MediaQuerySet& querySet, bool oldParser)
+{
+ StringBuilder output;
+ size_t j = 0;
+ while (j < querySet.queryVector().size()) {
+ String queryText = querySet.queryVector()[j]->cssText();
+ output.append(queryText);
+ ++j;
+ if (j >= querySet.queryVector().size())
+ break;
+ output.append(", ");
+ }
+ if (!oldParser || test.shouldWorkOnOldParser) {
+ if (test.output)
+ ASSERT_STREQ(test.output, output.toString().ascii().data());
+ else
+ ASSERT_STREQ(test.input, output.toString().ascii().data());
+ }
+}
+
+TEST(MediaQuerySetTest, Basic)
+{
+ // The first string represents the input string.
+ // The second string represents the output string, if present.
+ // Otherwise, the output string is identical to the first string.
+ TestCase testCases[] = {
+ {"", 0, true},
+ {" ", "", true},
+ {"screen", 0, true},
+ {"screen and (color)", 0, true},
+ {"all and (min-width:500px)", "(min-width: 500px)", true},
+ {"all and (min-width:/*bla*/500px)", "(min-width: 500px)", true},
+ {"(min-width:500px)", "(min-width: 500px)", true},
+ {"screen and (color), projection and (color)", 0, true},
+ {"not screen and (color)", 0, true},
+ {"only screen and (color)", 0, true},
+ {"screen and (color), projection and (color)", 0, true},
+ {"aural and (device-aspect-ratio: 16/9)", 0, true},
+ {"speech and (min-device-width: 800px)", 0, true},
+ {"example", 0, true},
+ {"screen and (max-weight: 3kg) and (color), (monochrome)", "not all, (monochrome)", true},
+ {"(min-width: -100px)", "not all", true},
+ {"(example, all,), speech", "not all, speech", true},
+ {"&test, screen", "not all, screen", true},
+ {"print and (min-width: 25cm)", 0, true},
+ {"screen and (min-width: 400px) and (max-width: 700px)", "screen and (max-width: 700px) and (min-width: 400px)", true},
+ {"screen and (device-width: 800px)", 0, true},
+ {"screen and (device-height: 60em)", 0, true},
+ {"screen and (device-aspect-ratio: 16/9)", 0, true},
+ {"(device-aspect-ratio: 16.0/9.0)", "not all", true},
+ {"(device-aspect-ratio: 16/ 9)", "(device-aspect-ratio: 16/9)", true},
+ {"(device-aspect-ratio: 16/\r9)", "(device-aspect-ratio: 16/9)", true},
+ {"all and (color)", "(color)", true},
+ {"all and (min-color: 1)", "(min-color: 1)", true},
+ {"all and (min-color: 1.0)", "not all", true},
+ {"all and (min-color: 2)", "(min-color: 2)", true},
+ {"all and (color-index)", "(color-index)", true},
+ {"all and (min-color-index: 1)", "(min-color-index: 1)", true},
+ {"all and (monochrome)", "(monochrome)", true},
+ {"all and (min-monochrome: 1)", "(min-monochrome: 1)", true},
+ {"all and (min-monochrome: 2)", "(min-monochrome: 2)", true},
+ {"print and (monochrome)", 0, true},
+ {"handheld and (grid) and (max-width: 15em)", 0, true},
+ {"handheld and (grid) and (max-device-height: 7em)", 0, true},
+ {"screen and (max-width: 50%)", "not all", true},
+ {"screen and (max-WIDTH: 500px)", "screen and (max-width: 500px)", true},
+ {"screen and (max-width: 24.4em)", 0, true},
+ {"screen and (max-width: 24.4EM)", "screen and (max-width: 24.4em)", true},
+ {"screen and (max-width: blabla)", "not all", true},
+ {"screen and (max-width: 1)", "not all", true},
+ {"screen and (max-width: 0)", 0, true},
+ {"screen and (max-width: 1deg)", "not all", true},
+ {"handheld and (min-width: 20em), \nscreen and (min-width: 20em)", "handheld and (min-width: 20em), screen and (min-width: 20em)", true},
+ {"print and (min-resolution: 300dpi)", 0, true},
+ {"print and (min-resolution: 118dpcm)", 0, true},
+ {"(resolution: 0.83333333333333333333dppx)", "(resolution: 0.833333333333333dppx)", true},
+ {"(resolution: 2.4dppx)", 0, true},
+ {"all and(color)", "not all", true},
+ {"all and (", "not all", true},
+ {"test;,all", "not all, all", true},
+ {"(color:20example)", "not all", false},
+ {"not braille", 0, true},
+ {",screen", "not all, screen", true},
+ {",all", "not all, all", true},
+ {",,all,,", "not all, not all, all, not all, not all", true},
+ {",,all,, ", "not all, not all, all, not all, not all", true},
+ {",screen,,&invalid,,", "not all, screen, not all, not all, not all, not all", true},
+ {",screen,,(invalid,),,", "not all, screen, not all, not all, not all, not all", true},
+ {",(all,),,", "not all, not all, not all, not all", true},
+ {",", "not all, not all", true},
+ {" ", "", true},
+ {"(color", "(color)", true},
+ {"(min-color: 2", "(min-color: 2)", true},
+ {"(orientation: portrait)", 0, true},
+ {"tv and (scan: progressive)", 0, true},
+ {"(pointer: coarse)", 0, true},
+ {"(min-orientation:portrait)", "not all", true},
+ {"all and (orientation:portrait)", "(orientation: portrait)", true},
+ {"all and (orientation:landscape)", "(orientation: landscape)", true},
+ {"NOT braille, tv AND (max-width: 200px) and (min-WIDTH: 100px) and (orientation: landscape), (color)",
+ "not braille, tv and (max-width: 200px) and (min-width: 100px) and (orientation: landscape), (color)", true},
+ {"(m\\61x-width: 300px)", "(max-width: 300px)", true},
+ {"(max-width: 400\\70\\78)", "(max-width: 400px)", false},
+ {"(max-width: 500\\0070\\0078)", "(max-width: 500px)", false},
+ {"(max-width: 600\\000070\\000078)", "(max-width: 600px)", false},
+ {"(max-width: 700px), (max-width: 700px)", "(max-width: 700px), (max-width: 700px)", true},
+ {"(max-width: 800px()), (max-width: 800px)", "not all, (max-width: 800px)", true},
+ {"(max-width: 900px(()), (max-width: 900px)", "not all", true},
+ {"(max-width: 600px(())))), (max-width: 600px)", "not all, (max-width: 600px)", true},
+ {"(max-width: 500px(((((((((())))), (max-width: 500px)", "not all", true},
+ {"(max-width: 800px[]), (max-width: 800px)", "not all, (max-width: 800px)", true},
+ {"(max-width: 900px[[]), (max-width: 900px)", "not all", true},
+ {"(max-width: 600px[[]]]]), (max-width: 600px)", "not all, (max-width: 600px)", true},
+ {"(max-width: 500px[[[[[[[[[[]]]]), (max-width: 500px)", "not all", true},
+ {"(max-width: 800px{}), (max-width: 800px)", "not all, (max-width: 800px)", true},
+ {"(max-width: 900px{{}), (max-width: 900px)", "not all", true},
+ {"(max-width: 600px{{}}}}), (max-width: 600px)", "not all, (max-width: 600px)", true},
+ {"(max-width: 500px{{{{{{{{{{}}}}), (max-width: 500px)", "not all", true},
+ {"[(), (max-width: 400px)", "not all", true},
+ {"[{}, (max-width: 500px)", "not all", true},
+ {"[{]}], (max-width: 900px)", "not all, (max-width: 900px)", true},
+ {"[{[]{}{{{}}}}], (max-width: 900px)", "not all, (max-width: 900px)", true},
+ {"[{[}], (max-width: 900px)", "not all", true},
+ {"[({)}], (max-width: 900px)", "not all", true},
+ {"[]((), (max-width: 900px)", "not all", true},
+ {"((), (max-width: 900px)", "not all", true},
+ {"(foo(), (max-width: 900px)", "not all", true},
+ {"[](()), (max-width: 900px)", "not all, (max-width: 900px)", true},
+ {"all an[isdfs bla())()]icalc(i)(()), (max-width: 400px)", "not all, (max-width: 400px)", true},
+ {"all an[isdfs bla())(]icalc(i)(()), (max-width: 500px)", "not all", true},
+ {"all an[isdfs bla())(]icalc(i)(())), (max-width: 600px)", "not all", true},
+ {"all an[isdfs bla())(]icalc(i)(()))], (max-width: 800px)", "not all, (max-width: 800px)", true},
+ {"(max-width: '40px')", "not all", true},
+ {"('max-width': 40px)", "not all", true},
+ {"'\"'\", (max-width: 900px)", "not all", true},
+ {"'\"\"\"', (max-width: 900px)", "not all, (max-width: 900px)", true},
+ {"\"'\"', (max-width: 900px)", "not all", true},
+ {"\"'''\", (max-width: 900px)", "not all, (max-width: 900px)", true},
+ {0, 0} // Do not remove the terminator line.
+ };
+
+ for (unsigned i = 0; testCases[i].input; ++i) {
+ RefPtrWillBeRawPtr<MediaQuerySet> oldParserQuerySet = MediaQuerySet::create(testCases[i].input);
+ RefPtrWillBeRawPtr<MediaQuerySet> threadSafeQuerySet = MediaQuerySet::createOffMainThread(testCases[i].input);
+ testMediaQuery(testCases[i], *oldParserQuerySet, true);
+ testMediaQuery(testCases[i], *threadSafeQuerySet, false);
+ }
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaTypeNames.in b/chromium/third_party/WebKit/Source/core/css/MediaTypeNames.in
new file mode 100644
index 00000000000..556996d8c61
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaTypeNames.in
@@ -0,0 +1,15 @@
+namespace="MediaType"
+export=""
+
+# http://www.w3.org/TR/CSS2/media.html#media-types
+
+all
+braille
+embossed
+handheld
+print
+projection
+screen
+speech
+tty
+tv
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValues.cpp b/chromium/third_party/WebKit/Source/core/css/MediaValues.cpp
new file mode 100644
index 00000000000..a2d5e1b63c6
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValues.cpp
@@ -0,0 +1,206 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/MediaValues.h"
+
+#include "core/css/CSSHelper.h"
+#include "core/css/MediaValuesCached.h"
+#include "core/css/MediaValuesDynamic.h"
+#include "core/dom/Document.h"
+#include "core/dom/Element.h"
+#include "core/frame/FrameHost.h"
+#include "core/frame/FrameView.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/Settings.h"
+#include "core/page/Page.h"
+#include "core/rendering/RenderObject.h"
+#include "core/rendering/RenderView.h"
+#include "core/rendering/compositing/RenderLayerCompositor.h"
+#include "core/rendering/style/RenderStyle.h"
+#include "platform/PlatformScreen.h"
+
+namespace WebCore {
+
+PassRefPtr<MediaValues> MediaValues::createDynamicIfFrameExists(LocalFrame* frame)
+{
+ if (frame)
+ return MediaValuesDynamic::create(frame);
+ return MediaValuesCached::create();
+}
+
+int MediaValues::calculateViewportWidth(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view() && frame->document());
+ int viewportWidth = frame->view()->layoutSize(IncludeScrollbars).width();
+ return adjustForAbsoluteZoom(viewportWidth, frame->document()->renderView());
+}
+
+int MediaValues::calculateViewportHeight(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view() && frame->document());
+ int viewportHeight = frame->view()->layoutSize(IncludeScrollbars).height();
+ return adjustForAbsoluteZoom(viewportHeight, frame->document()->renderView());
+}
+
+int MediaValues::calculateDeviceWidth(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view() && frame->settings() && frame->host());
+ int deviceWidth = static_cast<int>(screenRect(frame->view()).width());
+ if (frame->settings()->reportScreenSizeInPhysicalPixelsQuirk())
+ deviceWidth = lroundf(deviceWidth * frame->host()->deviceScaleFactor());
+ return deviceWidth;
+}
+
+int MediaValues::calculateDeviceHeight(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view() && frame->settings() && frame->host());
+ int deviceHeight = static_cast<int>(screenRect(frame->view()).height());
+ if (frame->settings()->reportScreenSizeInPhysicalPixelsQuirk())
+ deviceHeight = lroundf(deviceHeight * frame->host()->deviceScaleFactor());
+ return deviceHeight;
+}
+
+bool MediaValues::calculateStrictMode(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->document());
+ return !frame->document()->inQuirksMode();
+}
+
+float MediaValues::calculateDevicePixelRatio(LocalFrame* frame) const
+{
+ return frame->devicePixelRatio();
+}
+
+int MediaValues::calculateColorBitsPerComponent(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->page() && frame->page()->mainFrame());
+ if (!frame->page()->mainFrame()->isLocalFrame()
+ || screenIsMonochrome(frame->page()->deprecatedLocalMainFrame()->view()))
+ return 0;
+ return screenDepthPerComponent(frame->view());
+}
+
+int MediaValues::calculateMonochromeBitsPerComponent(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->page() && frame->page()->mainFrame());
+ if (!frame->page()->mainFrame()->isLocalFrame()
+ || !screenIsMonochrome(frame->page()->deprecatedLocalMainFrame()->view()))
+ return 0;
+ return screenDepthPerComponent(frame->view());
+}
+
+int MediaValues::calculateDefaultFontSize(LocalFrame* frame) const
+{
+ return frame->host()->settings().defaultFontSize();
+}
+
+bool MediaValues::calculateScanMediaType(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view());
+ // Scan only applies to 'tv' media.
+ return equalIgnoringCase(frame->view()->mediaType(), "tv");
+}
+
+bool MediaValues::calculateScreenMediaType(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view());
+ return equalIgnoringCase(frame->view()->mediaType(), "screen");
+}
+
+bool MediaValues::calculatePrintMediaType(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->view());
+ return equalIgnoringCase(frame->view()->mediaType(), "print");
+}
+
+bool MediaValues::calculateThreeDEnabled(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->contentRenderer() && frame->contentRenderer()->compositor());
+ bool threeDEnabled = false;
+ if (RenderView* view = frame->contentRenderer())
+ threeDEnabled = view->compositor()->hasAcceleratedCompositing();
+ return threeDEnabled;
+}
+
+MediaValues::PointerDeviceType MediaValues::calculateLeastCapablePrimaryPointerDeviceType(LocalFrame* frame) const
+{
+ ASSERT(frame && frame->settings());
+ if (frame->settings()->deviceSupportsTouch())
+ return MediaValues::TouchPointer;
+
+ // FIXME: We should also try to determine if we know we have a mouse.
+ // When we do this, we'll also need to differentiate between known not to
+ // have mouse or touch screen (NoPointer) and unknown (UnknownPointer).
+ // We could also take into account other preferences like accessibility
+ // settings to decide which of the available pointers should be considered
+ // "primary".
+
+ return MediaValues::UnknownPointer;
+}
+
+bool MediaValues::computeLengthImpl(double value, CSSPrimitiveValue::UnitType type, unsigned defaultFontSize, unsigned viewportWidth, unsigned viewportHeight, double& result)
+{
+ // The logic in this function is duplicated from CSSPrimitiveValue::computeLengthDouble
+ // because MediaValues::computeLength needs nearly identical logic, but we haven't found a way to make
+ // CSSPrimitiveValue::computeLengthDouble more generic (to solve both cases) without hurting performance.
+
+ // FIXME - Unite the logic here with CSSPrimitiveValue in a performant way.
+ double factor = 0;
+ switch (type) {
+ case CSSPrimitiveValue::CSS_EMS:
+ case CSSPrimitiveValue::CSS_REMS:
+ factor = defaultFontSize;
+ break;
+ case CSSPrimitiveValue::CSS_PX:
+ factor = 1;
+ break;
+ case CSSPrimitiveValue::CSS_EXS:
+ // FIXME: We have a bug right now where the zoom will be applied twice to EX units.
+ // FIXME: We don't seem to be able to cache fontMetrics related values.
+ // Trying to access them is triggering some sort of microtask. Serving the spec's default instead.
+ factor = defaultFontSize / 2.0;
+ break;
+ case CSSPrimitiveValue::CSS_CHS:
+ // FIXME: We don't seem to be able to cache fontMetrics related values.
+ // Trying to access them is triggering some sort of microtask. Serving the (future) spec default instead.
+ factor = defaultFontSize / 2.0;
+ break;
+ case CSSPrimitiveValue::CSS_VW:
+ factor = viewportWidth / 100.0;
+ break;
+ case CSSPrimitiveValue::CSS_VH:
+ factor = viewportHeight / 100.0;
+ break;
+ case CSSPrimitiveValue::CSS_VMIN:
+ factor = std::min(viewportWidth, viewportHeight) / 100.0;
+ break;
+ case CSSPrimitiveValue::CSS_VMAX:
+ factor = std::max(viewportWidth, viewportHeight) / 100.0;
+ break;
+ case CSSPrimitiveValue::CSS_CM:
+ factor = cssPixelsPerCentimeter;
+ break;
+ case CSSPrimitiveValue::CSS_MM:
+ factor = cssPixelsPerMillimeter;
+ break;
+ case CSSPrimitiveValue::CSS_IN:
+ factor = cssPixelsPerInch;
+ break;
+ case CSSPrimitiveValue::CSS_PT:
+ factor = cssPixelsPerPoint;
+ break;
+ case CSSPrimitiveValue::CSS_PC:
+ factor = cssPixelsPerPica;
+ break;
+ default:
+ return false;
+ }
+
+ ASSERT(factor > 0);
+ result = value * factor;
+ return true;
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValues.h b/chromium/third_party/WebKit/Source/core/css/MediaValues.h
new file mode 100644
index 00000000000..eee54657b37
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValues.h
@@ -0,0 +1,88 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaValues_h
+#define MediaValues_h
+
+#include "core/css/CSSPrimitiveValue.h"
+#include "wtf/RefCounted.h"
+#include "wtf/RefPtr.h"
+
+namespace WebCore {
+
+class Document;
+class CSSPrimitiveValue;
+class LocalFrame;
+
+class MediaValues : public RefCounted<MediaValues> {
+public:
+
+ enum MediaValuesMode {
+ CachingMode,
+ DynamicMode
+ };
+
+ enum PointerDeviceType {
+ TouchPointer,
+ MousePointer,
+ NoPointer,
+ UnknownPointer
+ };
+
+ virtual ~MediaValues() { }
+
+ static PassRefPtr<MediaValues> createDynamicIfFrameExists(LocalFrame*);
+ virtual PassRefPtr<MediaValues> copy() const = 0;
+ virtual bool isSafeToSendToAnotherThread() const = 0;
+
+ static bool computeLengthImpl(double value, CSSPrimitiveValue::UnitType, unsigned defaultFontSize, unsigned viewportWidth, unsigned viewportHeight, double& result);
+ template<typename T>
+ static bool computeLength(double value, CSSPrimitiveValue::UnitType type, unsigned defaultFontSize, unsigned viewportWidth, unsigned viewportHeight, T& result)
+ {
+ double tempResult;
+ if (!computeLengthImpl(value, type, defaultFontSize, viewportWidth, viewportHeight, tempResult))
+ return false;
+ result = roundForImpreciseConversion<T>(tempResult);
+ return true;
+ }
+ virtual bool computeLength(double value, CSSPrimitiveValue::UnitType, int& result) const = 0;
+ virtual bool computeLength(double value, CSSPrimitiveValue::UnitType, double& result) const = 0;
+
+ virtual int viewportWidth() const = 0;
+ virtual int viewportHeight() const = 0;
+ virtual int deviceWidth() const = 0;
+ virtual int deviceHeight() const = 0;
+ virtual float devicePixelRatio() const = 0;
+ virtual int colorBitsPerComponent() const = 0;
+ virtual int monochromeBitsPerComponent() const = 0;
+ virtual PointerDeviceType pointer() const = 0;
+ virtual bool threeDEnabled() const = 0;
+ virtual bool scanMediaType() const = 0;
+ virtual bool screenMediaType() const = 0;
+ virtual bool printMediaType() const = 0;
+ virtual bool strictMode() const = 0;
+ virtual Document* document() const = 0;
+ virtual bool hasValues() const = 0;
+
+protected:
+ int calculateViewportWidth(LocalFrame*) const;
+ int calculateViewportHeight(LocalFrame*) const;
+ int calculateDeviceWidth(LocalFrame*) const;
+ int calculateDeviceHeight(LocalFrame*) const;
+ bool calculateStrictMode(LocalFrame*) const;
+ float calculateDevicePixelRatio(LocalFrame*) const;
+ int calculateColorBitsPerComponent(LocalFrame*) const;
+ int calculateMonochromeBitsPerComponent(LocalFrame*) const;
+ int calculateDefaultFontSize(LocalFrame*) const;
+ bool calculateScanMediaType(LocalFrame*) const;
+ bool calculateScreenMediaType(LocalFrame*) const;
+ bool calculatePrintMediaType(LocalFrame*) const;
+ bool calculateThreeDEnabled(LocalFrame*) const;
+ MediaValues::PointerDeviceType calculateLeastCapablePrimaryPointerDeviceType(LocalFrame*) const;
+
+};
+
+} // namespace
+
+#endif // MediaValues_h
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValuesCached.cpp b/chromium/third_party/WebKit/Source/core/css/MediaValuesCached.cpp
new file mode 100644
index 00000000000..570a3a51709
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValuesCached.cpp
@@ -0,0 +1,169 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/MediaValuesCached.h"
+
+#include "core/css/CSSPrimitiveValue.h"
+#include "core/dom/Document.h"
+#include "core/frame/LocalFrame.h"
+#include "core/html/imports/HTMLImportsController.h"
+#include "core/rendering/RenderObject.h"
+
+namespace WebCore {
+
+PassRefPtr<MediaValues> MediaValuesCached::create()
+{
+ return adoptRef(new MediaValuesCached());
+}
+
+PassRefPtr<MediaValues> MediaValuesCached::create(MediaValuesCachedData& data)
+{
+ return adoptRef(new MediaValuesCached(data));
+}
+
+PassRefPtr<MediaValues> MediaValuesCached::create(Document& document)
+{
+ Document* executingDocument = document.importsController() ? document.importsController()->master() : &document;
+ ASSERT(executingDocument);
+ return MediaValuesCached::create(executingDocument->frame());
+}
+
+PassRefPtr<MediaValues> MediaValuesCached::create(LocalFrame* frame)
+{
+ // FIXME - Added an assert here so we can better understand when a frame is present without its view().
+ ASSERT(!frame || frame->view());
+ // FIXME - Because of crbug.com/371084, document()->renderView() may be null here.
+ if (!frame || !frame->view() || !frame->document() || !frame->document()->renderView())
+ return adoptRef(new MediaValuesCached());
+ return adoptRef(new MediaValuesCached(frame));
+}
+
+MediaValuesCached::MediaValuesCached()
+{
+}
+
+MediaValuesCached::MediaValuesCached(LocalFrame* frame)
+{
+ ASSERT(isMainThread());
+ ASSERT(frame);
+ // In case that frame is missing (e.g. for images that their document does not have a frame)
+ // We simply leave the MediaValues object with the default MediaValuesCachedData values.
+ m_data.viewportWidth = calculateViewportWidth(frame);
+ m_data.viewportHeight = calculateViewportHeight(frame);
+ m_data.deviceWidth = calculateDeviceWidth(frame);
+ m_data.deviceHeight = calculateDeviceHeight(frame);
+ m_data.devicePixelRatio = calculateDevicePixelRatio(frame);
+ m_data.colorBitsPerComponent = calculateColorBitsPerComponent(frame);
+ m_data.monochromeBitsPerComponent = calculateMonochromeBitsPerComponent(frame);
+ m_data.pointer = calculateLeastCapablePrimaryPointerDeviceType(frame);
+ m_data.defaultFontSize = calculateDefaultFontSize(frame);
+ m_data.threeDEnabled = calculateThreeDEnabled(frame);
+ m_data.scanMediaType = calculateScanMediaType(frame);
+ m_data.screenMediaType = calculateScreenMediaType(frame);
+ m_data.printMediaType = calculatePrintMediaType(frame);
+ m_data.strictMode = calculateStrictMode(frame);
+}
+
+MediaValuesCached::MediaValuesCached(const MediaValuesCachedData& data)
+ : m_data(data)
+{
+}
+
+PassRefPtr<MediaValues> MediaValuesCached::copy() const
+{
+ return adoptRef(new MediaValuesCached(m_data));
+}
+
+bool MediaValuesCached::computeLength(double value, CSSPrimitiveValue::UnitType type, int& result) const
+{
+ return MediaValues::computeLength(value, type, m_data.defaultFontSize, m_data.viewportWidth, m_data.viewportHeight, result);
+}
+
+bool MediaValuesCached::computeLength(double value, CSSPrimitiveValue::UnitType type, double& result) const
+{
+ return MediaValues::computeLength(value, type, m_data.defaultFontSize, m_data.viewportWidth, m_data.viewportHeight, result);
+}
+
+bool MediaValuesCached::isSafeToSendToAnotherThread() const
+{
+ return hasOneRef();
+}
+
+int MediaValuesCached::viewportWidth() const
+{
+ return m_data.viewportWidth;
+}
+
+int MediaValuesCached::viewportHeight() const
+{
+ return m_data.viewportHeight;
+}
+
+int MediaValuesCached::deviceWidth() const
+{
+ return m_data.deviceWidth;
+}
+
+int MediaValuesCached::deviceHeight() const
+{
+ return m_data.deviceHeight;
+}
+
+float MediaValuesCached::devicePixelRatio() const
+{
+ return m_data.devicePixelRatio;
+}
+
+int MediaValuesCached::colorBitsPerComponent() const
+{
+ return m_data.colorBitsPerComponent;
+}
+
+int MediaValuesCached::monochromeBitsPerComponent() const
+{
+ return m_data.monochromeBitsPerComponent;
+}
+
+MediaValues::PointerDeviceType MediaValuesCached::pointer() const
+{
+ return m_data.pointer;
+}
+
+bool MediaValuesCached::threeDEnabled() const
+{
+ return m_data.threeDEnabled;
+}
+
+bool MediaValuesCached::scanMediaType() const
+{
+ return m_data.scanMediaType;
+}
+
+bool MediaValuesCached::screenMediaType() const
+{
+ return m_data.screenMediaType;
+}
+
+bool MediaValuesCached::printMediaType() const
+{
+ return m_data.printMediaType;
+}
+
+bool MediaValuesCached::strictMode() const
+{
+ return m_data.strictMode;
+}
+
+Document* MediaValuesCached::document() const
+{
+ return 0;
+}
+
+bool MediaValuesCached::hasValues() const
+{
+ return true;
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValuesCached.h b/chromium/third_party/WebKit/Source/core/css/MediaValuesCached.h
new file mode 100644
index 00000000000..c3ff031c884
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValuesCached.h
@@ -0,0 +1,85 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaValuesCached_h
+#define MediaValuesCached_h
+
+#include "core/css/MediaValues.h"
+
+namespace WebCore {
+
+class MediaValuesCached FINAL : public MediaValues {
+public:
+ struct MediaValuesCachedData {
+ // Members variables must be thread safe, since they're copied to the parser thread
+ int viewportWidth;
+ int viewportHeight;
+ int deviceWidth;
+ int deviceHeight;
+ float devicePixelRatio;
+ int colorBitsPerComponent;
+ int monochromeBitsPerComponent;
+ PointerDeviceType pointer;
+ int defaultFontSize;
+ bool threeDEnabled;
+ bool scanMediaType;
+ bool screenMediaType;
+ bool printMediaType;
+ bool strictMode;
+
+ MediaValuesCachedData()
+ : viewportWidth(0)
+ , viewportHeight(0)
+ , deviceWidth(0)
+ , deviceHeight(0)
+ , devicePixelRatio(1.0)
+ , colorBitsPerComponent(24)
+ , monochromeBitsPerComponent(0)
+ , pointer(UnknownPointer)
+ , defaultFontSize(16)
+ , threeDEnabled(false)
+ , scanMediaType(false)
+ , screenMediaType(true)
+ , printMediaType(false)
+ , strictMode(true)
+ {
+ }
+ };
+
+ static PassRefPtr<MediaValues> create();
+ static PassRefPtr<MediaValues> create(Document&);
+ static PassRefPtr<MediaValues> create(LocalFrame*);
+ static PassRefPtr<MediaValues> create(MediaValuesCachedData&);
+ virtual PassRefPtr<MediaValues> copy() const OVERRIDE;
+ virtual bool isSafeToSendToAnotherThread() const OVERRIDE;
+ virtual bool computeLength(double value, CSSPrimitiveValue::UnitType, int& result) const OVERRIDE;
+ virtual bool computeLength(double value, CSSPrimitiveValue::UnitType, double& result) const OVERRIDE;
+
+ virtual int viewportWidth() const OVERRIDE;
+ virtual int viewportHeight() const OVERRIDE;
+ virtual int deviceWidth() const OVERRIDE;
+ virtual int deviceHeight() const OVERRIDE;
+ virtual float devicePixelRatio() const OVERRIDE;
+ virtual int colorBitsPerComponent() const OVERRIDE;
+ virtual int monochromeBitsPerComponent() const OVERRIDE;
+ virtual PointerDeviceType pointer() const OVERRIDE;
+ virtual bool threeDEnabled() const OVERRIDE;
+ virtual bool scanMediaType() const OVERRIDE;
+ virtual bool screenMediaType() const OVERRIDE;
+ virtual bool printMediaType() const OVERRIDE;
+ virtual bool strictMode() const OVERRIDE;
+ virtual Document* document() const OVERRIDE;
+ virtual bool hasValues() const OVERRIDE;
+
+protected:
+ MediaValuesCached();
+ MediaValuesCached(LocalFrame*);
+ MediaValuesCached(const MediaValuesCachedData&);
+
+ MediaValuesCachedData m_data;
+};
+
+} // namespace
+
+#endif // MediaValuesCached_h
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.cpp b/chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.cpp
new file mode 100644
index 00000000000..2ac823feb98
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.cpp
@@ -0,0 +1,132 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/MediaValuesDynamic.h"
+
+#include "core/css/CSSHelper.h"
+#include "core/css/CSSPrimitiveValue.h"
+#include "core/css/CSSToLengthConversionData.h"
+#include "core/dom/Document.h"
+#include "core/frame/LocalFrame.h"
+
+namespace WebCore {
+
+PassRefPtr<MediaValues> MediaValuesDynamic::create(LocalFrame* frame)
+{
+ return adoptRef(new MediaValuesDynamic(frame));
+}
+
+MediaValuesDynamic::MediaValuesDynamic(LocalFrame* frame)
+ : m_frame(frame)
+{
+ ASSERT(m_frame);
+}
+
+PassRefPtr<MediaValues> MediaValuesDynamic::copy() const
+{
+ return adoptRef(new MediaValuesDynamic(m_frame));
+}
+
+bool MediaValuesDynamic::computeLength(double value, CSSPrimitiveValue::UnitType type, int& result) const
+{
+ return MediaValues::computeLength(value,
+ type,
+ calculateDefaultFontSize(m_frame),
+ calculateViewportWidth(m_frame),
+ calculateViewportHeight(m_frame),
+ result);
+}
+
+bool MediaValuesDynamic::computeLength(double value, CSSPrimitiveValue::UnitType type, double& result) const
+{
+ return MediaValues::computeLength(value,
+ type,
+ calculateDefaultFontSize(m_frame),
+ calculateViewportWidth(m_frame),
+ calculateViewportHeight(m_frame),
+ result);
+}
+
+bool MediaValuesDynamic::isSafeToSendToAnotherThread() const
+{
+ return false;
+}
+
+int MediaValuesDynamic::viewportWidth() const
+{
+ return calculateViewportWidth(m_frame);
+}
+
+int MediaValuesDynamic::viewportHeight() const
+{
+ return calculateViewportHeight(m_frame);
+}
+
+int MediaValuesDynamic::deviceWidth() const
+{
+ return calculateDeviceWidth(m_frame);
+}
+
+int MediaValuesDynamic::deviceHeight() const
+{
+ return calculateDeviceHeight(m_frame);
+}
+
+float MediaValuesDynamic::devicePixelRatio() const
+{
+ return calculateDevicePixelRatio(m_frame);
+}
+
+int MediaValuesDynamic::colorBitsPerComponent() const
+{
+ return calculateColorBitsPerComponent(m_frame);
+}
+
+int MediaValuesDynamic::monochromeBitsPerComponent() const
+{
+ return calculateMonochromeBitsPerComponent(m_frame);
+}
+
+MediaValues::PointerDeviceType MediaValuesDynamic::pointer() const
+{
+ return calculateLeastCapablePrimaryPointerDeviceType(m_frame);
+}
+
+bool MediaValuesDynamic::threeDEnabled() const
+{
+ return calculateThreeDEnabled(m_frame);
+}
+
+bool MediaValuesDynamic::scanMediaType() const
+{
+ return calculateScanMediaType(m_frame);
+}
+
+bool MediaValuesDynamic::screenMediaType() const
+{
+ return calculateScreenMediaType(m_frame);
+}
+
+bool MediaValuesDynamic::printMediaType() const
+{
+ return calculatePrintMediaType(m_frame);
+}
+
+bool MediaValuesDynamic::strictMode() const
+{
+ return calculateStrictMode(m_frame);
+}
+
+Document* MediaValuesDynamic::document() const
+{
+ return m_frame->document();
+}
+
+bool MediaValuesDynamic::hasValues() const
+{
+ return m_frame;
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.h b/chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.h
new file mode 100644
index 00000000000..26fac877451
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValuesDynamic.h
@@ -0,0 +1,49 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaValuesDynamic_h
+#define MediaValuesDynamic_h
+
+#include "core/css/MediaValues.h"
+
+namespace WebCore {
+
+class Document;
+
+class MediaValuesDynamic FINAL : public MediaValues {
+public:
+ static PassRefPtr<MediaValues> create(LocalFrame*);
+ virtual PassRefPtr<MediaValues> copy() const OVERRIDE;
+ virtual bool isSafeToSendToAnotherThread() const OVERRIDE;
+ virtual bool computeLength(double value, CSSPrimitiveValue::UnitType, int& result) const OVERRIDE;
+ virtual bool computeLength(double value, CSSPrimitiveValue::UnitType, double& result) const OVERRIDE;
+
+ virtual int viewportWidth() const OVERRIDE;
+ virtual int viewportHeight() const OVERRIDE;
+ virtual int deviceWidth() const OVERRIDE;
+ virtual int deviceHeight() const OVERRIDE;
+ virtual float devicePixelRatio() const OVERRIDE;
+ virtual int colorBitsPerComponent() const OVERRIDE;
+ virtual int monochromeBitsPerComponent() const OVERRIDE;
+ virtual PointerDeviceType pointer() const OVERRIDE;
+ virtual bool threeDEnabled() const OVERRIDE;
+ virtual bool scanMediaType() const OVERRIDE;
+ virtual bool screenMediaType() const OVERRIDE;
+ virtual bool printMediaType() const OVERRIDE;
+ virtual bool strictMode() const OVERRIDE;
+ virtual Document* document() const OVERRIDE;
+ virtual bool hasValues() const OVERRIDE;
+
+protected:
+ MediaValuesDynamic(LocalFrame*);
+
+ // This raw ptr is safe, as MediaValues would not outlive MediaQueryEvaluator, and
+ // MediaQueryEvaluator is reset on |Document::detach|.
+ // FIXME: Oilpan: This raw ptr should be changed to a Member when LocalFrame is migrated to the heap.
+ LocalFrame* m_frame;
+};
+
+} // namespace
+
+#endif // MediaValuesDynamic_h
diff --git a/chromium/third_party/WebKit/Source/core/css/MediaValuesTest.cpp b/chromium/third_party/WebKit/Source/core/css/MediaValuesTest.cpp
new file mode 100644
index 00000000000..f4b9c8b650a
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/MediaValuesTest.cpp
@@ -0,0 +1,61 @@
+// Use of this source code is governed by a BSD-style license that can be
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/MediaValues.h"
+
+#include "core/css/CSSPrimitiveValue.h"
+#include "wtf/text/StringBuilder.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+struct TestCase {
+ double value;
+ CSSPrimitiveValue::UnitType type;
+ unsigned fontSize;
+ unsigned viewportWidth;
+ unsigned viewportHeight;
+ bool success;
+ int output;
+};
+
+TEST(MediaValuesTest, Basic)
+{
+ TestCase testCases[] = {
+ { 40.0, CSSPrimitiveValue::CSS_PX, 16, 300, 300, true, 40 },
+ { 40.0, CSSPrimitiveValue::CSS_EMS, 16, 300, 300, true, 640 },
+ { 40.0, CSSPrimitiveValue::CSS_REMS, 16, 300, 300, true, 640 },
+ { 40.0, CSSPrimitiveValue::CSS_EXS, 16, 300, 300, true, 320 },
+ { 40.0, CSSPrimitiveValue::CSS_CHS, 16, 300, 300, true, 320 },
+ { 43.0, CSSPrimitiveValue::CSS_VW, 16, 848, 976, true, 364 },
+ { 43.0, CSSPrimitiveValue::CSS_VH, 16, 848, 976, true, 419 },
+ { 43.0, CSSPrimitiveValue::CSS_VMIN, 16, 848, 976, true, 364 },
+ { 43.0, CSSPrimitiveValue::CSS_VMAX, 16, 848, 976, true, 419 },
+ { 1.3, CSSPrimitiveValue::CSS_CM, 16, 300, 300, true, 49 },
+ { 1.3, CSSPrimitiveValue::CSS_MM, 16, 300, 300, true, 4 },
+ { 1.3, CSSPrimitiveValue::CSS_IN, 16, 300, 300, true, 124 },
+ { 13, CSSPrimitiveValue::CSS_PT, 16, 300, 300, true, 17 },
+ { 1.3, CSSPrimitiveValue::CSS_PC, 16, 300, 300, true, 20 },
+ { 1.3, CSSPrimitiveValue::CSS_UNKNOWN, 16, 300, 300, false, 20 },
+ { 0.0, CSSPrimitiveValue::CSS_UNKNOWN, 0, 0, 0, false, 0.0 } // Do not remove the terminating line.
+ };
+
+
+ for (unsigned i = 0; testCases[i].viewportWidth; ++i) {
+ int output = 0;
+ bool success = MediaValues::computeLength(testCases[i].value,
+ testCases[i].type,
+ testCases[i].fontSize,
+ testCases[i].viewportWidth,
+ testCases[i].viewportHeight,
+ output);
+ ASSERT_EQ(testCases[i].success, success);
+ if (success)
+ ASSERT_EQ(testCases[i].output, output);
+ }
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.cpp b/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.cpp
index e4494526d30..3e8c76f8919 100644
--- a/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.cpp
@@ -73,7 +73,7 @@ void PageRuleCollector::matchPageRules(RuleSet* rules)
return;
rules->compactRulesIfNeeded();
- Vector<StyleRulePage*> matchedPageRules;
+ WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> > matchedPageRules;
matchPageRulesForList(matchedPageRules, rules->pageRules(), m_isLeftPage, m_isFirstPage, m_pageName);
if (matchedPageRules.isEmpty())
return;
@@ -81,13 +81,13 @@ void PageRuleCollector::matchPageRules(RuleSet* rules)
std::stable_sort(matchedPageRules.begin(), matchedPageRules.end(), comparePageRules);
for (unsigned i = 0; i < matchedPageRules.size(); i++)
- m_result.addMatchedProperties(matchedPageRules[i]->properties());
+ m_result.addMatchedProperties(&matchedPageRules[i]->properties());
}
static bool checkPageSelectorComponents(const CSSSelector* selector, bool isLeftPage, bool isFirstPage, const String& pageName)
{
for (const CSSSelector* component = selector; component; component = component->tagHistory()) {
- if (component->m_match == CSSSelector::Tag) {
+ if (component->match() == CSSSelector::Tag) {
const AtomicString& localName = component->tagQName().localName();
if (localName != starAtom && localName != pageName)
return false;
@@ -104,7 +104,7 @@ static bool checkPageSelectorComponents(const CSSSelector* selector, bool isLeft
return true;
}
-void PageRuleCollector::matchPageRulesForList(Vector<StyleRulePage*>& matchedRules, const Vector<StyleRulePage*>& rules, bool isLeftPage, bool isFirstPage, const String& pageName)
+void PageRuleCollector::matchPageRulesForList(WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >& matchedRules, const WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >& rules, bool isLeftPage, bool isFirstPage, const String& pageName)
{
for (unsigned i = 0; i < rules.size(); ++i) {
StyleRulePage* rule = rules[i];
@@ -113,8 +113,8 @@ void PageRuleCollector::matchPageRulesForList(Vector<StyleRulePage*>& matchedRul
continue;
// If the rule has no properties to apply, then ignore it.
- const StylePropertySet* properties = rule->properties();
- if (!properties || properties->isEmpty())
+ const StylePropertySet& properties = rule->properties();
+ if (properties.isEmpty())
continue;
// Add this rule to our list of matched rules.
diff --git a/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.h b/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.h
index 83251612aaf..af632809358 100644
--- a/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.h
+++ b/chromium/third_party/WebKit/Source/core/css/PageRuleCollector.h
@@ -31,6 +31,7 @@ class ElementResolveContext;
class StyleRulePage;
class PageRuleCollector {
+ STACK_ALLOCATED();
public:
PageRuleCollector(const RenderStyle* rootElementStyle, int pageIndex);
@@ -43,7 +44,7 @@ private:
bool isFirstPage(int pageIndex) const;
String pageName(int pageIndex) const;
- void matchPageRulesForList(Vector<StyleRulePage*>& matchedRules, const Vector<StyleRulePage*>& rules, bool isLeftPage, bool isFirstPage, const String& pageName);
+ void matchPageRulesForList(WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >& matchedRules, const WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >& rules, bool isLeftPage, bool isFirstPage, const String& pageName);
const bool m_isLeftPage;
const bool m_isFirstPage;
diff --git a/chromium/third_party/WebKit/Source/core/css/Pair.cpp b/chromium/third_party/WebKit/Source/core/css/Pair.cpp
new file mode 100644
index 00000000000..5362b6b5274
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/Pair.cpp
@@ -0,0 +1,16 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/Pair.h"
+
+namespace WebCore {
+
+void Pair::trace(Visitor* visitor)
+{
+ visitor->trace(m_first);
+ visitor->trace(m_second);
+}
+
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/Pair.h b/chromium/third_party/WebKit/Source/core/css/Pair.h
index fc2edaa828b..5cafb532092 100644
--- a/chromium/third_party/WebKit/Source/core/css/Pair.h
+++ b/chromium/third_party/WebKit/Source/core/css/Pair.h
@@ -32,25 +32,22 @@ namespace WebCore {
// and border-spacing (all of which are space-separated sets of two values). At the moment we are only using it for
// border-radius and background-size, but (FIXME) border-spacing and background-position could be converted over to use
// it (eliminating some extra -webkit- internal properties).
-class Pair FINAL : public RefCounted<Pair> {
+class Pair FINAL : public RefCountedWillBeGarbageCollected<Pair> {
public:
enum IdenticalValuesPolicy { DropIdenticalValues, KeepIdenticalValues };
- static PassRefPtr<Pair> create()
+ static PassRefPtrWillBeRawPtr<Pair> create(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> first, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> second,
+ IdenticalValuesPolicy identicalValuesPolicy)
{
- return adoptRef(new Pair);
- }
- static PassRefPtr<Pair> create(PassRefPtr<CSSPrimitiveValue> first, PassRefPtr<CSSPrimitiveValue> second, IdenticalValuesPolicy identicalValuesPolicy)
- {
- return adoptRef(new Pair(first, second, identicalValuesPolicy));
+ return adoptRefWillBeNoop(new Pair(first, second, identicalValuesPolicy));
}
CSSPrimitiveValue* first() const { return m_first.get(); }
CSSPrimitiveValue* second() const { return m_second.get(); }
IdenticalValuesPolicy identicalValuesPolicy() const { return m_identicalValuesPolicy; }
- void setFirst(PassRefPtr<CSSPrimitiveValue> first) { m_first = first; }
- void setSecond(PassRefPtr<CSSPrimitiveValue> second) { m_second = second; }
+ void setFirst(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> first) { m_first = first; }
+ void setSecond(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> second) { m_second = second; }
void setIdenticalValuesPolicy(IdenticalValuesPolicy identicalValuesPolicy) { m_identicalValuesPolicy = identicalValuesPolicy; }
String cssText() const
@@ -65,23 +62,15 @@ public:
&& m_identicalValuesPolicy == other.m_identicalValuesPolicy;
}
- String serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
- {
- return generateCSSString(
- first()->customSerializeResolvingVariables(variables),
- second()->customSerializeResolvingVariables(variables),
- m_identicalValuesPolicy);
- }
-
- bool hasVariableReference() const { return first()->hasVariableReference() || second()->hasVariableReference(); }
+ void trace(Visitor*);
private:
Pair()
- : m_first(0)
- , m_second(0)
+ : m_first(nullptr)
+ , m_second(nullptr)
, m_identicalValuesPolicy(DropIdenticalValues) { }
- Pair(PassRefPtr<CSSPrimitiveValue> first, PassRefPtr<CSSPrimitiveValue> second, IdenticalValuesPolicy identicalValuesPolicy)
+ Pair(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> first, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> second, IdenticalValuesPolicy identicalValuesPolicy)
: m_first(first)
, m_second(second)
, m_identicalValuesPolicy(identicalValuesPolicy) { }
@@ -93,8 +82,8 @@ private:
return first + ' ' + second;
}
- RefPtr<CSSPrimitiveValue> m_first;
- RefPtr<CSSPrimitiveValue> m_second;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_first;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_second;
IdenticalValuesPolicy m_identicalValuesPolicy;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.cpp b/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.cpp
index e30610ab3a2..b6d0f6eed1f 100644
--- a/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.cpp
@@ -22,18 +22,16 @@
#include "config.h"
#include "core/css/PropertySetCSSStyleDeclaration.h"
-#include "HTMLNames.h"
-#include "RuntimeEnabledFeatures.h"
#include "bindings/v8/ExceptionState.h"
-#include "core/css/CSSParser.h"
+#include "core/HTMLNames.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSStyleSheet.h"
#include "core/css/StylePropertySet.h"
#include "core/dom/Element.h"
#include "core/dom/MutationObserverInterestGroup.h"
#include "core/dom/MutationRecord.h"
#include "core/inspector/InspectorInstrumentation.h"
-
-using namespace std;
+#include "platform/RuntimeEnabledFeatures.h"
namespace WebCore {
@@ -41,8 +39,9 @@ namespace {
class StyleAttributeMutationScope {
WTF_MAKE_NONCOPYABLE(StyleAttributeMutationScope);
+ STACK_ALLOCATED();
public:
- StyleAttributeMutationScope(PropertySetCSSStyleDeclaration* decl)
+ StyleAttributeMutationScope(AbstractPropertySetCSSStyleDeclaration* decl)
{
InspectorInstrumentation::willMutateStyle(decl);
++s_scopeCount;
@@ -86,7 +85,7 @@ public:
s_shouldDeliver = false;
// We have to clear internal state before calling Inspector's code.
- PropertySetCSSStyleDeclaration* localCopyStyleDecl = s_currentDecl;
+ AbstractPropertySetCSSStyleDeclaration* localCopyStyleDecl = s_currentDecl;
s_currentDecl = 0;
InspectorInstrumentation::didMutateStyle(localCopyStyleDecl, localCopyStyleDecl->parentElement());
@@ -110,21 +109,22 @@ public:
private:
static unsigned s_scopeCount;
- static PropertySetCSSStyleDeclaration* s_currentDecl;
+ static AbstractPropertySetCSSStyleDeclaration* s_currentDecl;
static bool s_shouldNotifyInspector;
static bool s_shouldDeliver;
- OwnPtr<MutationObserverInterestGroup> m_mutationRecipients;
- RefPtr<MutationRecord> m_mutation;
+ OwnPtrWillBeMember<MutationObserverInterestGroup> m_mutationRecipients;
+ RefPtrWillBeMember<MutationRecord> m_mutation;
};
unsigned StyleAttributeMutationScope::s_scopeCount = 0;
-PropertySetCSSStyleDeclaration* StyleAttributeMutationScope::s_currentDecl = 0;
+AbstractPropertySetCSSStyleDeclaration* StyleAttributeMutationScope::s_currentDecl = 0;
bool StyleAttributeMutationScope::s_shouldNotifyInspector = false;
bool StyleAttributeMutationScope::s_shouldDeliver = false;
} // namespace
+#if !ENABLE(OILPAN)
void PropertySetCSSStyleDeclaration::ref()
{
m_propertySet->ref();
@@ -134,103 +134,101 @@ void PropertySetCSSStyleDeclaration::deref()
{
m_propertySet->deref();
}
+#endif
-unsigned PropertySetCSSStyleDeclaration::length() const
+void PropertySetCSSStyleDeclaration::trace(Visitor* visitor)
{
- return m_propertySet->propertyCount();
+ visitor->trace(m_propertySet);
+ AbstractPropertySetCSSStyleDeclaration::trace(visitor);
}
-String PropertySetCSSStyleDeclaration::item(unsigned i) const
+unsigned AbstractPropertySetCSSStyleDeclaration::length() const
{
- if (i >= m_propertySet->propertyCount())
+ return propertySet().propertyCount();
+}
+
+String AbstractPropertySetCSSStyleDeclaration::item(unsigned i) const
+{
+ if (i >= propertySet().propertyCount())
return "";
- return m_propertySet->propertyAt(i).cssName();
+ return propertySet().propertyAt(i).cssName();
}
-String PropertySetCSSStyleDeclaration::cssText() const
+String AbstractPropertySetCSSStyleDeclaration::cssText() const
{
- return m_propertySet->asText();
+ return propertySet().asText();
}
-void PropertySetCSSStyleDeclaration::setCSSText(const String& text, ExceptionState& exceptionState)
+void AbstractPropertySetCSSStyleDeclaration::setCSSText(const String& text, ExceptionState& exceptionState)
{
StyleAttributeMutationScope mutationScope(this);
willMutate();
// FIXME: Detect syntax errors and set exceptionState.
- m_propertySet->parseDeclaration(text, contextStyleSheet());
+ propertySet().parseDeclaration(text, contextStyleSheet());
didMutate(PropertyChanged);
mutationScope.enqueueMutationRecord();
}
-PassRefPtr<CSSValue> PropertySetCSSStyleDeclaration::getPropertyCSSValue(const String& propertyName)
+PassRefPtrWillBeRawPtr<CSSValue> AbstractPropertySetCSSStyleDeclaration::getPropertyCSSValue(const String& propertyName)
{
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
- return 0;
- return cloneAndCacheForCSSOM(m_propertySet->getPropertyCSSValue(propertyID).get());
+ return nullptr;
+ return cloneAndCacheForCSSOM(propertySet().getPropertyCSSValue(propertyID).get());
}
-String PropertySetCSSStyleDeclaration::getPropertyValue(const String &propertyName)
+String AbstractPropertySetCSSStyleDeclaration::getPropertyValue(const String &propertyName)
{
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
return String();
- return m_propertySet->getPropertyValue(propertyID);
+ return propertySet().getPropertyValue(propertyID);
}
-String PropertySetCSSStyleDeclaration::getPropertyPriority(const String& propertyName)
+String AbstractPropertySetCSSStyleDeclaration::getPropertyPriority(const String& propertyName)
{
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
return String();
- return m_propertySet->propertyIsImportant(propertyID) ? "important" : "";
+ return propertySet().propertyIsImportant(propertyID) ? "important" : "";
}
-String PropertySetCSSStyleDeclaration::getPropertyShorthand(const String& propertyName)
+String AbstractPropertySetCSSStyleDeclaration::getPropertyShorthand(const String& propertyName)
{
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
return String();
- CSSPropertyID shorthandID = m_propertySet->getPropertyShorthand(propertyID);
+ CSSPropertyID shorthandID = propertySet().getPropertyShorthand(propertyID);
if (!shorthandID)
return String();
return getPropertyNameString(shorthandID);
}
-bool PropertySetCSSStyleDeclaration::isPropertyImplicit(const String& propertyName)
+bool AbstractPropertySetCSSStyleDeclaration::isPropertyImplicit(const String& propertyName)
{
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
return false;
- return m_propertySet->isPropertyImplicit(propertyID);
+ return propertySet().isPropertyImplicit(propertyID);
}
-void PropertySetCSSStyleDeclaration::setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState& exceptionState)
+void AbstractPropertySetCSSStyleDeclaration::setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState& exceptionState)
{
- StyleAttributeMutationScope mutationScope(this);
CSSPropertyID propertyID = cssPropertyID(propertyName);
if (!propertyID)
return;
- bool important = priority.find("important", 0, false) != kNotFound;
-
- willMutate();
-
- bool changed = m_propertySet->setProperty(propertyID, value, important, contextStyleSheet());
-
- didMutate(changed ? PropertyChanged : NoChanges);
+ bool important = equalIgnoringCase(priority, "important");
+ if (!important && !priority.isEmpty())
+ return;
- if (changed) {
- // CSS DOM requires raising SyntaxError of parsing failed, but this is too dangerous for compatibility,
- // see <http://bugs.webkit.org/show_bug.cgi?id=7296>.
- mutationScope.enqueueMutationRecord();
- }
+ setPropertyInternal(propertyID, value, important, exceptionState);
}
-String PropertySetCSSStyleDeclaration::removeProperty(const String& propertyName, ExceptionState& exceptionState)
+String AbstractPropertySetCSSStyleDeclaration::removeProperty(const String& propertyName, ExceptionState& exceptionState)
{
StyleAttributeMutationScope mutationScope(this);
CSSPropertyID propertyID = cssPropertyID(propertyName);
@@ -240,7 +238,7 @@ String PropertySetCSSStyleDeclaration::removeProperty(const String& propertyName
willMutate();
String result;
- bool changed = m_propertySet->removeProperty(propertyID, &result);
+ bool changed = propertySet().removeProperty(propertyID, &result);
didMutate(changed ? PropertyChanged : NoChanges);
@@ -249,22 +247,22 @@ String PropertySetCSSStyleDeclaration::removeProperty(const String& propertyName
return result;
}
-PassRefPtr<CSSValue> PropertySetCSSStyleDeclaration::getPropertyCSSValueInternal(CSSPropertyID propertyID)
+PassRefPtrWillBeRawPtr<CSSValue> AbstractPropertySetCSSStyleDeclaration::getPropertyCSSValueInternal(CSSPropertyID propertyID)
{
- return m_propertySet->getPropertyCSSValue(propertyID);
+ return propertySet().getPropertyCSSValue(propertyID);
}
-String PropertySetCSSStyleDeclaration::getPropertyValueInternal(CSSPropertyID propertyID)
+String AbstractPropertySetCSSStyleDeclaration::getPropertyValueInternal(CSSPropertyID propertyID)
{
- return m_propertySet->getPropertyValue(propertyID);
+ return propertySet().getPropertyValue(propertyID);
}
-void PropertySetCSSStyleDeclaration::setPropertyInternal(CSSPropertyID propertyID, const String& value, bool important, ExceptionState&)
+void AbstractPropertySetCSSStyleDeclaration::setPropertyInternal(CSSPropertyID propertyID, const String& value, bool important, ExceptionState&)
{
StyleAttributeMutationScope mutationScope(this);
willMutate();
- bool changed = m_propertySet->setProperty(propertyID, value, important, contextStyleSheet());
+ bool changed = propertySet().setProperty(propertyID, value, important, contextStyleSheet());
didMutate(changed ? PropertyChanged : NoChanges);
@@ -272,60 +270,7 @@ void PropertySetCSSStyleDeclaration::setPropertyInternal(CSSPropertyID propertyI
mutationScope.enqueueMutationRecord();
}
-unsigned PropertySetCSSStyleDeclaration::variableCount() const
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- return m_propertySet->variableCount();
-}
-
-String PropertySetCSSStyleDeclaration::variableValue(const AtomicString& name) const
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- return m_propertySet->variableValue(name);
-}
-
-bool PropertySetCSSStyleDeclaration::setVariableValue(const AtomicString& name, const String& value, ExceptionState&)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- StyleAttributeMutationScope mutationScope(this);
- willMutate();
- bool changed = m_propertySet->setVariableValue(name, value);
- didMutate(changed ? PropertyChanged : NoChanges);
- if (changed)
- mutationScope.enqueueMutationRecord();
- return changed;
-}
-
-bool PropertySetCSSStyleDeclaration::removeVariable(const AtomicString& name)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- StyleAttributeMutationScope mutationScope(this);
- willMutate();
- bool changed = m_propertySet->removeVariable(name);
- didMutate(changed ? PropertyChanged : NoChanges);
- if (changed)
- mutationScope.enqueueMutationRecord();
- return changed;
-}
-
-bool PropertySetCSSStyleDeclaration::clearVariables(ExceptionState&)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- StyleAttributeMutationScope mutationScope(this);
- willMutate();
- bool changed = m_propertySet->clearVariables();
- didMutate(changed ? PropertyChanged : NoChanges);
- if (changed)
- mutationScope.enqueueMutationRecord();
- return changed;
-}
-
-PassRefPtr<CSSVariablesIterator> PropertySetCSSStyleDeclaration::variablesIterator() const
-{
- return m_propertySet->variablesIterator();
-}
-
-CSSValue* PropertySetCSSStyleDeclaration::cloneAndCacheForCSSOM(CSSValue* internalValue)
+CSSValue* AbstractPropertySetCSSStyleDeclaration::cloneAndCacheForCSSOM(CSSValue* internalValue)
{
if (!internalValue)
return 0;
@@ -333,43 +278,58 @@ CSSValue* PropertySetCSSStyleDeclaration::cloneAndCacheForCSSOM(CSSValue* intern
// The map is here to maintain the object identity of the CSSValues over multiple invocations.
// FIXME: It is likely that the identity is not important for web compatibility and this code should be removed.
if (!m_cssomCSSValueClones)
- m_cssomCSSValueClones = adoptPtr(new HashMap<CSSValue*, RefPtr<CSSValue> >);
+ m_cssomCSSValueClones = adoptPtrWillBeNoop(new WillBeHeapHashMap<RawPtrWillBeMember<CSSValue>, RefPtrWillBeMember<CSSValue> >);
- RefPtr<CSSValue>& clonedValue = m_cssomCSSValueClones->add(internalValue, RefPtr<CSSValue>()).iterator->value;
+ RefPtrWillBeMember<CSSValue>& clonedValue = m_cssomCSSValueClones->add(internalValue, RefPtrWillBeMember<CSSValue>()).storedValue->value;
if (!clonedValue)
clonedValue = internalValue->cloneForCSSOM();
return clonedValue.get();
}
-StyleSheetContents* PropertySetCSSStyleDeclaration::contextStyleSheet() const
+StyleSheetContents* AbstractPropertySetCSSStyleDeclaration::contextStyleSheet() const
{
CSSStyleSheet* cssStyleSheet = parentStyleSheet();
return cssStyleSheet ? cssStyleSheet->contents() : 0;
}
-PassRefPtr<MutableStylePropertySet> PropertySetCSSStyleDeclaration::copyProperties() const
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> AbstractPropertySetCSSStyleDeclaration::copyProperties() const
+{
+ return propertySet().mutableCopy();
+}
+
+bool AbstractPropertySetCSSStyleDeclaration::cssPropertyMatches(CSSPropertyID propertyID, const CSSValue* propertyValue) const
{
- return m_propertySet->mutableCopy();
+ return propertySet().propertyMatches(propertyID, propertyValue);
}
-bool PropertySetCSSStyleDeclaration::cssPropertyMatches(CSSPropertyID propertyID, const CSSValue* propertyValue) const
+void AbstractPropertySetCSSStyleDeclaration::trace(Visitor* visitor)
{
- return m_propertySet->propertyMatches(propertyID, propertyValue);
+#if ENABLE(OILPAN)
+ visitor->trace(m_cssomCSSValueClones);
+#endif
+ CSSStyleDeclaration::trace(visitor);
}
-StyleRuleCSSStyleDeclaration::StyleRuleCSSStyleDeclaration(MutableStylePropertySet* propertySet, CSSRule* parentRule)
- : PropertySetCSSStyleDeclaration(propertySet)
+StyleRuleCSSStyleDeclaration::StyleRuleCSSStyleDeclaration(MutableStylePropertySet& propertySetArg, CSSRule* parentRule)
+ : PropertySetCSSStyleDeclaration(propertySetArg)
+#if !ENABLE(OILPAN)
, m_refCount(1)
+#endif
, m_parentRule(parentRule)
{
+#if !ENABLE(OILPAN)
m_propertySet->ref();
+#endif
}
StyleRuleCSSStyleDeclaration::~StyleRuleCSSStyleDeclaration()
{
+#if !ENABLE(OILPAN)
m_propertySet->deref();
+#endif
}
+#if !ENABLE(OILPAN)
void StyleRuleCSSStyleDeclaration::ref()
{
++m_refCount;
@@ -381,6 +341,7 @@ void StyleRuleCSSStyleDeclaration::deref()
if (!--m_refCount)
delete this;
}
+#endif
void StyleRuleCSSStyleDeclaration::willMutate()
{
@@ -403,12 +364,26 @@ CSSStyleSheet* StyleRuleCSSStyleDeclaration::parentStyleSheet() const
return m_parentRule ? m_parentRule->parentStyleSheet() : 0;
}
-void StyleRuleCSSStyleDeclaration::reattach(MutableStylePropertySet* propertySet)
+void StyleRuleCSSStyleDeclaration::reattach(MutableStylePropertySet& propertySet)
{
- ASSERT(propertySet);
+#if !ENABLE(OILPAN)
m_propertySet->deref();
- m_propertySet = propertySet;
+#endif
+ m_propertySet = &propertySet;
+#if !ENABLE(OILPAN)
m_propertySet->ref();
+#endif
+}
+
+void StyleRuleCSSStyleDeclaration::trace(Visitor* visitor)
+{
+ visitor->trace(m_parentRule);
+ PropertySetCSSStyleDeclaration::trace(visitor);
+}
+
+MutableStylePropertySet& InlineCSSStyleDeclaration::propertySet() const
+{
+ return m_parentElement->ensureMutableInlineStyle();
}
void InlineCSSStyleDeclaration::didMutate(MutationType type)
@@ -421,6 +396,7 @@ void InlineCSSStyleDeclaration::didMutate(MutationType type)
if (!m_parentElement)
return;
+ m_parentElement->clearMutableInlineStyleIfEmpty();
m_parentElement->setNeedsStyleRecalc(LocalStyleChange);
m_parentElement->invalidateStyleAttribute();
StyleAttributeMutationScope(this).didInvalidateStyleAttr();
@@ -428,7 +404,25 @@ void InlineCSSStyleDeclaration::didMutate(MutationType type)
CSSStyleSheet* InlineCSSStyleDeclaration::parentStyleSheet() const
{
- return m_parentElement ? m_parentElement->document().elementSheet() : 0;
+ return m_parentElement ? &m_parentElement->document().elementSheet() : 0;
+}
+
+#if !ENABLE(OILPAN)
+void InlineCSSStyleDeclaration::ref()
+{
+ m_parentElement->ref();
+}
+
+void InlineCSSStyleDeclaration::deref()
+{
+ m_parentElement->deref();
+}
+#endif
+
+void InlineCSSStyleDeclaration::trace(Visitor* visitor)
+{
+ visitor->trace(m_parentElement);
+ AbstractPropertySetCSSStyleDeclaration::trace(visitor);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.h b/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.h
index 20b36855afe..e38bd4557f7 100644
--- a/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.h
+++ b/chromium/third_party/WebKit/Source/core/css/PropertySetCSSStyleDeclaration.h
@@ -40,43 +40,32 @@ class ExceptionState;
class MutableStylePropertySet;
class StyleSheetContents;
-class PropertySetCSSStyleDeclaration : public CSSStyleDeclaration {
+class AbstractPropertySetCSSStyleDeclaration : public CSSStyleDeclaration {
public:
- PropertySetCSSStyleDeclaration(MutableStylePropertySet* propertySet) : m_propertySet(propertySet) { }
-
virtual Element* parentElement() const { return 0; }
- virtual void clearParentElement() { ASSERT_NOT_REACHED(); }
StyleSheetContents* contextStyleSheet() const;
- virtual void ref() OVERRIDE;
- virtual void deref() OVERRIDE;
+ virtual void trace(Visitor*) OVERRIDE;
private:
- virtual CSSRule* parentRule() const OVERRIDE { return 0; };
- virtual unsigned length() const OVERRIDE;
- virtual String item(unsigned index) const OVERRIDE;
- virtual PassRefPtr<CSSValue> getPropertyCSSValue(const String& propertyName) OVERRIDE;
- virtual String getPropertyValue(const String& propertyName) OVERRIDE;
- virtual String getPropertyPriority(const String& propertyName) OVERRIDE;
- virtual String getPropertyShorthand(const String& propertyName) OVERRIDE;
- virtual bool isPropertyImplicit(const String& propertyName) OVERRIDE;
- virtual void setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState&) OVERRIDE;
- virtual String removeProperty(const String& propertyName, ExceptionState&) OVERRIDE;
- virtual String cssText() const OVERRIDE;
- virtual void setCSSText(const String&, ExceptionState&) OVERRIDE;
- virtual PassRefPtr<CSSValue> getPropertyCSSValueInternal(CSSPropertyID) OVERRIDE;
- virtual String getPropertyValueInternal(CSSPropertyID) OVERRIDE;
- virtual void setPropertyInternal(CSSPropertyID, const String& value, bool important, ExceptionState&) OVERRIDE;
-
- virtual unsigned variableCount() const OVERRIDE;
- virtual String variableValue(const AtomicString& name) const OVERRIDE;
- virtual bool setVariableValue(const AtomicString& name, const String& value, ExceptionState&) OVERRIDE;
- virtual bool removeVariable(const AtomicString& name) OVERRIDE;
- virtual bool clearVariables(ExceptionState&) OVERRIDE;
- virtual PassRefPtr<CSSVariablesIterator> variablesIterator() const OVERRIDE;
-
- virtual bool cssPropertyMatches(CSSPropertyID, const CSSValue*) const OVERRIDE;
- virtual PassRefPtr<MutableStylePropertySet> copyProperties() const OVERRIDE;
+ virtual CSSRule* parentRule() const OVERRIDE { return 0; }
+ virtual unsigned length() const OVERRIDE FINAL;
+ virtual String item(unsigned index) const OVERRIDE FINAL;
+ virtual PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValue(const String& propertyName) OVERRIDE FINAL;
+ virtual String getPropertyValue(const String& propertyName) OVERRIDE FINAL;
+ virtual String getPropertyPriority(const String& propertyName) OVERRIDE FINAL;
+ virtual String getPropertyShorthand(const String& propertyName) OVERRIDE FINAL;
+ virtual bool isPropertyImplicit(const String& propertyName) OVERRIDE FINAL;
+ virtual void setProperty(const String& propertyName, const String& value, const String& priority, ExceptionState&) OVERRIDE FINAL;
+ virtual String removeProperty(const String& propertyName, ExceptionState&) OVERRIDE FINAL;
+ virtual String cssText() const OVERRIDE FINAL;
+ virtual void setCSSText(const String&, ExceptionState&) OVERRIDE FINAL;
+ virtual PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValueInternal(CSSPropertyID) OVERRIDE FINAL;
+ virtual String getPropertyValueInternal(CSSPropertyID) OVERRIDE FINAL;
+ virtual void setPropertyInternal(CSSPropertyID, const String& value, bool important, ExceptionState&) OVERRIDE FINAL;
+
+ virtual bool cssPropertyMatches(CSSPropertyID, const CSSValue*) const OVERRIDE FINAL;
+ virtual PassRefPtrWillBeRawPtr<MutableStylePropertySet> copyProperties() const OVERRIDE FINAL;
CSSValue* cloneAndCacheForCSSOM(CSSValue*);
@@ -84,28 +73,49 @@ protected:
enum MutationType { NoChanges, PropertyChanged };
virtual void willMutate() { }
virtual void didMutate(MutationType) { }
+ virtual MutableStylePropertySet& propertySet() const = 0;
- MutableStylePropertySet* m_propertySet;
- OwnPtr<HashMap<CSSValue*, RefPtr<CSSValue> > > m_cssomCSSValueClones;
+ OwnPtrWillBeMember<WillBeHeapHashMap<RawPtrWillBeMember<CSSValue>, RefPtrWillBeMember<CSSValue> > > m_cssomCSSValueClones;
};
-class StyleRuleCSSStyleDeclaration : public PropertySetCSSStyleDeclaration
+class PropertySetCSSStyleDeclaration : public AbstractPropertySetCSSStyleDeclaration {
+public:
+ PropertySetCSSStyleDeclaration(MutableStylePropertySet& propertySet) : m_propertySet(&propertySet) { }
+
+#if !ENABLE(OILPAN)
+ virtual void ref() OVERRIDE;
+ virtual void deref() OVERRIDE;
+#endif
+
+ virtual void trace(Visitor*) OVERRIDE;
+
+protected:
+ virtual MutableStylePropertySet& propertySet() const OVERRIDE FINAL { ASSERT(m_propertySet); return *m_propertySet; }
+
+ RawPtrWillBeMember<MutableStylePropertySet> m_propertySet; // Cannot be null
+};
+
+class StyleRuleCSSStyleDeclaration FINAL : public PropertySetCSSStyleDeclaration
{
public:
- static PassRefPtr<StyleRuleCSSStyleDeclaration> create(MutableStylePropertySet* propertySet, CSSRule* parentRule)
+ static PassRefPtrWillBeRawPtr<StyleRuleCSSStyleDeclaration> create(MutableStylePropertySet& propertySet, CSSRule* parentRule)
{
- return adoptRef(new StyleRuleCSSStyleDeclaration(propertySet, parentRule));
+ return adoptRefWillBeNoop(new StyleRuleCSSStyleDeclaration(propertySet, parentRule));
}
- void clearParentRule() { m_parentRule = 0; }
+#if !ENABLE(OILPAN)
+ void clearParentRule() { m_parentRule = nullptr; }
virtual void ref() OVERRIDE;
virtual void deref() OVERRIDE;
+#endif
+
+ void reattach(MutableStylePropertySet&);
- void reattach(MutableStylePropertySet*);
+ virtual void trace(Visitor*) OVERRIDE;
private:
- StyleRuleCSSStyleDeclaration(MutableStylePropertySet*, CSSRule*);
+ StyleRuleCSSStyleDeclaration(MutableStylePropertySet&, CSSRule*);
virtual ~StyleRuleCSSStyleDeclaration();
virtual CSSStyleSheet* parentStyleSheet() const OVERRIDE;
@@ -115,27 +125,34 @@ private:
virtual void willMutate() OVERRIDE;
virtual void didMutate(MutationType) OVERRIDE;
+#if !ENABLE(OILPAN)
unsigned m_refCount;
- CSSRule* m_parentRule;
+#endif
+ RawPtrWillBeMember<CSSRule> m_parentRule;
};
-class InlineCSSStyleDeclaration : public PropertySetCSSStyleDeclaration
+class InlineCSSStyleDeclaration FINAL : public AbstractPropertySetCSSStyleDeclaration
{
public:
- InlineCSSStyleDeclaration(MutableStylePropertySet* propertySet, Element* parentElement)
- : PropertySetCSSStyleDeclaration(propertySet)
- , m_parentElement(parentElement)
+ explicit InlineCSSStyleDeclaration(Element* parentElement)
+ : m_parentElement(parentElement)
{
}
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
+ virtual MutableStylePropertySet& propertySet() const OVERRIDE;
+#if !ENABLE(OILPAN)
+ virtual void ref() OVERRIDE;
+ virtual void deref() OVERRIDE;
+#endif
virtual CSSStyleSheet* parentStyleSheet() const OVERRIDE;
virtual Element* parentElement() const OVERRIDE { return m_parentElement; }
- virtual void clearParentElement() OVERRIDE { m_parentElement = 0; }
virtual void didMutate(MutationType) OVERRIDE;
- Element* m_parentElement;
+ RawPtrWillBeMember<Element> m_parentElement;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/RGBColor.cpp b/chromium/third_party/WebKit/Source/core/css/RGBColor.cpp
index 6b131d04654..9994d231786 100644
--- a/chromium/third_party/WebKit/Source/core/css/RGBColor.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/RGBColor.cpp
@@ -30,39 +30,39 @@
namespace WebCore {
-PassRefPtr<RGBColor> RGBColor::create(unsigned rgbColor)
+PassRefPtrWillBeRawPtr<RGBColor> RGBColor::create(unsigned rgbColor)
{
- return adoptRef(new RGBColor(rgbColor));
+ return adoptRefWillBeNoop(new RGBColor(rgbColor));
}
-PassRefPtr<CSSPrimitiveValue> RGBColor::red()
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> RGBColor::red()
{
unsigned value = (m_rgbColor >> 16) & 0xFF;
- RefPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
result->setCSSOMSafe();
return result.release();
}
-PassRefPtr<CSSPrimitiveValue> RGBColor::green()
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> RGBColor::green()
{
unsigned value = (m_rgbColor >> 8) & 0xFF;
- RefPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
result->setCSSOMSafe();
return result.release();
}
-PassRefPtr<CSSPrimitiveValue> RGBColor::blue()
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> RGBColor::blue()
{
unsigned value = m_rgbColor & 0xFF;
- RefPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
result->setCSSOMSafe();
return result.release();
}
-PassRefPtr<CSSPrimitiveValue> RGBColor::alpha()
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> RGBColor::alpha()
{
float value = static_cast<float>((m_rgbColor >> 24) & 0xFF) / 0xFF;
- RefPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = CSSPrimitiveValue::create(value, CSSPrimitiveValue::CSS_NUMBER);
result->setCSSOMSafe();
return result.release();
}
diff --git a/chromium/third_party/WebKit/Source/core/css/RGBColor.h b/chromium/third_party/WebKit/Source/core/css/RGBColor.h
index 5cd4697d4fb..51a98f8845a 100644
--- a/chromium/third_party/WebKit/Source/core/css/RGBColor.h
+++ b/chromium/third_party/WebKit/Source/core/css/RGBColor.h
@@ -28,23 +28,26 @@
#define RGBColor_h
#include "platform/graphics/Color.h"
+#include "platform/heap/Handle.h"
#include "wtf/RefCounted.h"
namespace WebCore {
class CSSPrimitiveValue;
- class RGBColor : public RefCounted<RGBColor> {
+ class RGBColor : public RefCountedWillBeGarbageCollected<RGBColor> {
public:
- static PassRefPtr<RGBColor> create(unsigned rgbColor);
+ static PassRefPtrWillBeRawPtr<RGBColor> create(unsigned rgbColor);
- PassRefPtr<CSSPrimitiveValue> red();
- PassRefPtr<CSSPrimitiveValue> green();
- PassRefPtr<CSSPrimitiveValue> blue();
- PassRefPtr<CSSPrimitiveValue> alpha();
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> red();
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> green();
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> blue();
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> alpha();
Color color() const { return Color(m_rgbColor); }
+ void trace(Visitor*) { }
+
private:
RGBColor(unsigned rgbColor)
: m_rgbColor(rgbColor)
diff --git a/chromium/third_party/WebKit/Source/core/css/RGBColor.idl b/chromium/third_party/WebKit/Source/core/css/RGBColor.idl
index 09fa76ef2ef..398fe1b5085 100644
--- a/chromium/third_party/WebKit/Source/core/css/RGBColor.idl
+++ b/chromium/third_party/WebKit/Source/core/css/RGBColor.idl
@@ -19,6 +19,7 @@
*/
[
+ WillBeGarbageCollected
] interface RGBColor {
readonly attribute CSSPrimitiveValue red;
readonly attribute CSSPrimitiveValue green;
diff --git a/chromium/third_party/WebKit/Source/core/css/Rect.cpp b/chromium/third_party/WebKit/Source/core/css/Rect.cpp
new file mode 100644
index 00000000000..13afc70a656
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/Rect.cpp
@@ -0,0 +1,20 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/Rect.h"
+
+namespace WebCore {
+
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(RectBase)
+
+void RectBase::trace(Visitor* visitor)
+{
+ visitor->trace(m_top);
+ visitor->trace(m_right);
+ visitor->trace(m_bottom);
+ visitor->trace(m_left);
+}
+
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/Rect.h b/chromium/third_party/WebKit/Source/core/css/Rect.h
index 21978cd15fa..2f9e08e4a6d 100644
--- a/chromium/third_party/WebKit/Source/core/css/Rect.h
+++ b/chromium/third_party/WebKit/Source/core/css/Rect.h
@@ -27,17 +27,18 @@
namespace WebCore {
-class RectBase {
+class RectBase : public RefCountedWillBeGarbageCollected<RectBase> {
+ DECLARE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(RectBase);
public:
CSSPrimitiveValue* top() const { return m_top.get(); }
CSSPrimitiveValue* right() const { return m_right.get(); }
CSSPrimitiveValue* bottom() const { return m_bottom.get(); }
CSSPrimitiveValue* left() const { return m_left.get(); }
- void setTop(PassRefPtr<CSSPrimitiveValue> top) { m_top = top; }
- void setRight(PassRefPtr<CSSPrimitiveValue> right) { m_right = right; }
- void setBottom(PassRefPtr<CSSPrimitiveValue> bottom) { m_bottom = bottom; }
- void setLeft(PassRefPtr<CSSPrimitiveValue> left) { m_left = left; }
+ void setTop(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> top) { m_top = top; }
+ void setRight(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> right) { m_right = right; }
+ void setBottom(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> bottom) { m_bottom = bottom; }
+ void setLeft(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> left) { m_left = left; }
bool equals(const RectBase& other) const
{
@@ -47,83 +48,63 @@ public:
&& compareCSSValuePtr(m_bottom, other.m_bottom);
}
- bool hasVariableReference() const
- {
- return m_top->hasVariableReference()
- || m_right->hasVariableReference()
- || m_bottom->hasVariableReference()
- || m_left->hasVariableReference();
- }
+ void trace(Visitor*);
protected:
RectBase() { }
RectBase(const RectBase& cloneFrom)
- : m_top(cloneFrom.m_top ? cloneFrom.m_top->cloneForCSSOM() : 0)
- , m_right(cloneFrom.m_right ? cloneFrom.m_right->cloneForCSSOM() : 0)
- , m_bottom(cloneFrom.m_bottom ? cloneFrom.m_bottom->cloneForCSSOM() : 0)
- , m_left(cloneFrom.m_left ? cloneFrom.m_left->cloneForCSSOM() : 0)
+ : m_top(cloneFrom.m_top ? cloneFrom.m_top->cloneForCSSOM() : nullptr)
+ , m_right(cloneFrom.m_right ? cloneFrom.m_right->cloneForCSSOM() : nullptr)
+ , m_bottom(cloneFrom.m_bottom ? cloneFrom.m_bottom->cloneForCSSOM() : nullptr)
+ , m_left(cloneFrom.m_left ? cloneFrom.m_left->cloneForCSSOM() : nullptr)
{
}
- ~RectBase() { }
-
private:
- RefPtr<CSSPrimitiveValue> m_top;
- RefPtr<CSSPrimitiveValue> m_right;
- RefPtr<CSSPrimitiveValue> m_bottom;
- RefPtr<CSSPrimitiveValue> m_left;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_top;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_right;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_bottom;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_left;
};
-class Rect : public RectBase, public RefCounted<Rect> {
+class Rect : public RectBase {
public:
- static PassRefPtr<Rect> create() { return adoptRef(new Rect); }
+ static PassRefPtrWillBeRawPtr<Rect> create() { return adoptRefWillBeNoop(new Rect); }
- PassRefPtr<Rect> cloneForCSSOM() const { return adoptRef(new Rect(*this)); }
+ PassRefPtrWillBeRawPtr<Rect> cloneForCSSOM() const { return adoptRefWillBeNoop(new Rect(*this)); }
String cssText() const
{
return generateCSSString(top()->cssText(), right()->cssText(), bottom()->cssText(), left()->cssText());
}
- String serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
- {
- return generateCSSString(top()->customSerializeResolvingVariables(variables),
- right()->customSerializeResolvingVariables(variables),
- bottom()->customSerializeResolvingVariables(variables),
- left()->customSerializeResolvingVariables(variables));
- }
-
private:
Rect() { }
- Rect(const Rect& cloneFrom) : RectBase(cloneFrom), RefCounted<Rect>() { }
+ Rect(const Rect& cloneFrom) : RectBase(cloneFrom) { }
static String generateCSSString(const String& top, const String& right, const String& bottom, const String& left)
{
return "rect(" + top + ' ' + right + ' ' + bottom + ' ' + left + ')';
}
+
+ // NOTE: If adding fields to this class please make the RectBase trace
+ // method virtual and add a trace method in this subclass tracing the new
+ // fields.
};
-class Quad : public RectBase, public RefCounted<Quad> {
+class Quad : public RectBase {
public:
- static PassRefPtr<Quad> create() { return adoptRef(new Quad); }
+ static PassRefPtrWillBeRawPtr<Quad> create() { return adoptRefWillBeNoop(new Quad); }
- PassRefPtr<Quad> cloneForCSSOM() const { return adoptRef(new Quad(*this)); }
+ PassRefPtrWillBeRawPtr<Quad> cloneForCSSOM() const { return adoptRefWillBeNoop(new Quad(*this)); }
String cssText() const
{
return generateCSSString(top()->cssText(), right()->cssText(), bottom()->cssText(), left()->cssText());
}
- String serializeResolvingVariables(const HashMap<AtomicString, String>& variables) const
- {
- return generateCSSString(top()->customSerializeResolvingVariables(variables),
- right()->customSerializeResolvingVariables(variables),
- bottom()->customSerializeResolvingVariables(variables),
- left()->customSerializeResolvingVariables(variables));
- }
-
private:
Quad() { }
- Quad(const Quad& cloneFrom) : RectBase(cloneFrom), RefCounted<Quad>() { }
+ Quad(const Quad& cloneFrom) : RectBase(cloneFrom) { }
static String generateCSSString(const String& top, const String& right, const String& bottom, const String& left)
{
StringBuilder result;
@@ -144,6 +125,10 @@ private:
}
return result.toString();
}
+
+ // NOTE: If adding fields to this class please make the RectBase trace
+ // method virtual and add a trace method in this subclass tracing the new
+ // fields.
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/Rect.idl b/chromium/third_party/WebKit/Source/core/css/Rect.idl
index 3eac82fd539..87336d5bc06 100644
--- a/chromium/third_party/WebKit/Source/core/css/Rect.idl
+++ b/chromium/third_party/WebKit/Source/core/css/Rect.idl
@@ -18,6 +18,7 @@
*/
[
+ WillBeGarbageCollected
] interface Rect {
readonly attribute CSSPrimitiveValue top;
readonly attribute CSSPrimitiveValue right;
diff --git a/chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.cpp b/chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.cpp
new file mode 100644
index 00000000000..5316a6ef55a
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.cpp
@@ -0,0 +1,193 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/RemoteFontFaceSource.h"
+
+#include "core/css/CSSCustomFontData.h"
+#include "core/css/CSSFontFace.h"
+#include "core/css/FontLoader.h"
+#include "platform/fonts/FontCache.h"
+#include "platform/fonts/FontDescription.h"
+#include "platform/fonts/SimpleFontData.h"
+#include "public/platform/Platform.h"
+#include "wtf/CurrentTime.h"
+
+namespace WebCore {
+
+RemoteFontFaceSource::RemoteFontFaceSource(FontResource* font, PassRefPtrWillBeRawPtr<FontLoader> fontLoader)
+ : m_font(font)
+ , m_fontLoader(fontLoader)
+{
+ m_font->addClient(this);
+}
+
+RemoteFontFaceSource::~RemoteFontFaceSource()
+{
+ m_font->removeClient(this);
+ pruneTable();
+}
+
+void RemoteFontFaceSource::pruneTable()
+{
+ if (m_fontDataTable.isEmpty())
+ return;
+
+ for (FontDataTable::iterator it = m_fontDataTable.begin(); it != m_fontDataTable.end(); ++it) {
+ SimpleFontData* fontData = it->value.get();
+ if (fontData && fontData->customFontData())
+ fontData->customFontData()->clearFontFaceSource();
+ }
+ m_fontDataTable.clear();
+}
+
+bool RemoteFontFaceSource::isLoading() const
+{
+ return !m_font->stillNeedsLoad() && !m_font->isLoaded();
+}
+
+bool RemoteFontFaceSource::isLoaded() const
+{
+ return m_font->isLoaded();
+}
+
+bool RemoteFontFaceSource::isValid() const
+{
+ return !m_font->errorOccurred();
+}
+
+void RemoteFontFaceSource::didStartFontLoad(FontResource*)
+{
+ // We may send duplicated reports when multiple CSSFontFaceSource are
+ // registered at this FontResource. Associating the same URL to different
+ // font-family causes the case, but we treat them as indivisual resources.
+ m_histograms.loadStarted();
+}
+
+void RemoteFontFaceSource::fontLoaded(FontResource*)
+{
+ m_histograms.recordRemoteFont(m_font.get());
+
+ pruneTable();
+ if (m_face) {
+ m_fontLoader->fontFaceInvalidated();
+ m_face->fontLoaded(this);
+ }
+}
+
+void RemoteFontFaceSource::fontLoadWaitLimitExceeded(FontResource*)
+{
+ pruneTable();
+ if (m_face) {
+ m_fontLoader->fontFaceInvalidated();
+ m_face->fontLoadWaitLimitExceeded(this);
+ }
+
+ m_histograms.recordFallbackTime(m_font.get());
+}
+
+PassRefPtr<SimpleFontData> RemoteFontFaceSource::createFontData(const FontDescription& fontDescription)
+{
+ if (!isLoaded())
+ return createLoadingFallbackFontData(fontDescription);
+
+ // Create new FontPlatformData from our CGFontRef, point size and ATSFontRef.
+ if (!m_font->ensureCustomFontData())
+ return nullptr;
+
+ m_histograms.recordFallbackTime(m_font.get());
+
+ return SimpleFontData::create(
+ m_font->platformDataFromCustomData(fontDescription.effectiveFontSize(),
+ fontDescription.isSyntheticBold(), fontDescription.isSyntheticItalic(),
+ fontDescription.orientation(), fontDescription.widthVariant()), CustomFontData::create());
+}
+
+PassRefPtr<SimpleFontData> RemoteFontFaceSource::createLoadingFallbackFontData(const FontDescription& fontDescription)
+{
+ // This temporary font is not retained and should not be returned.
+ FontCachePurgePreventer fontCachePurgePreventer;
+ SimpleFontData* temporaryFont = FontCache::fontCache()->getNonRetainedLastResortFallbackFont(fontDescription);
+ if (!temporaryFont) {
+ ASSERT_NOT_REACHED();
+ return nullptr;
+ }
+ RefPtr<CSSCustomFontData> cssFontData = CSSCustomFontData::create(this, m_font->exceedsFontLoadWaitLimit() ? CSSCustomFontData::VisibleFallback : CSSCustomFontData::InvisibleFallback);
+ return SimpleFontData::create(temporaryFont->platformData(), cssFontData);
+}
+
+void RemoteFontFaceSource::beginLoadIfNeeded()
+{
+ if (m_font->stillNeedsLoad())
+ m_fontLoader->addFontToBeginLoading(m_font.get());
+
+ if (m_face)
+ m_face->didBeginLoad();
+}
+
+bool RemoteFontFaceSource::ensureFontData()
+{
+ return m_font->ensureCustomFontData();
+}
+
+void RemoteFontFaceSource::trace(Visitor* visitor)
+{
+ visitor->trace(m_fontLoader);
+ CSSFontFaceSource::trace(visitor);
+}
+
+void RemoteFontFaceSource::FontLoadHistograms::loadStarted()
+{
+ if (!m_loadStartTime)
+ m_loadStartTime = currentTimeMS();
+}
+
+void RemoteFontFaceSource::FontLoadHistograms::fallbackFontPainted()
+{
+ if (!m_fallbackPaintTime)
+ m_fallbackPaintTime = currentTimeMS();
+}
+
+void RemoteFontFaceSource::FontLoadHistograms::recordFallbackTime(const FontResource* font)
+{
+ if (m_fallbackPaintTime <= 0)
+ return;
+ int duration = static_cast<int>(currentTimeMS() - m_fallbackPaintTime);
+ blink::Platform::current()->histogramCustomCounts("WebFont.BlankTextShownTime", duration, 0, 10000, 50);
+ m_fallbackPaintTime = -1;
+}
+
+void RemoteFontFaceSource::FontLoadHistograms::recordRemoteFont(const FontResource* font)
+{
+ if (m_loadStartTime > 0 && font && !font->isLoading()) {
+ int duration = static_cast<int>(currentTimeMS() - m_loadStartTime);
+ blink::Platform::current()->histogramCustomCounts(histogramName(font), duration, 0, 10000, 50);
+ m_loadStartTime = -1;
+
+ enum { Miss, Hit, DataUrl, CacheHitEnumMax };
+ int histogramValue = font->url().protocolIsData() ? DataUrl
+ : font->response().wasCached() ? Hit
+ : Miss;
+ blink::Platform::current()->histogramEnumeration("WebFont.CacheHit", histogramValue, CacheHitEnumMax);
+ }
+}
+
+const char* RemoteFontFaceSource::FontLoadHistograms::histogramName(const FontResource* font)
+{
+ if (font->errorOccurred())
+ return "WebFont.DownloadTime.LoadError";
+
+ unsigned size = font->encodedSize();
+ if (size < 10 * 1024)
+ return "WebFont.DownloadTime.0.Under10KB";
+ if (size < 50 * 1024)
+ return "WebFont.DownloadTime.1.10KBTo50KB";
+ if (size < 100 * 1024)
+ return "WebFont.DownloadTime.2.50KBTo100KB";
+ if (size < 1024 * 1024)
+ return "WebFont.DownloadTime.3.100KBTo1MB";
+ return "WebFont.DownloadTime.4.Over1MB";
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.h b/chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.h
new file mode 100644
index 00000000000..f7d84ee5a36
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/RemoteFontFaceSource.h
@@ -0,0 +1,70 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef RemoteFontFaceSource_h
+#define RemoteFontFaceSource_h
+
+#include "core/css/CSSFontFaceSource.h"
+#include "core/fetch/FontResource.h"
+#include "core/fetch/ResourcePtr.h"
+
+namespace WebCore {
+
+class FontLoader;
+
+class RemoteFontFaceSource : public CSSFontFaceSource, public FontResourceClient {
+public:
+ explicit RemoteFontFaceSource(FontResource*, PassRefPtrWillBeRawPtr<FontLoader>);
+ virtual ~RemoteFontFaceSource();
+
+ virtual FontResource* resource() OVERRIDE { return m_font.get(); }
+ virtual bool isLoading() const OVERRIDE;
+ virtual bool isLoaded() const OVERRIDE;
+ virtual bool isValid() const OVERRIDE;
+
+ void beginLoadIfNeeded() OVERRIDE;
+ virtual bool ensureFontData();
+
+#if ENABLE(SVG_FONTS)
+ virtual bool isSVGFontFaceSource() const { return false; }
+#endif
+
+ virtual void didStartFontLoad(FontResource*) OVERRIDE;
+ virtual void fontLoaded(FontResource*) OVERRIDE;
+ virtual void fontLoadWaitLimitExceeded(FontResource*) OVERRIDE;
+
+ // For UMA reporting
+ virtual bool hadBlankText() OVERRIDE { return m_histograms.hadBlankText(); }
+ void paintRequested() { m_histograms.fallbackFontPainted(); }
+
+ virtual void trace(Visitor*) OVERRIDE;
+
+protected:
+ virtual PassRefPtr<SimpleFontData> createFontData(const FontDescription&) OVERRIDE;
+ PassRefPtr<SimpleFontData> createLoadingFallbackFontData(const FontDescription&);
+ void pruneTable();
+
+private:
+ class FontLoadHistograms {
+ public:
+ FontLoadHistograms() : m_loadStartTime(0), m_fallbackPaintTime(0) { }
+ void loadStarted();
+ void fallbackFontPainted();
+ void recordRemoteFont(const FontResource*);
+ void recordFallbackTime(const FontResource*);
+ bool hadBlankText() { return m_fallbackPaintTime; }
+ private:
+ const char* histogramName(const FontResource*);
+ double m_loadStartTime;
+ double m_fallbackPaintTime;
+ };
+
+ ResourcePtr<FontResource> m_font;
+ RefPtrWillBeMember<FontLoader> m_fontLoader;
+ FontLoadHistograms m_histograms;
+};
+
+} // namespace WebCore
+
+#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/RuleFeature.cpp b/chromium/third_party/WebKit/Source/core/css/RuleFeature.cpp
index 7c8f160ae43..26aea450ff0 100644
--- a/chromium/third_party/WebKit/Source/core/css/RuleFeature.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/RuleFeature.cpp
@@ -29,70 +29,501 @@
#include "config.h"
#include "core/css/RuleFeature.h"
-#include "HTMLNames.h"
+#include "core/HTMLNames.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSSelectorList.h"
+#include "core/css/RuleSet.h"
+#include "core/css/StyleRule.h"
+#include "core/css/invalidation/DescendantInvalidationSet.h"
+#include "core/dom/Element.h"
+#include "core/dom/Node.h"
+#include "platform/RuntimeEnabledFeatures.h"
+#include "wtf/BitVector.h"
namespace WebCore {
-void RuleFeatureSet::collectFeaturesFromSelector(const CSSSelector* selector)
-{
- if (selector->m_match == CSSSelector::Id)
- idsInRules.add(selector->value());
- else if (selector->m_match == CSSSelector::Class)
- classesInRules.add(selector->value());
- else if (selector->isAttributeSelector())
- attrsInRules.add(selector->attribute().localName());
- switch (selector->pseudoType()) {
- case CSSSelector::PseudoFirstLine:
- m_usesFirstLineRules = true;
- break;
- break;
- case CSSSelector::PseudoHost:
- collectFeaturesFromSelectorList(selector->selectorList());
- break;
+static bool isSkippableComponentForInvalidation(const CSSSelector& selector)
+{
+ if (selector.match() == CSSSelector::Tag
+ || selector.match() == CSSSelector::Id
+ || selector.isAttributeSelector())
+ return true;
+ if (selector.match() == CSSSelector::PseudoElement) {
+ switch (selector.pseudoType()) {
+ case CSSSelector::PseudoBefore:
+ case CSSSelector::PseudoAfter:
+ case CSSSelector::PseudoBackdrop:
+ case CSSSelector::PseudoShadow:
+ return true;
+ default:
+ return selector.isCustomPseudoElement();
+ }
+ }
+ if (selector.match() != CSSSelector::PseudoClass)
+ return false;
+ switch (selector.pseudoType()) {
+ case CSSSelector::PseudoEmpty:
+ case CSSSelector::PseudoFirstChild:
+ case CSSSelector::PseudoFirstOfType:
+ case CSSSelector::PseudoLastChild:
+ case CSSSelector::PseudoLastOfType:
+ case CSSSelector::PseudoOnlyChild:
+ case CSSSelector::PseudoOnlyOfType:
+ case CSSSelector::PseudoNthChild:
+ case CSSSelector::PseudoNthOfType:
+ case CSSSelector::PseudoNthLastChild:
+ case CSSSelector::PseudoNthLastOfType:
+ case CSSSelector::PseudoLink:
+ case CSSSelector::PseudoVisited:
+ case CSSSelector::PseudoAnyLink:
+ case CSSSelector::PseudoHover:
+ case CSSSelector::PseudoDrag:
+ case CSSSelector::PseudoFocus:
+ case CSSSelector::PseudoActive:
+ case CSSSelector::PseudoChecked:
+ case CSSSelector::PseudoEnabled:
+ case CSSSelector::PseudoDefault:
+ case CSSSelector::PseudoDisabled:
+ case CSSSelector::PseudoOptional:
+ case CSSSelector::PseudoRequired:
+ case CSSSelector::PseudoReadOnly:
+ case CSSSelector::PseudoReadWrite:
+ case CSSSelector::PseudoValid:
+ case CSSSelector::PseudoInvalid:
+ case CSSSelector::PseudoIndeterminate:
+ case CSSSelector::PseudoTarget:
+ case CSSSelector::PseudoLang:
+ case CSSSelector::PseudoRoot:
+ case CSSSelector::PseudoScope:
+ case CSSSelector::PseudoInRange:
+ case CSSSelector::PseudoOutOfRange:
+ case CSSSelector::PseudoUnresolved:
+ return true;
default:
- break;
+ return false;
+ }
+}
+
+RuleFeature::RuleFeature(StyleRule* rule, unsigned selectorIndex, bool hasDocumentSecurityOrigin)
+ : rule(rule)
+ , selectorIndex(selectorIndex)
+ , hasDocumentSecurityOrigin(hasDocumentSecurityOrigin)
+{
+}
+
+void RuleFeature::trace(Visitor* visitor)
+{
+ visitor->trace(rule);
+}
+
+// This method is somewhat conservative in what it accepts.
+RuleFeatureSet::InvalidationSetMode RuleFeatureSet::invalidationSetModeForSelector(const CSSSelector& selector)
+{
+ bool foundDescendantRelation = false;
+ bool foundIdent = false;
+ for (const CSSSelector* component = &selector; component; component = component->tagHistory()) {
+
+ if (component->match() == CSSSelector::Class || component->match() == CSSSelector::Id
+ || (component->match() == CSSSelector::Tag && component->tagQName().localName() != starAtom)
+ || component->isAttributeSelector() || component->isCustomPseudoElement()) {
+ if (!foundDescendantRelation)
+ foundIdent = true;
+ } else if (component->pseudoType() == CSSSelector::PseudoHost || component->pseudoType() == CSSSelector::PseudoAny) {
+ if (const CSSSelectorList* selectorList = component->selectorList()) {
+ for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(*selector)) {
+ InvalidationSetMode hostMode = invalidationSetModeForSelector(*selector);
+ if (hostMode == UseSubtreeStyleChange)
+ return foundDescendantRelation ? UseLocalStyleChange : UseSubtreeStyleChange;
+ if (!foundDescendantRelation && hostMode == AddFeatures)
+ foundIdent = true;
+ }
+ }
+ } else if (!isSkippableComponentForInvalidation(*component)) {
+ return foundDescendantRelation ? UseLocalStyleChange : UseSubtreeStyleChange;
+ }
+ switch (component->relation()) {
+ case CSSSelector::Descendant:
+ case CSSSelector::Child:
+ case CSSSelector::ShadowPseudo:
+ case CSSSelector::ShadowDeep:
+ foundDescendantRelation = true;
+ // Fall through!
+ case CSSSelector::SubSelector:
+ case CSSSelector::DirectAdjacent:
+ case CSSSelector::IndirectAdjacent:
+ continue;
+ default:
+ // All combinators should be handled above.
+ ASSERT_NOT_REACHED();
+ return UseLocalStyleChange;
+ }
+ }
+ return foundIdent ? AddFeatures : UseLocalStyleChange;
+}
+
+void RuleFeatureSet::extractInvalidationSetFeature(const CSSSelector& selector, InvalidationSetFeatures& features)
+{
+ if (selector.match() == CSSSelector::Tag)
+ features.tagName = selector.tagQName().localName();
+ else if (selector.match() == CSSSelector::Id)
+ features.id = selector.value();
+ else if (selector.match() == CSSSelector::Class)
+ features.classes.append(selector.value());
+ else if (selector.isAttributeSelector())
+ features.attributes.append(selector.attribute().localName());
+ else if (selector.isCustomPseudoElement())
+ features.customPseudoElement = true;
+}
+
+RuleFeatureSet::RuleFeatureSet()
+ : m_targetedStyleRecalcEnabled(RuntimeEnabledFeatures::targetedStyleRecalcEnabled())
+{
+}
+
+RuleFeatureSet::~RuleFeatureSet()
+{
+}
+
+DescendantInvalidationSet* RuleFeatureSet::invalidationSetForSelector(const CSSSelector& selector)
+{
+ if (selector.match() == CSSSelector::Class)
+ return &ensureClassInvalidationSet(selector.value());
+ if (selector.isAttributeSelector())
+ return &ensureAttributeInvalidationSet(selector.attribute().localName());
+ if (selector.match() == CSSSelector::Id)
+ return &ensureIdInvalidationSet(selector.value());
+ if (selector.match() == CSSSelector::PseudoClass) {
+ CSSSelector::PseudoType pseudo = selector.pseudoType();
+ if (pseudo == CSSSelector::PseudoHover || pseudo == CSSSelector::PseudoActive || pseudo == CSSSelector::PseudoFocus)
+ return &ensurePseudoInvalidationSet(pseudo);
+ }
+ return 0;
+}
+
+RuleFeatureSet::InvalidationSetMode RuleFeatureSet::updateInvalidationSets(const CSSSelector& selector)
+{
+ InvalidationSetMode mode = invalidationSetModeForSelector(selector);
+ if (mode != AddFeatures)
+ return mode;
+
+ InvalidationSetFeatures features;
+ if (const CSSSelector* current = extractInvalidationSetFeatures(selector, features))
+ addFeaturesToInvalidationSets(*current, features);
+ return AddFeatures;
+}
+
+const CSSSelector* RuleFeatureSet::extractInvalidationSetFeatures(const CSSSelector& selector, InvalidationSetFeatures& features)
+{
+ for (const CSSSelector* current = &selector; current; current = current->tagHistory()) {
+ extractInvalidationSetFeature(*current, features);
+ // Initialize the entry in the invalidation set map, if supported.
+ invalidationSetForSelector(*current);
+ if (current->pseudoType() == CSSSelector::PseudoHost || current->pseudoType() == CSSSelector::PseudoAny) {
+ if (const CSSSelectorList* selectorList = current->selectorList()) {
+ for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(*selector))
+ extractInvalidationSetFeatures(*selector, features);
+ }
+ }
+
+ switch (current->relation()) {
+ case CSSSelector::SubSelector:
+ break;
+ case CSSSelector::ShadowPseudo:
+ case CSSSelector::ShadowDeep:
+ features.treeBoundaryCrossing = true;
+ return current->tagHistory();
+ case CSSSelector::DirectAdjacent:
+ case CSSSelector::IndirectAdjacent:
+ features.wholeSubtree = true;
+ return current->tagHistory();
+ case CSSSelector::Descendant:
+ case CSSSelector::Child:
+ return current->tagHistory();
+ }
+ }
+ return 0;
+}
+
+void RuleFeatureSet::addFeaturesToInvalidationSets(const CSSSelector& selector, InvalidationSetFeatures& features)
+{
+ for (const CSSSelector* current = &selector; current; current = current->tagHistory()) {
+ if (DescendantInvalidationSet* invalidationSet = invalidationSetForSelector(*current)) {
+ if (features.treeBoundaryCrossing)
+ invalidationSet->setTreeBoundaryCrossing();
+ if (features.wholeSubtree) {
+ invalidationSet->setWholeSubtreeInvalid();
+ } else {
+ if (!features.id.isEmpty())
+ invalidationSet->addId(features.id);
+ if (!features.tagName.isEmpty())
+ invalidationSet->addTagName(features.tagName);
+ for (Vector<AtomicString>::const_iterator it = features.classes.begin(); it != features.classes.end(); ++it)
+ invalidationSet->addClass(*it);
+ for (Vector<AtomicString>::const_iterator it = features.attributes.begin(); it != features.attributes.end(); ++it)
+ invalidationSet->addAttribute(*it);
+ if (features.customPseudoElement)
+ invalidationSet->setCustomPseudoInvalid();
+ }
+ } else if (current->pseudoType() == CSSSelector::PseudoHost || current->pseudoType() == CSSSelector::PseudoAny) {
+ if (current->pseudoType() == CSSSelector::PseudoHost)
+ features.treeBoundaryCrossing = true;
+ if (const CSSSelectorList* selectorList = current->selectorList()) {
+ for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(*selector))
+ addFeaturesToInvalidationSets(*selector, features);
+ }
+ }
+ switch (current->relation()) {
+ case CSSSelector::SubSelector:
+ break;
+ case CSSSelector::ShadowPseudo:
+ case CSSSelector::ShadowDeep:
+ features.treeBoundaryCrossing = true;
+ features.wholeSubtree = false;
+ break;
+ case CSSSelector::Descendant:
+ case CSSSelector::Child:
+ features.wholeSubtree = false;
+ break;
+ case CSSSelector::DirectAdjacent:
+ case CSSSelector::IndirectAdjacent:
+ features.wholeSubtree = true;
+ break;
+ }
+ }
+}
+
+void RuleFeatureSet::addContentAttr(const AtomicString& attributeName)
+{
+ DescendantInvalidationSet& invalidationSet = ensureAttributeInvalidationSet(attributeName);
+ invalidationSet.setWholeSubtreeInvalid();
+}
+
+void RuleFeatureSet::collectFeaturesFromRuleData(const RuleData& ruleData)
+{
+ FeatureMetadata metadata;
+ InvalidationSetMode mode = UseSubtreeStyleChange;
+ if (m_targetedStyleRecalcEnabled)
+ mode = updateInvalidationSets(ruleData.selector());
+
+ collectFeaturesFromSelector(ruleData.selector(), metadata, mode);
+ m_metadata.add(metadata);
+
+ if (metadata.foundSiblingSelector)
+ siblingRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex(), ruleData.hasDocumentSecurityOrigin()));
+ if (ruleData.containsUncommonAttributeSelector())
+ uncommonAttributeRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex(), ruleData.hasDocumentSecurityOrigin()));
+}
+
+DescendantInvalidationSet& RuleFeatureSet::ensureClassInvalidationSet(const AtomicString& className)
+{
+ InvalidationSetMap::AddResult addResult = m_classInvalidationSets.add(className, nullptr);
+ if (addResult.isNewEntry)
+ addResult.storedValue->value = DescendantInvalidationSet::create();
+ return *addResult.storedValue->value;
+}
+
+DescendantInvalidationSet& RuleFeatureSet::ensureAttributeInvalidationSet(const AtomicString& attributeName)
+{
+ InvalidationSetMap::AddResult addResult = m_attributeInvalidationSets.add(attributeName, nullptr);
+ if (addResult.isNewEntry)
+ addResult.storedValue->value = DescendantInvalidationSet::create();
+ return *addResult.storedValue->value;
+}
+
+DescendantInvalidationSet& RuleFeatureSet::ensureIdInvalidationSet(const AtomicString& id)
+{
+ InvalidationSetMap::AddResult addResult = m_idInvalidationSets.add(id, nullptr);
+ if (addResult.isNewEntry)
+ addResult.storedValue->value = DescendantInvalidationSet::create();
+ return *addResult.storedValue->value;
+}
+
+DescendantInvalidationSet& RuleFeatureSet::ensurePseudoInvalidationSet(CSSSelector::PseudoType pseudoType)
+{
+ PseudoTypeInvalidationSetMap::AddResult addResult = m_pseudoInvalidationSets.add(pseudoType, nullptr);
+ if (addResult.isNewEntry)
+ addResult.storedValue->value = DescendantInvalidationSet::create();
+ return *addResult.storedValue->value;
+}
+
+void RuleFeatureSet::collectFeaturesFromSelector(const CSSSelector& selector)
+{
+ collectFeaturesFromSelector(selector, m_metadata, UseSubtreeStyleChange);
+}
+
+void RuleFeatureSet::collectFeaturesFromSelector(const CSSSelector& selector, RuleFeatureSet::FeatureMetadata& metadata, InvalidationSetMode mode)
+{
+ unsigned maxDirectAdjacentSelectors = 0;
+
+ for (const CSSSelector* current = &selector; current; current = current->tagHistory()) {
+ if (mode != AddFeatures) {
+ if (DescendantInvalidationSet* invalidationSet = invalidationSetForSelector(*current)) {
+ if (mode == UseSubtreeStyleChange)
+ invalidationSet->setWholeSubtreeInvalid();
+ }
+ }
+ if (current->pseudoType() == CSSSelector::PseudoFirstLine)
+ metadata.usesFirstLineRules = true;
+ if (current->isDirectAdjacentSelector()) {
+ maxDirectAdjacentSelectors++;
+ } else if (maxDirectAdjacentSelectors) {
+ if (maxDirectAdjacentSelectors > metadata.maxDirectAdjacentSelectors)
+ metadata.maxDirectAdjacentSelectors = maxDirectAdjacentSelectors;
+ maxDirectAdjacentSelectors = 0;
+ }
+ if (current->isSiblingSelector())
+ metadata.foundSiblingSelector = true;
+
+ collectFeaturesFromSelectorList(current->selectorList(), metadata, mode);
+
+ if (mode == UseLocalStyleChange && current->relation() != CSSSelector::SubSelector)
+ mode = UseSubtreeStyleChange;
}
+
+ ASSERT(!maxDirectAdjacentSelectors);
}
-void RuleFeatureSet::collectFeaturesFromSelectorList(const CSSSelectorList* selectorList)
+void RuleFeatureSet::collectFeaturesFromSelectorList(const CSSSelectorList* selectorList, RuleFeatureSet::FeatureMetadata& metadata, InvalidationSetMode mode)
{
if (!selectorList)
return;
- for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(selector)) {
- for (const CSSSelector* subSelector = selector; subSelector; subSelector = subSelector->tagHistory())
- collectFeaturesFromSelector(subSelector);
- }
+ for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(*selector))
+ collectFeaturesFromSelector(*selector, metadata, mode);
+}
+
+void RuleFeatureSet::FeatureMetadata::add(const FeatureMetadata& other)
+{
+ usesFirstLineRules = usesFirstLineRules || other.usesFirstLineRules;
+ maxDirectAdjacentSelectors = std::max(maxDirectAdjacentSelectors, other.maxDirectAdjacentSelectors);
+}
+
+void RuleFeatureSet::FeatureMetadata::clear()
+{
+ usesFirstLineRules = false;
+ foundSiblingSelector = false;
+ maxDirectAdjacentSelectors = 0;
}
void RuleFeatureSet::add(const RuleFeatureSet& other)
{
- HashSet<AtomicString>::const_iterator end = other.idsInRules.end();
- for (HashSet<AtomicString>::const_iterator it = other.idsInRules.begin(); it != end; ++it)
- idsInRules.add(*it);
- end = other.classesInRules.end();
- for (HashSet<AtomicString>::const_iterator it = other.classesInRules.begin(); it != end; ++it)
- classesInRules.add(*it);
- end = other.attrsInRules.end();
- for (HashSet<AtomicString>::const_iterator it = other.attrsInRules.begin(); it != end; ++it)
- attrsInRules.add(*it);
- siblingRules.append(other.siblingRules);
- uncommonAttributeRules.append(other.uncommonAttributeRules);
- m_usesFirstLineRules = m_usesFirstLineRules || other.m_usesFirstLineRules;
- m_maxDirectAdjacentSelectors = std::max(m_maxDirectAdjacentSelectors, other.maxDirectAdjacentSelectors());
+ for (InvalidationSetMap::const_iterator it = other.m_classInvalidationSets.begin(); it != other.m_classInvalidationSets.end(); ++it)
+ ensureClassInvalidationSet(it->key).combine(*it->value);
+ for (InvalidationSetMap::const_iterator it = other.m_attributeInvalidationSets.begin(); it != other.m_attributeInvalidationSets.end(); ++it)
+ ensureAttributeInvalidationSet(it->key).combine(*it->value);
+ for (InvalidationSetMap::const_iterator it = other.m_idInvalidationSets.begin(); it != other.m_idInvalidationSets.end(); ++it)
+ ensureIdInvalidationSet(it->key).combine(*it->value);
+ for (PseudoTypeInvalidationSetMap::const_iterator it = other.m_pseudoInvalidationSets.begin(); it != other.m_pseudoInvalidationSets.end(); ++it)
+ ensurePseudoInvalidationSet(static_cast<CSSSelector::PseudoType>(it->key)).combine(*it->value);
+
+ m_metadata.add(other.m_metadata);
+
+ siblingRules.appendVector(other.siblingRules);
+ uncommonAttributeRules.appendVector(other.uncommonAttributeRules);
}
void RuleFeatureSet::clear()
{
- idsInRules.clear();
- classesInRules.clear();
- attrsInRules.clear();
siblingRules.clear();
uncommonAttributeRules.clear();
- m_usesFirstLineRules = false;
- m_maxDirectAdjacentSelectors = 0;
+ m_metadata.clear();
+ m_classInvalidationSets.clear();
+ m_attributeInvalidationSets.clear();
+ m_idInvalidationSets.clear();
+ // We cannot clear m_styleInvalidator here, because the style invalidator might not
+ // have been evaluated yet. If not yet, in StyleInvalidator, there exists some element
+ // who has needsStyleInvlidation but does not have any invalidation list.
+ // This makes Blink not to recalc style correctly. crbug.com/344729.
+}
+
+void RuleFeatureSet::scheduleStyleInvalidationForClassChange(const SpaceSplitString& changedClasses, Element& element)
+{
+ unsigned changedSize = changedClasses.size();
+ for (unsigned i = 0; i < changedSize; ++i) {
+ addClassToInvalidationSet(changedClasses[i], element);
+ }
+}
+
+void RuleFeatureSet::scheduleStyleInvalidationForClassChange(const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses, Element& element)
+{
+ if (!oldClasses.size()) {
+ scheduleStyleInvalidationForClassChange(newClasses, element);
+ return;
+ }
+
+ // Class vectors tend to be very short. This is faster than using a hash table.
+ BitVector remainingClassBits;
+ remainingClassBits.ensureSize(oldClasses.size());
+
+ for (unsigned i = 0; i < newClasses.size(); ++i) {
+ bool found = false;
+ for (unsigned j = 0; j < oldClasses.size(); ++j) {
+ if (newClasses[i] == oldClasses[j]) {
+ // Mark each class that is still in the newClasses so we can skip doing
+ // an n^2 search below when looking for removals. We can't break from
+ // this loop early since a class can appear more than once.
+ remainingClassBits.quickSet(j);
+ found = true;
+ }
+ }
+ // Class was added.
+ if (!found)
+ addClassToInvalidationSet(newClasses[i], element);
+ }
+
+ for (unsigned i = 0; i < oldClasses.size(); ++i) {
+ if (remainingClassBits.quickGet(i))
+ continue;
+ // Class was removed.
+ addClassToInvalidationSet(oldClasses[i], element);
+ }
+}
+
+void RuleFeatureSet::scheduleStyleInvalidationForAttributeChange(const QualifiedName& attributeName, Element& element)
+{
+
+ if (RefPtrWillBeRawPtr<DescendantInvalidationSet> invalidationSet = m_attributeInvalidationSets.get(attributeName.localName()))
+ m_styleInvalidator.scheduleInvalidation(invalidationSet, element);
+}
+
+void RuleFeatureSet::scheduleStyleInvalidationForIdChange(const AtomicString& oldId, const AtomicString& newId, Element& element)
+{
+ if (!oldId.isEmpty()) {
+ if (RefPtrWillBeRawPtr<DescendantInvalidationSet> invalidationSet = m_idInvalidationSets.get(oldId))
+ m_styleInvalidator.scheduleInvalidation(invalidationSet, element);
+ }
+ if (!newId.isEmpty()) {
+ if (RefPtrWillBeRawPtr<DescendantInvalidationSet> invalidationSet = m_idInvalidationSets.get(newId))
+ m_styleInvalidator.scheduleInvalidation(invalidationSet, element);
+ }
+}
+
+void RuleFeatureSet::scheduleStyleInvalidationForPseudoChange(CSSSelector::PseudoType pseudo, Element& element)
+{
+ if (RefPtrWillBeRawPtr<DescendantInvalidationSet> invalidationSet = m_pseudoInvalidationSets.get(pseudo))
+ m_styleInvalidator.scheduleInvalidation(invalidationSet, element);
+}
+
+void RuleFeatureSet::addClassToInvalidationSet(const AtomicString& className, Element& element)
+{
+ if (RefPtrWillBeRawPtr<DescendantInvalidationSet> invalidationSet = m_classInvalidationSets.get(className))
+ m_styleInvalidator.scheduleInvalidation(invalidationSet, element);
+}
+
+StyleInvalidator& RuleFeatureSet::styleInvalidator()
+{
+ return m_styleInvalidator;
+}
+
+void RuleFeatureSet::trace(Visitor* visitor)
+{
+ visitor->trace(siblingRules);
+ visitor->trace(uncommonAttributeRules);
+ visitor->trace(m_classInvalidationSets);
+ visitor->trace(m_attributeInvalidationSets);
+ visitor->trace(m_idInvalidationSets);
+ visitor->trace(m_pseudoInvalidationSets);
+ visitor->trace(m_styleInvalidator);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/RuleFeature.h b/chromium/third_party/WebKit/Source/core/css/RuleFeature.h
index b51863c4289..bc098d89244 100644
--- a/chromium/third_party/WebKit/Source/core/css/RuleFeature.h
+++ b/chromium/third_party/WebKit/Source/core/css/RuleFeature.h
@@ -22,76 +22,172 @@
#ifndef RuleFeature_h
#define RuleFeature_h
+#include "core/css/CSSSelector.h"
+#include "core/css/invalidation/StyleInvalidator.h"
#include "wtf/Forward.h"
#include "wtf/HashSet.h"
#include "wtf/text/AtomicStringHash.h"
namespace WebCore {
-class StyleRule;
-class CSSSelector;
class CSSSelectorList;
+class DescendantInvalidationSet;
+class Document;
+class Node;
+class QualifiedName;
+class RuleData;
+class ShadowRoot;
+class SpaceSplitString;
+class StyleRule;
struct RuleFeature {
- RuleFeature(StyleRule* rule, unsigned selectorIndex, bool hasDocumentSecurityOrigin)
- : rule(rule)
- , selectorIndex(selectorIndex)
- , hasDocumentSecurityOrigin(hasDocumentSecurityOrigin)
- {
- }
- StyleRule* rule;
+ ALLOW_ONLY_INLINE_ALLOCATION();
+public:
+ RuleFeature(StyleRule* rule, unsigned selectorIndex, bool hasDocumentSecurityOrigin);
+
+ void trace(Visitor*);
+
+ RawPtrWillBeMember<StyleRule> rule;
unsigned selectorIndex;
bool hasDocumentSecurityOrigin;
};
class RuleFeatureSet {
+ DISALLOW_ALLOCATION();
public:
- RuleFeatureSet()
- : m_usesFirstLineRules(false)
- , m_maxDirectAdjacentSelectors(0)
- { }
+ RuleFeatureSet();
+ ~RuleFeatureSet();
void add(const RuleFeatureSet&);
void clear();
- void collectFeaturesFromSelector(const CSSSelector*);
+ void collectFeaturesFromSelector(const CSSSelector&);
+ void collectFeaturesFromRuleData(const RuleData&);
bool usesSiblingRules() const { return !siblingRules.isEmpty(); }
- bool usesFirstLineRules() const { return m_usesFirstLineRules; }
+ bool usesFirstLineRules() const { return m_metadata.usesFirstLineRules; }
- unsigned maxDirectAdjacentSelectors() const { return m_maxDirectAdjacentSelectors; }
- void setMaxDirectAdjacentSelectors(unsigned value) { m_maxDirectAdjacentSelectors = std::max(value, m_maxDirectAdjacentSelectors); }
+ unsigned maxDirectAdjacentSelectors() const { return m_metadata.maxDirectAdjacentSelectors; }
+ void setMaxDirectAdjacentSelectors(unsigned value) { m_metadata.maxDirectAdjacentSelectors = std::max(value, m_metadata.maxDirectAdjacentSelectors); }
inline bool hasSelectorForAttribute(const AtomicString& attributeName) const
{
ASSERT(!attributeName.isEmpty());
- return attrsInRules.contains(attributeName);
+ return m_attributeInvalidationSets.contains(attributeName);
}
inline bool hasSelectorForClass(const AtomicString& classValue) const
{
ASSERT(!classValue.isEmpty());
- return classesInRules.contains(classValue);
+ return m_classInvalidationSets.contains(classValue);
}
inline bool hasSelectorForId(const AtomicString& idValue) const
{
- ASSERT(!idValue.isEmpty());
- return idsInRules.contains(idValue);
+ return m_idInvalidationSets.contains(idValue);
}
- HashSet<AtomicString> idsInRules;
- HashSet<AtomicString> classesInRules;
- HashSet<AtomicString> attrsInRules;
- Vector<RuleFeature> siblingRules;
- Vector<RuleFeature> uncommonAttributeRules;
-private:
- void collectFeaturesFromSelectorList(const CSSSelectorList*);
+ void scheduleStyleInvalidationForClassChange(const SpaceSplitString& changedClasses, Element&);
+ void scheduleStyleInvalidationForClassChange(const SpaceSplitString& oldClasses, const SpaceSplitString& newClasses, Element&);
+ void scheduleStyleInvalidationForAttributeChange(const QualifiedName& attributeName, Element&);
+ void scheduleStyleInvalidationForIdChange(const AtomicString& oldId, const AtomicString& newId, Element&);
+ void scheduleStyleInvalidationForPseudoChange(CSSSelector::PseudoType, Element&);
+
+ bool hasIdsInSelectors() const
+ {
+ return m_idInvalidationSets.size() > 0;
+ }
- bool m_usesFirstLineRules;
- unsigned m_maxDirectAdjacentSelectors;
+ // Marks the given attribute name as "appearing in a selector". Used for
+ // CSS properties such as content: ... attr(...) ...
+ // FIXME: record these internally to this class instead calls from StyleResolver to here.
+ void addContentAttr(const AtomicString& attributeName);
+
+ StyleInvalidator& styleInvalidator();
+
+ void trace(Visitor*);
+
+ WillBeHeapVector<RuleFeature> siblingRules;
+ WillBeHeapVector<RuleFeature> uncommonAttributeRules;
+
+private:
+ typedef WillBeHeapHashMap<AtomicString, RefPtrWillBeMember<DescendantInvalidationSet> > InvalidationSetMap;
+ typedef WillBeHeapHashMap<CSSSelector::PseudoType, RefPtrWillBeMember<DescendantInvalidationSet>, WTF::IntHash<unsigned>, WTF::UnsignedWithZeroKeyHashTraits<unsigned> > PseudoTypeInvalidationSetMap;
+
+ struct FeatureMetadata {
+ FeatureMetadata()
+ : usesFirstLineRules(false)
+ , foundSiblingSelector(false)
+ , maxDirectAdjacentSelectors(0)
+ { }
+ void add(const FeatureMetadata& other);
+ void clear();
+
+ bool usesFirstLineRules;
+ bool foundSiblingSelector;
+ unsigned maxDirectAdjacentSelectors;
+ };
+
+ enum InvalidationSetMode {
+ AddFeatures,
+ UseLocalStyleChange,
+ UseSubtreeStyleChange
+ };
+
+ static InvalidationSetMode invalidationSetModeForSelector(const CSSSelector&);
+
+ void collectFeaturesFromSelector(const CSSSelector&, FeatureMetadata&, InvalidationSetMode);
+ void collectFeaturesFromSelectorList(const CSSSelectorList*, FeatureMetadata&, InvalidationSetMode);
+
+ DescendantInvalidationSet& ensureClassInvalidationSet(const AtomicString& className);
+ DescendantInvalidationSet& ensureAttributeInvalidationSet(const AtomicString& attributeName);
+ DescendantInvalidationSet& ensureIdInvalidationSet(const AtomicString& attributeName);
+ DescendantInvalidationSet& ensurePseudoInvalidationSet(CSSSelector::PseudoType);
+ DescendantInvalidationSet* invalidationSetForSelector(const CSSSelector&);
+
+ InvalidationSetMode updateInvalidationSets(const CSSSelector&);
+
+ struct InvalidationSetFeatures {
+ InvalidationSetFeatures()
+ : customPseudoElement(false)
+ , treeBoundaryCrossing(false)
+ , wholeSubtree(false)
+ { }
+ Vector<AtomicString> classes;
+ Vector<AtomicString> attributes;
+ AtomicString id;
+ AtomicString tagName;
+ bool customPseudoElement;
+ bool treeBoundaryCrossing;
+ bool wholeSubtree;
+ };
+
+ static void extractInvalidationSetFeature(const CSSSelector&, InvalidationSetFeatures&);
+ const CSSSelector* extractInvalidationSetFeatures(const CSSSelector&, InvalidationSetFeatures&);
+ void addFeaturesToInvalidationSets(const CSSSelector&, InvalidationSetFeatures&);
+
+ void addClassToInvalidationSet(const AtomicString& className, Element&);
+
+ FeatureMetadata m_metadata;
+ InvalidationSetMap m_classInvalidationSets;
+ InvalidationSetMap m_attributeInvalidationSets;
+ InvalidationSetMap m_idInvalidationSets;
+ PseudoTypeInvalidationSetMap m_pseudoInvalidationSets;
+ bool m_targetedStyleRecalcEnabled;
+ StyleInvalidator m_styleInvalidator;
};
+
} // namespace WebCore
+namespace WTF {
+
+template <> struct VectorTraits<WebCore::RuleFeature> : VectorTraitsBase<WebCore::RuleFeature> {
+ static const bool needsDestruction = false;
+ static const bool canInitializeWithMemset = true;
+ static const bool canMoveWithMemcpy = true;
+};
+
+} // namespace WTF
+
#endif // RuleFeature_h
diff --git a/chromium/third_party/WebKit/Source/core/css/RuleSet.cpp b/chromium/third_party/WebKit/Source/core/css/RuleSet.cpp
index f7a0325f543..7e2a8f344fd 100644
--- a/chromium/third_party/WebKit/Source/core/css/RuleSet.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/RuleSet.cpp
@@ -29,39 +29,43 @@
#include "config.h"
#include "core/css/RuleSet.h"
-#include "HTMLNames.h"
-#include "RuntimeEnabledFeatures.h"
+#include "core/HTMLNames.h"
#include "core/css/CSSFontSelector.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSSelectorList.h"
#include "core/css/SelectorChecker.h"
-#include "core/css/SelectorCheckerFastPath.h"
#include "core/css/SelectorFilter.h"
#include "core/css/StyleRuleImport.h"
#include "core/css/StyleSheetContents.h"
#include "core/html/track/TextTrackCue.h"
+#include "platform/RuntimeEnabledFeatures.h"
+#include "platform/TraceEvent.h"
+#include "platform/heap/HeapTerminatedArrayBuilder.h"
#include "platform/weborigin/SecurityOrigin.h"
+#include "wtf/TerminatedArrayBuilder.h"
+
namespace WebCore {
using namespace HTMLNames;
// -----------------------------------------------------------------
-static inline bool isSelectorMatchingHTMLBasedOnRuleHash(const CSSSelector* selector)
+static inline bool isSelectorMatchingHTMLBasedOnRuleHash(const CSSSelector& selector)
{
- ASSERT(selector);
- if (selector->m_match == CSSSelector::Tag) {
- const AtomicString& selectorNamespace = selector->tagQName().namespaceURI();
+ if (selector.match() == CSSSelector::Tag) {
+ const AtomicString& selectorNamespace = selector.tagQName().namespaceURI();
if (selectorNamespace != starAtom && selectorNamespace != xhtmlNamespaceURI)
return false;
- if (selector->relation() == CSSSelector::SubSelector)
- return isSelectorMatchingHTMLBasedOnRuleHash(selector->tagHistory());
+ if (selector.relation() == CSSSelector::SubSelector) {
+ ASSERT(selector.tagHistory());
+ return isSelectorMatchingHTMLBasedOnRuleHash(*selector.tagHistory());
+ }
return true;
}
if (SelectorChecker::isCommonPseudoClassSelector(selector))
return true;
- return selector->m_match == CSSSelector::Id || selector->m_match == CSSSelector::Class;
+ return selector.match() == CSSSelector::Id || selector.match() == CSSSelector::Class;
}
static inline bool selectorListContainsUncommonAttributeSelector(const CSSSelector* selector)
@@ -69,7 +73,7 @@ static inline bool selectorListContainsUncommonAttributeSelector(const CSSSelect
const CSSSelectorList* selectorList = selector->selectorList();
if (!selectorList)
return false;
- for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(selector)) {
+ for (const CSSSelector* selector = selectorList->first(); selector; selector = CSSSelectorList::next(*selector)) {
for (const CSSSelector* component = selector; component; component = component->tagHistory()) {
if (component->isAttributeSelector())
return true;
@@ -84,118 +88,48 @@ static inline bool isCommonAttributeSelectorAttribute(const QualifiedName& attri
return attribute == typeAttr || attribute == readonlyAttr;
}
-static inline bool containsUncommonAttributeSelector(const CSSSelector* selector)
+static inline bool containsUncommonAttributeSelector(const CSSSelector& selector)
{
- for (; selector; selector = selector->tagHistory()) {
+ const CSSSelector* current = &selector;
+ for (; current; current = current->tagHistory()) {
// Allow certain common attributes (used in the default style) in the selectors that match the current element.
- if (selector->isAttributeSelector() && !isCommonAttributeSelectorAttribute(selector->attribute()))
+ if (current->isAttributeSelector() && !isCommonAttributeSelectorAttribute(current->attribute()))
return true;
- if (selectorListContainsUncommonAttributeSelector(selector))
+ if (selectorListContainsUncommonAttributeSelector(current))
return true;
- if (selector->relation() != CSSSelector::SubSelector) {
- selector = selector->tagHistory();
+ if (current->relation() != CSSSelector::SubSelector) {
+ current = current->tagHistory();
break;
}
}
- for (; selector; selector = selector->tagHistory()) {
- if (selector->isAttributeSelector())
+ for (; current; current = current->tagHistory()) {
+ if (current->isAttributeSelector())
return true;
- if (selectorListContainsUncommonAttributeSelector(selector))
+ if (selectorListContainsUncommonAttributeSelector(current))
return true;
}
return false;
}
-static inline PropertyWhitelistType determinePropertyWhitelistType(const AddRuleFlags addRuleFlags, const CSSSelector* selector)
+static inline PropertyWhitelistType determinePropertyWhitelistType(const AddRuleFlags addRuleFlags, const CSSSelector& selector)
{
- if (addRuleFlags & RuleIsInRegionRule)
- return PropertyWhitelistRegion;
- for (const CSSSelector* component = selector; component; component = component->tagHistory()) {
- if (component->pseudoType() == CSSSelector::PseudoCue || (component->m_match == CSSSelector::PseudoElement && component->value() == TextTrackCue::cueShadowPseudoId()))
+ for (const CSSSelector* component = &selector; component; component = component->tagHistory()) {
+ if (component->pseudoType() == CSSSelector::PseudoCue || (component->match() == CSSSelector::PseudoElement && component->value() == TextTrackCue::cueShadowPseudoId()))
return PropertyWhitelistCue;
+ if (component->pseudoType() == CSSSelector::PseudoFirstLetter)
+ return PropertyWhitelistFirstLetter;
}
return PropertyWhitelistNone;
}
-namespace {
-
-// FIXME: Should we move this class to WTF?
-template<typename T>
-class TerminatedArrayBuilder {
-public:
- explicit TerminatedArrayBuilder(PassOwnPtr<T> array)
- : m_array(array)
- , m_count(0)
- , m_capacity(0)
- {
- if (!m_array)
- return;
- for (T* item = m_array.get(); !item->isLastInArray(); ++item)
- ++m_count;
- ++m_count; // To count the last item itself.
- m_capacity = m_count;
- }
-
- void grow(size_t count)
- {
- ASSERT(count);
- if (!m_array) {
- ASSERT(!m_count);
- ASSERT(!m_capacity);
- m_capacity = count;
- m_array = adoptPtr(static_cast<T*>(fastMalloc(m_capacity * sizeof(T))));
- return;
- }
- m_capacity += count;
- m_array = adoptPtr(static_cast<T*>(fastRealloc(m_array.leakPtr(), m_capacity * sizeof(T))));
- m_array.get()[m_count - 1].setLastInArray(false);
- }
-
- void append(const T& item)
- {
- RELEASE_ASSERT(m_count < m_capacity);
- ASSERT(!item.isLastInArray());
- m_array.get()[m_count++] = item;
- }
-
- PassOwnPtr<T> release()
- {
- RELEASE_ASSERT(m_count == m_capacity);
- if (m_array)
- m_array.get()[m_count - 1].setLastInArray(true);
- assertValid();
- return m_array.release();
- }
-
-private:
-#ifndef NDEBUG
- void assertValid()
- {
- for (size_t i = 0; i < m_count; ++i) {
- bool isLastInArray = (i + 1 == m_count);
- ASSERT(m_array.get()[i].isLastInArray() == isLastInArray);
- }
- }
-#else
- void assertValid() { }
-#endif
-
- OwnPtr<T> m_array;
- size_t m_count;
- size_t m_capacity;
-};
-
-}
-
RuleData::RuleData(StyleRule* rule, unsigned selectorIndex, unsigned position, AddRuleFlags addRuleFlags)
: m_rule(rule)
, m_selectorIndex(selectorIndex)
, m_isLastInArray(false)
, m_position(position)
- , m_hasFastCheckableSelector((addRuleFlags & RuleCanUseFastCheckSelector) && SelectorCheckerFastPath::canUse(selector()))
- , m_specificity(selector()->specificity())
- , m_hasMultipartSelector(!!selector()->tagHistory())
+ , m_specificity(selector().specificity())
+ , m_hasMultipartSelector(!!selector().tagHistory())
, m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash(isSelectorMatchingHTMLBasedOnRuleHash(selector()))
, m_containsUncommonAttributeSelector(WebCore::containsUncommonAttributeSelector(selector()))
, m_linkMatchType(SelectorChecker::determineLinkMatchType(selector()))
@@ -207,66 +141,78 @@ RuleData::RuleData(StyleRule* rule, unsigned selectorIndex, unsigned position, A
SelectorFilter::collectIdentifierHashes(selector(), m_descendantSelectorIdentifierHashes, maximumIdentifierCount);
}
-static void collectFeaturesFromRuleData(RuleFeatureSet& features, const RuleData& ruleData)
+void RuleSet::addToRuleSet(const AtomicString& key, PendingRuleMap& map, const RuleData& ruleData)
{
- bool foundSiblingSelector = false;
- unsigned maxDirectAdjacentSelectors = 0;
- for (const CSSSelector* selector = ruleData.selector(); selector; selector = selector->tagHistory()) {
- features.collectFeaturesFromSelector(selector);
-
- if (const CSSSelectorList* selectorList = selector->selectorList()) {
- for (const CSSSelector* subSelector = selectorList->first(); subSelector; subSelector = CSSSelectorList::next(subSelector)) {
- // FIXME: Shouldn't this be checking subSelector->isSiblingSelector()?
- if (!foundSiblingSelector && selector->isSiblingSelector())
- foundSiblingSelector = true;
- if (subSelector->isDirectAdjacentSelector())
- maxDirectAdjacentSelectors++;
- features.collectFeaturesFromSelector(subSelector);
- }
- } else {
- if (!foundSiblingSelector && selector->isSiblingSelector())
- foundSiblingSelector = true;
- if (selector->isDirectAdjacentSelector())
- maxDirectAdjacentSelectors++;
- }
- }
- features.setMaxDirectAdjacentSelectors(maxDirectAdjacentSelectors);
- if (foundSiblingSelector)
- features.siblingRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex(), ruleData.hasDocumentSecurityOrigin()));
- if (ruleData.containsUncommonAttributeSelector())
- features.uncommonAttributeRules.append(RuleFeature(ruleData.rule(), ruleData.selectorIndex(), ruleData.hasDocumentSecurityOrigin()));
+ OwnPtrWillBeMember<WillBeHeapLinkedStack<RuleData> >& rules = map.add(key, nullptr).storedValue->value;
+ if (!rules)
+ rules = adoptPtrWillBeNoop(new WillBeHeapLinkedStack<RuleData>);
+ rules->push(ruleData);
}
-void RuleSet::addToRuleSet(StringImpl* key, PendingRuleMap& map, const RuleData& ruleData)
+static void extractValuesforSelector(const CSSSelector* selector, AtomicString& id, AtomicString& className, AtomicString& customPseudoElementName, AtomicString& tagName)
{
- if (!key)
- return;
- OwnPtr<LinkedStack<RuleData> >& rules = map.add(key, nullptr).iterator->value;
- if (!rules)
- rules = adoptPtr(new LinkedStack<RuleData>);
- rules->push(ruleData);
+ switch (selector->match()) {
+ case CSSSelector::Id:
+ id = selector->value();
+ break;
+ case CSSSelector::Class:
+ className = selector->value();
+ break;
+ case CSSSelector::Tag:
+ if (selector->tagQName().localName() != starAtom)
+ tagName = selector->tagQName().localName();
+ break;
+ default:
+ break;
+ }
+ if (selector->isCustomPseudoElement())
+ customPseudoElementName = selector->value();
}
-bool RuleSet::findBestRuleSetAndAdd(const CSSSelector* component, RuleData& ruleData)
+bool RuleSet::findBestRuleSetAndAdd(const CSSSelector& component, RuleData& ruleData)
{
- if (component->m_match == CSSSelector::Id) {
- addToRuleSet(component->value().impl(), ensurePendingRules()->idRules, ruleData);
+ AtomicString id;
+ AtomicString className;
+ AtomicString customPseudoElementName;
+ AtomicString tagName;
+
+#ifndef NDEBUG
+ m_allRules.append(ruleData);
+#endif
+
+ const CSSSelector* it = &component;
+ for (; it && it->relation() == CSSSelector::SubSelector; it = it->tagHistory()) {
+ extractValuesforSelector(it, id, className, customPseudoElementName, tagName);
+ }
+ // FIXME: this null check should not be necessary. See crbug.com/358475
+ if (it)
+ extractValuesforSelector(it, id, className, customPseudoElementName, tagName);
+
+ // Prefer rule sets in order of most likely to apply infrequently.
+ if (!id.isEmpty()) {
+ addToRuleSet(id, ensurePendingRules()->idRules, ruleData);
return true;
}
- if (component->m_match == CSSSelector::Class) {
- addToRuleSet(component->value().impl(), ensurePendingRules()->classRules, ruleData);
+ if (!className.isEmpty()) {
+ addToRuleSet(className, ensurePendingRules()->classRules, ruleData);
return true;
}
- if (component->isCustomPseudoElement()) {
- addToRuleSet(component->value().impl(), ensurePendingRules()->shadowPseudoElementRules, ruleData);
+ if (!customPseudoElementName.isEmpty()) {
+ // Custom pseudos come before ids and classes in the order of tagHistory, and have a relation of
+ // ShadowPseudo between them. Therefore we should never be a situation where extractValuesforSelector
+ // finsd id and className in addition to custom pseudo.
+ ASSERT(id.isEmpty() && className.isEmpty());
+ addToRuleSet(customPseudoElementName, ensurePendingRules()->shadowPseudoElementRules, ruleData);
return true;
}
- if (component->pseudoType() == CSSSelector::PseudoCue) {
+
+ if (component.pseudoType() == CSSSelector::PseudoCue) {
m_cuePseudoRules.append(ruleData);
return true;
}
+
if (SelectorChecker::isCommonPseudoClassSelector(component)) {
- switch (component->pseudoType()) {
+ switch (component.pseudoType()) {
case CSSSelector::PseudoLink:
case CSSSelector::PseudoVisited:
case CSSSelector::PseudoAnyLink:
@@ -281,25 +227,18 @@ bool RuleSet::findBestRuleSetAndAdd(const CSSSelector* component, RuleData& rule
}
}
- if (component->m_match == CSSSelector::Tag) {
- if (component->tagQName().localName() != starAtom) {
- // If this is part of a subselector chain, recurse ahead to find a narrower set (ID/class.)
- if (component->relation() == CSSSelector::SubSelector
- && (component->tagHistory()->m_match == CSSSelector::Class || component->tagHistory()->m_match == CSSSelector::Id || SelectorChecker::isCommonPseudoClassSelector(component->tagHistory()))
- && findBestRuleSetAndAdd(component->tagHistory(), ruleData))
- return true;
-
- addToRuleSet(component->tagQName().localName().impl(), ensurePendingRules()->tagRules, ruleData);
- return true;
- }
+ if (!tagName.isEmpty()) {
+ addToRuleSet(tagName, ensurePendingRules()->tagRules, ruleData);
+ return true;
}
+
return false;
}
void RuleSet::addRule(StyleRule* rule, unsigned selectorIndex, AddRuleFlags addRuleFlags)
{
RuleData ruleData(rule, selectorIndex, m_ruleCount++, addRuleFlags);
- collectFeaturesFromRuleData(m_features, ruleData);
+ m_features.collectFeaturesFromRuleData(ruleData);
if (!findBestRuleSetAndAdd(ruleData.selector(), ruleData)) {
// If we didn't find a specialized map to stick it in, file under universal rules.
@@ -331,32 +270,7 @@ void RuleSet::addKeyframesRule(StyleRuleKeyframes* rule)
m_keyframesRules.append(rule);
}
-void RuleSet::addRegionRule(StyleRuleRegion* regionRule, bool hasDocumentSecurityOrigin)
-{
- ensurePendingRules(); // So that m_regionSelectorsAndRuleSets.shrinkToFit() gets called.
- OwnPtr<RuleSet> regionRuleSet = RuleSet::create();
- // The region rule set should take into account the position inside the parent rule set.
- // Otherwise, the rules inside region block might be incorrectly positioned before other similar rules from
- // the stylesheet that contains the region block.
- regionRuleSet->m_ruleCount = m_ruleCount;
-
- // Collect the region rules into a rule set
- // FIXME: Should this add other types of rules? (i.e. use addChildRules() directly?)
- const Vector<RefPtr<StyleRuleBase> >& childRules = regionRule->childRules();
- AddRuleFlags addRuleFlags = hasDocumentSecurityOrigin ? RuleHasDocumentSecurityOrigin : RuleHasNoSpecialState;
- addRuleFlags = static_cast<AddRuleFlags>(addRuleFlags | RuleIsInRegionRule | RuleCanUseFastCheckSelector);
- for (unsigned i = 0; i < childRules.size(); ++i) {
- StyleRuleBase* regionStylingRule = childRules[i].get();
- if (regionStylingRule->isStyleRule())
- regionRuleSet->addStyleRule(toStyleRule(regionStylingRule), addRuleFlags);
- }
- // Update the "global" rule count so that proper order is maintained
- m_ruleCount = regionRuleSet->m_ruleCount;
-
- m_regionSelectorsAndRuleSets.append(RuleSetSelectorPair(regionRule->selectorList().first(), regionRuleSet.release()));
-}
-
-void RuleSet::addChildRules(const Vector<RefPtr<StyleRuleBase> >& rules, const MediaQueryEvaluator& medium, AddRuleFlags addRuleFlags)
+void RuleSet::addChildRules(const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& rules, const MediaQueryEvaluator& medium, AddRuleFlags addRuleFlags)
{
for (unsigned i = 0; i < rules.size(); ++i) {
StyleRuleBase* rule = rules[i].get();
@@ -366,7 +280,7 @@ void RuleSet::addChildRules(const Vector<RefPtr<StyleRuleBase> >& rules, const M
const CSSSelectorList& selectorList = styleRule->selectorList();
for (size_t selectorIndex = 0; selectorIndex != kNotFound; selectorIndex = selectorList.indexOfNextSelectorAfter(selectorIndex)) {
- if (selectorList.hasCombinatorCrossingTreeBoundaryAt(selectorIndex)) {
+ if (selectorList.selectorCrossesTreeScopes(selectorIndex)) {
m_treeBoundaryCrossingRules.append(MinimalRuleData(styleRule, selectorIndex, addRuleFlags));
} else if (selectorList.hasShadowDistributedAt(selectorIndex)) {
m_shadowDistributedRules.append(MinimalRuleData(styleRule, selectorIndex, addRuleFlags));
@@ -384,8 +298,6 @@ void RuleSet::addChildRules(const Vector<RefPtr<StyleRuleBase> >& rules, const M
addFontFaceRule(toStyleRuleFontFace(rule));
} else if (rule->isKeyframesRule()) {
addKeyframesRule(toStyleRuleKeyframes(rule));
- } else if (rule->isRegionRule()) {
- addRegionRule(toStyleRuleRegion(rule), addRuleFlags & RuleHasDocumentSecurityOrigin);
} else if (rule->isViewportRule()) {
addViewportRule(toStyleRuleViewport(rule));
} else if (rule->isSupportsRule() && toStyleRuleSupports(rule)->conditionIsSupported()) {
@@ -396,10 +308,12 @@ void RuleSet::addChildRules(const Vector<RefPtr<StyleRuleBase> >& rules, const M
void RuleSet::addRulesFromSheet(StyleSheetContents* sheet, const MediaQueryEvaluator& medium, AddRuleFlags addRuleFlags)
{
+ TRACE_EVENT0("webkit", "RuleSet::addRulesFromSheet");
+
ASSERT(sheet);
addRuleFlags = static_cast<AddRuleFlags>(addRuleFlags | RuleCanUseFastCheckSelector);
- const Vector<RefPtr<StyleRuleImport> >& importRules = sheet->importRules();
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleImport> >& importRules = sheet->importRules();
for (unsigned i = 0; i < importRules.size(); ++i) {
StyleRuleImport* importRule = importRules[i].get();
if (importRule->styleSheet() && (!importRule->mediaQueries() || medium.eval(importRule->mediaQueries(), &m_viewportDependentMediaQueryResults)))
@@ -419,10 +333,10 @@ void RuleSet::compactPendingRules(PendingRuleMap& pendingMap, CompactRuleMap& co
{
PendingRuleMap::iterator end = pendingMap.end();
for (PendingRuleMap::iterator it = pendingMap.begin(); it != end; ++it) {
- OwnPtr<LinkedStack<RuleData> > pendingRules = it->value.release();
- CompactRuleMap::iterator compactRules = compactMap.add(it->key, nullptr).iterator;
+ OwnPtrWillBeRawPtr<WillBeHeapLinkedStack<RuleData> > pendingRules = it->value.release();
+ CompactRuleMap::ValueType* compactRules = compactMap.add(it->key, nullptr).storedValue;
- TerminatedArrayBuilder<RuleData> builder(compactRules->value.release());
+ WillBeHeapTerminatedArrayBuilder<RuleData> builder(compactRules->value.release());
builder.grow(pendingRules->size());
while (!pendingRules->isEmpty()) {
builder.append(pendingRules->peek());
@@ -436,7 +350,7 @@ void RuleSet::compactPendingRules(PendingRuleMap& pendingMap, CompactRuleMap& co
void RuleSet::compactRules()
{
ASSERT(m_pendingRules);
- OwnPtr<PendingRuleMaps> pendingRules = m_pendingRules.release();
+ OwnPtrWillBeRawPtr<PendingRuleMaps> pendingRules = m_pendingRules.release();
compactPendingRules(pendingRules->idRules, m_idRules);
compactPendingRules(pendingRules->classRules, m_classRules);
compactPendingRules(pendingRules->tagRules, m_tagRules);
@@ -453,4 +367,56 @@ void RuleSet::compactRules()
m_shadowDistributedRules.shrinkToFit();
}
+void MinimalRuleData::trace(Visitor* visitor)
+{
+ visitor->trace(m_rule);
+}
+
+void RuleData::trace(Visitor* visitor)
+{
+ visitor->trace(m_rule);
+}
+
+void RuleSet::PendingRuleMaps::trace(Visitor* visitor)
+{
+ visitor->trace(idRules);
+ visitor->trace(classRules);
+ visitor->trace(tagRules);
+ visitor->trace(shadowPseudoElementRules);
+}
+
+void RuleSet::trace(Visitor* visitor)
+{
+#if ENABLE(OILPAN)
+ visitor->trace(m_idRules);
+ visitor->trace(m_classRules);
+ visitor->trace(m_tagRules);
+ visitor->trace(m_shadowPseudoElementRules);
+ visitor->trace(m_linkPseudoClassRules);
+ visitor->trace(m_cuePseudoRules);
+ visitor->trace(m_focusPseudoClassRules);
+ visitor->trace(m_universalRules);
+ visitor->trace(m_features);
+ visitor->trace(m_pageRules);
+ visitor->trace(m_viewportRules);
+ visitor->trace(m_fontFaceRules);
+ visitor->trace(m_keyframesRules);
+ visitor->trace(m_treeBoundaryCrossingRules);
+ visitor->trace(m_shadowDistributedRules);
+ visitor->trace(m_viewportDependentMediaQueryResults);
+ visitor->trace(m_pendingRules);
+#ifndef NDEBUG
+ visitor->trace(m_allRules);
+#endif
+#endif
+}
+
+#ifndef NDEBUG
+void RuleSet::show()
+{
+ for (WillBeHeapVector<RuleData>::const_iterator it = m_allRules.begin(); it != m_allRules.end(); ++it)
+ it->selector().show();
+}
+#endif
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/RuleSet.h b/chromium/third_party/WebKit/Source/core/css/RuleSet.h
index d8249a3edb9..e7538f58100 100644
--- a/chromium/third_party/WebKit/Source/core/css/RuleSet.h
+++ b/chromium/third_party/WebKit/Source/core/css/RuleSet.h
@@ -27,9 +27,12 @@
#include "core/css/RuleFeature.h"
#include "core/css/StyleRule.h"
#include "core/css/resolver/MediaQueryResult.h"
+#include "platform/heap/HeapLinkedStack.h"
+#include "platform/heap/HeapTerminatedArray.h"
#include "wtf/Forward.h"
#include "wtf/HashMap.h"
#include "wtf/LinkedStack.h"
+#include "wtf/TerminatedArray.h"
namespace WebCore {
@@ -37,21 +40,21 @@ enum AddRuleFlags {
RuleHasNoSpecialState = 0,
RuleHasDocumentSecurityOrigin = 1,
RuleCanUseFastCheckSelector = 1 << 1,
- RuleIsInRegionRule = 1 << 2,
};
enum PropertyWhitelistType {
PropertyWhitelistNone = 0,
- PropertyWhitelistRegion,
- PropertyWhitelistCue
+ PropertyWhitelistCue,
+ PropertyWhitelistFirstLetter,
};
class CSSSelector;
class MediaQueryEvaluator;
-class StyleRuleRegion;
class StyleSheetContents;
-struct MinimalRuleData {
+class MinimalRuleData {
+ ALLOW_ONLY_INLINE_ALLOCATION();
+public:
MinimalRuleData(StyleRule* rule, unsigned selectorIndex, AddRuleFlags flags)
: m_rule(rule)
, m_selectorIndex(selectorIndex)
@@ -59,25 +62,26 @@ struct MinimalRuleData {
{
}
- StyleRule* m_rule;
+ void trace(Visitor*);
+
+ RawPtrWillBeMember<StyleRule> m_rule;
unsigned m_selectorIndex;
AddRuleFlags m_flags;
};
class RuleData {
- WTF_MAKE_FAST_ALLOCATED;
+ ALLOW_ONLY_INLINE_ALLOCATION();
public:
RuleData(StyleRule*, unsigned selectorIndex, unsigned position, AddRuleFlags);
unsigned position() const { return m_position; }
StyleRule* rule() const { return m_rule; }
- const CSSSelector* selector() const { return m_rule->selectorList().selectorAt(m_selectorIndex); }
+ const CSSSelector& selector() const { return m_rule->selectorList().selectorAt(m_selectorIndex); }
unsigned selectorIndex() const { return m_selectorIndex; }
bool isLastInArray() const { return m_isLastInArray; }
void setLastInArray(bool flag) { m_isLastInArray = flag; }
- bool hasFastCheckableSelector() const { return m_hasFastCheckableSelector; }
bool hasMultipartSelector() const { return m_hasMultipartSelector; }
bool hasRightmostSelectorMatchingHTMLBasedOnRuleHash() const { return m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash; }
bool containsUncommonAttributeSelector() const { return m_containsUncommonAttributeSelector; }
@@ -89,14 +93,15 @@ public:
static const unsigned maximumIdentifierCount = 4;
const unsigned* descendantSelectorIdentifierHashes() const { return m_descendantSelectorIdentifierHashes; }
+ void trace(Visitor*);
+
private:
- StyleRule* m_rule;
+ RawPtrWillBeMember<StyleRule> m_rule;
unsigned m_selectorIndex : 12;
unsigned m_isLastInArray : 1; // We store an array of RuleData objects in a primitive array.
// 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 : 18;
- unsigned m_hasFastCheckableSelector : 1;
unsigned m_specificity : 24;
unsigned m_hasMultipartSelector : 1;
unsigned m_hasRightmostSelectorMatchingHTMLBasedOnRuleHash : 1;
@@ -117,10 +122,11 @@ struct SameSizeAsRuleData {
COMPILE_ASSERT(sizeof(RuleData) == sizeof(SameSizeAsRuleData), RuleData_should_stay_small);
-class RuleSet {
- WTF_MAKE_NONCOPYABLE(RuleSet); WTF_MAKE_FAST_ALLOCATED;
+class RuleSet : public NoBaseWillBeGarbageCollectedFinalized<RuleSet> {
+ WTF_MAKE_NONCOPYABLE(RuleSet);
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- static PassOwnPtr<RuleSet> create() { return adoptPtr(new RuleSet); }
+ static PassOwnPtrWillBeRawPtr<RuleSet> create() { return adoptPtrWillBeNoop(new RuleSet); }
void addRulesFromSheet(StyleSheetContents*, const MediaQueryEvaluator&, AddRuleFlags = RuleHasNoSpecialState);
void addStyleRule(StyleRule*, AddRuleFlags);
@@ -128,20 +134,20 @@ public:
const RuleFeatureSet& features() const { return m_features; }
- const RuleData* idRules(StringImpl* key) const { ASSERT(!m_pendingRules); return m_idRules.get(key); }
- const RuleData* classRules(StringImpl* key) const { ASSERT(!m_pendingRules); return m_classRules.get(key); }
- const RuleData* tagRules(StringImpl* key) const { ASSERT(!m_pendingRules); return m_tagRules.get(key); }
- const RuleData* shadowPseudoElementRules(StringImpl* key) const { ASSERT(!m_pendingRules); return m_shadowPseudoElementRules.get(key); }
- const Vector<RuleData>* linkPseudoClassRules() const { ASSERT(!m_pendingRules); return &m_linkPseudoClassRules; }
- const Vector<RuleData>* cuePseudoRules() const { ASSERT(!m_pendingRules); return &m_cuePseudoRules; }
- const Vector<RuleData>* focusPseudoClassRules() const { ASSERT(!m_pendingRules); return &m_focusPseudoClassRules; }
- const Vector<RuleData>* universalRules() const { ASSERT(!m_pendingRules); return &m_universalRules; }
- const Vector<StyleRulePage*>& pageRules() const { ASSERT(!m_pendingRules); return m_pageRules; }
- const Vector<StyleRuleViewport*>& viewportRules() const { ASSERT(!m_pendingRules); return m_viewportRules; }
- const Vector<StyleRuleFontFace*>& fontFaceRules() const { return m_fontFaceRules; }
- const Vector<StyleRuleKeyframes*>& keyframesRules() const { return m_keyframesRules; }
- const Vector<MinimalRuleData>& treeBoundaryCrossingRules() const { return m_treeBoundaryCrossingRules; }
- const Vector<MinimalRuleData>& shadowDistributedRules() const { return m_shadowDistributedRules; }
+ const WillBeHeapTerminatedArray<RuleData>* idRules(const AtomicString& key) const { ASSERT(!m_pendingRules); return m_idRules.get(key); }
+ const WillBeHeapTerminatedArray<RuleData>* classRules(const AtomicString& key) const { ASSERT(!m_pendingRules); return m_classRules.get(key); }
+ const WillBeHeapTerminatedArray<RuleData>* tagRules(const AtomicString& key) const { ASSERT(!m_pendingRules); return m_tagRules.get(key); }
+ const WillBeHeapTerminatedArray<RuleData>* shadowPseudoElementRules(const AtomicString& key) const { ASSERT(!m_pendingRules); return m_shadowPseudoElementRules.get(key); }
+ const WillBeHeapVector<RuleData>* linkPseudoClassRules() const { ASSERT(!m_pendingRules); return &m_linkPseudoClassRules; }
+ const WillBeHeapVector<RuleData>* cuePseudoRules() const { ASSERT(!m_pendingRules); return &m_cuePseudoRules; }
+ const WillBeHeapVector<RuleData>* focusPseudoClassRules() const { ASSERT(!m_pendingRules); return &m_focusPseudoClassRules; }
+ const WillBeHeapVector<RuleData>* universalRules() const { ASSERT(!m_pendingRules); return &m_universalRules; }
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >& pageRules() const { ASSERT(!m_pendingRules); return m_pageRules; }
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRuleViewport> >& viewportRules() const { ASSERT(!m_pendingRules); return m_viewportRules; }
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRuleFontFace> >& fontFaceRules() const { return m_fontFaceRules; }
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRuleKeyframes> >& keyframesRules() const { return m_keyframesRules; }
+ const WillBeHeapVector<MinimalRuleData>& treeBoundaryCrossingRules() const { return m_treeBoundaryCrossingRules; }
+ const WillBeHeapVector<MinimalRuleData>& shadowDistributedRules() const { return m_shadowDistributedRules; }
const MediaQueryResultList& viewportDependentMediaQueryResults() const { return m_viewportDependentMediaQueryResults; }
unsigned ruleCount() const { return m_ruleCount; }
@@ -153,49 +159,52 @@ public:
compactRules();
}
- struct RuleSetSelectorPair {
- RuleSetSelectorPair(const CSSSelector* selector, PassOwnPtr<RuleSet> ruleSet) : selector(selector), ruleSet(ruleSet) { }
- RuleSetSelectorPair(const RuleSetSelectorPair& rs) : selector(rs.selector), ruleSet(const_cast<RuleSetSelectorPair*>(&rs)->ruleSet.release()) { }
-
- const CSSSelector* selector;
- OwnPtr<RuleSet> ruleSet;
- };
+#ifndef NDEBUG
+ void show();
+#endif
- Vector<RuleSetSelectorPair> m_regionSelectorsAndRuleSets;
+ void trace(Visitor*);
private:
- typedef HashMap<StringImpl*, OwnPtr<LinkedStack<RuleData> > > PendingRuleMap;
- typedef HashMap<StringImpl*, OwnPtr<RuleData> > CompactRuleMap;
+ typedef WillBeHeapHashMap<AtomicString, OwnPtrWillBeMember<WillBeHeapLinkedStack<RuleData> > > PendingRuleMap;
+ typedef WillBeHeapHashMap<AtomicString, OwnPtrWillBeMember<WillBeHeapTerminatedArray<RuleData> > > CompactRuleMap;
RuleSet()
: m_ruleCount(0)
{
}
- void addToRuleSet(StringImpl* key, PendingRuleMap&, const RuleData&);
+ void addToRuleSet(const AtomicString& key, PendingRuleMap&, const RuleData&);
void addPageRule(StyleRulePage*);
void addViewportRule(StyleRuleViewport*);
void addFontFaceRule(StyleRuleFontFace*);
void addKeyframesRule(StyleRuleKeyframes*);
- void addRegionRule(StyleRuleRegion*, bool hasDocumentSecurityOrigin);
- void addChildRules(const Vector<RefPtr<StyleRuleBase> >&, const MediaQueryEvaluator& medium, AddRuleFlags);
- bool findBestRuleSetAndAdd(const CSSSelector*, RuleData&);
+ void addChildRules(const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >&, const MediaQueryEvaluator& medium, AddRuleFlags);
+ bool findBestRuleSetAndAdd(const CSSSelector&, RuleData&);
void compactRules();
static void compactPendingRules(PendingRuleMap&, CompactRuleMap&);
- struct PendingRuleMaps {
+ class PendingRuleMaps : public NoBaseWillBeGarbageCollected<PendingRuleMaps> {
+ public:
+ static PassOwnPtrWillBeRawPtr<PendingRuleMaps> create() { return adoptPtrWillBeNoop(new PendingRuleMaps); }
+
PendingRuleMap idRules;
PendingRuleMap classRules;
PendingRuleMap tagRules;
PendingRuleMap shadowPseudoElementRules;
+
+ void trace(Visitor*);
+
+ private:
+ PendingRuleMaps() { }
};
PendingRuleMaps* ensurePendingRules()
{
if (!m_pendingRules)
- m_pendingRules = adoptPtr(new PendingRuleMaps);
+ m_pendingRules = PendingRuleMaps::create();
return m_pendingRules.get();
}
@@ -203,24 +212,31 @@ private:
CompactRuleMap m_classRules;
CompactRuleMap m_tagRules;
CompactRuleMap m_shadowPseudoElementRules;
- Vector<RuleData> m_linkPseudoClassRules;
- Vector<RuleData> m_cuePseudoRules;
- Vector<RuleData> m_focusPseudoClassRules;
- Vector<RuleData> m_universalRules;
+ WillBeHeapVector<RuleData> m_linkPseudoClassRules;
+ WillBeHeapVector<RuleData> m_cuePseudoRules;
+ WillBeHeapVector<RuleData> m_focusPseudoClassRules;
+ WillBeHeapVector<RuleData> m_universalRules;
RuleFeatureSet m_features;
- Vector<StyleRulePage*> m_pageRules;
- Vector<StyleRuleViewport*> m_viewportRules;
- Vector<StyleRuleFontFace*> m_fontFaceRules;
- Vector<StyleRuleKeyframes*> m_keyframesRules;
- Vector<MinimalRuleData> m_treeBoundaryCrossingRules;
- Vector<MinimalRuleData> m_shadowDistributedRules;
+ WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> > m_pageRules;
+ WillBeHeapVector<RawPtrWillBeMember<StyleRuleViewport> > m_viewportRules;
+ WillBeHeapVector<RawPtrWillBeMember<StyleRuleFontFace> > m_fontFaceRules;
+ WillBeHeapVector<RawPtrWillBeMember<StyleRuleKeyframes> > m_keyframesRules;
+ WillBeHeapVector<MinimalRuleData> m_treeBoundaryCrossingRules;
+ WillBeHeapVector<MinimalRuleData> m_shadowDistributedRules;
MediaQueryResultList m_viewportDependentMediaQueryResults;
unsigned m_ruleCount;
- OwnPtr<PendingRuleMaps> m_pendingRules;
+ OwnPtrWillBeMember<PendingRuleMaps> m_pendingRules;
+
+#ifndef NDEBUG
+ WillBeHeapVector<RuleData> m_allRules;
+#endif
};
} // namespace WebCore
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::RuleData);
+WTF_ALLOW_MOVE_AND_INIT_WITH_MEM_FUNCTIONS(WebCore::MinimalRuleData);
+
#endif // RuleSet_h
diff --git a/chromium/third_party/WebKit/Source/core/css/RuleSetTest.cpp b/chromium/third_party/WebKit/Source/core/css/RuleSetTest.cpp
new file mode 100644
index 00000000000..8fd5ec63bba
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/RuleSetTest.cpp
@@ -0,0 +1,139 @@
+/*
+ * Copyright (c) 2014, Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Opera Software ASA nor the names of its
+ * contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
+ * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "core/css/CSSTestHelper.h"
+#include "core/css/RuleSet.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_CustomPseudoElements)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("summary::-webkit-details-marker { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("-webkit-details-marker");
+ const TerminatedArray<RuleData>* rules = ruleSet.shadowPseudoElementRules(str);
+ ASSERT_EQ(1u, rules->size());
+ ASSERT_EQ(str, rules->at(0).selector().value());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_Id)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("#id { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("id");
+ const TerminatedArray<RuleData>* rules = ruleSet.idRules(str);
+ ASSERT_EQ(1u, rules->size());
+ ASSERT_EQ(str, rules->at(0).selector().value());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_NthChild)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("div:nth-child(2) { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("div");
+ const TerminatedArray<RuleData>* rules = ruleSet.tagRules(str);
+ ASSERT_EQ(1u, rules->size());
+ ASSERT_EQ(str, rules->at(0).selector().tagQName().localName());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_ClassThenId)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules(".class#id { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("id");
+ // id is prefered over class even if class preceeds it in the selector.
+ const TerminatedArray<RuleData>* rules = ruleSet.idRules(str);
+ ASSERT_EQ(1u, rules->size());
+ AtomicString classStr("class");
+ ASSERT_EQ(classStr, rules->at(0).selector().value());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_IdThenClass)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("#id.class { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("id");
+ const TerminatedArray<RuleData>* rules = ruleSet.idRules(str);
+ ASSERT_EQ(1u, rules->size());
+ ASSERT_EQ(str, rules->at(0).selector().value());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_AttrThenId)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("[attr]#id { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("id");
+ const TerminatedArray<RuleData>* rules = ruleSet.idRules(str);
+ ASSERT_EQ(1u, rules->size());
+ AtomicString attrStr("attr");
+ ASSERT_EQ(attrStr, rules->at(0).selector().attribute().localName());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_TagThenAttrThenId)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("div[attr]#id { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("id");
+ const TerminatedArray<RuleData>* rules = ruleSet.idRules(str);
+ ASSERT_EQ(1u, rules->size());
+ AtomicString tagStr("div");
+ ASSERT_EQ(tagStr, rules->at(0).selector().tagQName().localName());
+}
+
+TEST(RuleSetTest, findBestRuleSetAndAdd_DivWithContent)
+{
+ CSSTestHelper helper;
+
+ helper.addCSSRules("div::content { }");
+ RuleSet& ruleSet = helper.ruleSet();
+ AtomicString str("div");
+ const TerminatedArray<RuleData>* rules = ruleSet.tagRules(str);
+ ASSERT_EQ(1u, rules->size());
+ AtomicString valueStr("content");
+ ASSERT_EQ(valueStr, rules->at(0).selector().value());
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.cpp b/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.cpp
index 7e0d728e2b8..dd9796bfc9d 100644
--- a/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.cpp
@@ -30,12 +30,12 @@
#include "config.h"
#include "core/css/RuntimeCSSEnabled.h"
-#include "RuntimeEnabledFeatures.h"
+#include "platform/RuntimeEnabledFeatures.h"
+#include "wtf/BitArray.h"
namespace WebCore {
-// FIXME: We should use a real BitVector class instead!
-typedef Vector<bool> BoolVector;
+typedef BitArray<numCSSProperties> CSSPropertySwitches;
static void setCSSPropertiesEnabled(CSSPropertyID* properties, size_t length, bool featureFlag)
{
@@ -45,15 +45,6 @@ static void setCSSPropertiesEnabled(CSSPropertyID* properties, size_t length, bo
static void setPropertySwitchesFromRuntimeFeatures()
{
- CSSPropertyID regionProperites[] = {
- CSSPropertyWebkitFlowInto,
- CSSPropertyWebkitFlowFrom,
- CSSPropertyWebkitRegionFragment,
- CSSPropertyWebkitRegionBreakAfter,
- CSSPropertyWebkitRegionBreakBefore,
- CSSPropertyWebkitRegionBreakInside
- };
- setCSSPropertiesEnabled(regionProperites, WTF_ARRAY_LENGTH(regionProperites), RuntimeEnabledFeatures::cssRegionsEnabled());
CSSPropertyID exclusionProperties[] = {
CSSPropertyWebkitWrapFlow,
CSSPropertyWebkitWrapThrough,
@@ -61,9 +52,7 @@ static void setPropertySwitchesFromRuntimeFeatures()
setCSSPropertiesEnabled(exclusionProperties, WTF_ARRAY_LENGTH(exclusionProperties), RuntimeEnabledFeatures::cssExclusionsEnabled());
CSSPropertyID shapeProperties[] = {
CSSPropertyShapeMargin,
- CSSPropertyShapePadding,
CSSPropertyShapeImageThreshold,
- CSSPropertyShapeInside,
CSSPropertyShapeOutside,
};
setCSSPropertiesEnabled(shapeProperties, WTF_ARRAY_LENGTH(shapeProperties), RuntimeEnabledFeatures::cssShapesEnabled());
@@ -82,8 +71,8 @@ static void setPropertySwitchesFromRuntimeFeatures()
CSSPropertyID cssGridLayoutProperties[] = {
CSSPropertyGridAutoColumns,
CSSPropertyGridAutoRows,
- CSSPropertyGridDefinitionColumns,
- CSSPropertyGridDefinitionRows,
+ CSSPropertyGridTemplateColumns,
+ CSSPropertyGridTemplateRows,
CSSPropertyGridColumnStart,
CSSPropertyGridColumnEnd,
CSSPropertyGridRowStart,
@@ -92,7 +81,10 @@ static void setPropertySwitchesFromRuntimeFeatures()
CSSPropertyGridRow,
CSSPropertyGridArea,
CSSPropertyGridAutoFlow,
- CSSPropertyGridTemplate
+ CSSPropertyGridTemplateAreas,
+ CSSPropertyGridTemplate,
+ CSSPropertyGrid,
+ CSSPropertyJustifySelf
};
setCSSPropertiesEnabled(cssGridLayoutProperties, WTF_ARRAY_LENGTH(cssGridLayoutProperties), RuntimeEnabledFeatures::cssGridLayoutEnabled());
CSSPropertyID cssObjectFitPositionProperties[] = {
@@ -114,26 +106,34 @@ static void setPropertySwitchesFromRuntimeFeatures()
};
setCSSPropertiesEnabled(animationProperties, WTF_ARRAY_LENGTH(animationProperties), RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled());
- RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyBackgroundBlendMode, RuntimeEnabledFeatures::cssCompositingEnabled());
+ CSSPropertyID transformProperties[] = {
+ CSSPropertyBackfaceVisibility,
+ CSSPropertyPerspective,
+ CSSPropertyPerspectiveOrigin,
+ CSSPropertyTransform,
+ CSSPropertyTransformOrigin,
+ CSSPropertyTransformStyle
+ };
+ setCSSPropertiesEnabled(transformProperties, WTF_ARRAY_LENGTH(transformProperties), RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
+
RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyMixBlendMode, RuntimeEnabledFeatures::cssCompositingEnabled());
RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyIsolation, RuntimeEnabledFeatures::cssCompositingEnabled());
RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyTouchAction, RuntimeEnabledFeatures::cssTouchActionEnabled());
- RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyPaintOrder, RuntimeEnabledFeatures::svgPaintOrderEnabled());
- RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyVariable, RuntimeEnabledFeatures::cssVariablesEnabled());
+ RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyTouchActionDelay, RuntimeEnabledFeatures::cssTouchActionDelayEnabled());
RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyMaskSourceType, RuntimeEnabledFeatures::cssMaskSourceTypeEnabled());
RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyColumnFill, RuntimeEnabledFeatures::regionBasedColumnsEnabled());
+ RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyScrollBehavior, RuntimeEnabledFeatures::cssomSmoothScrollEnabled());
+ RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyWillChange, RuntimeEnabledFeatures::cssWillChangeEnabled());
// InternalCallback is an implementation detail, rather than an experimental feature, and should never be exposed to the web.
RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyInternalCallback, false);
}
-static BoolVector& propertySwitches()
+static CSSPropertySwitches& propertySwitches()
{
- static BoolVector* switches = 0;
+ static CSSPropertySwitches* switches = 0;
if (!switches) {
- switches = new BoolVector;
- // Accomodate CSSPropertyIDs that fall outside the firstCSSProperty, lastCSSProperty range (eg. CSSPropertyVariable).
- switches->fill(true, lastCSSProperty + 1);
+ switches = new CSSPropertySwitches(true); // All bits sets to 1.
setPropertySwitchesFromRuntimeFeatures();
}
return *switches;
@@ -141,9 +141,9 @@ static BoolVector& propertySwitches()
size_t indexForProperty(CSSPropertyID propertyId)
{
- RELEASE_ASSERT(propertyId >= 0 && propertyId <= lastCSSProperty);
- ASSERT(propertyId != CSSPropertyInvalid);
- return static_cast<size_t>(propertyId);
+ RELEASE_ASSERT(propertyId >= firstCSSProperty && propertyId <= lastCSSProperty);
+ // Values all start at 0. BitArray ASSERTS will catch if we're ever wrong.
+ return static_cast<size_t>(propertyId - firstCSSProperty);
}
bool RuntimeCSSEnabled::isCSSPropertyEnabled(CSSPropertyID propertyId)
@@ -153,12 +153,16 @@ bool RuntimeCSSEnabled::isCSSPropertyEnabled(CSSPropertyID propertyId)
if (isInternalProperty(propertyId))
return false;
- return propertySwitches()[indexForProperty(propertyId)];
+ return propertySwitches().get(indexForProperty(propertyId));
}
void RuntimeCSSEnabled::setCSSPropertyEnabled(CSSPropertyID propertyId, bool enable)
{
- propertySwitches()[indexForProperty(propertyId)] = enable;
+ size_t propertyIndex = indexForProperty(propertyId);
+ if (enable)
+ propertySwitches().set(propertyIndex);
+ else
+ propertySwitches().clear(propertyIndex);
}
void RuntimeCSSEnabled::filterEnabledCSSPropertiesIntoVector(const CSSPropertyID* properties, size_t propertyCount, Vector<CSSPropertyID>& outVector)
diff --git a/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.h b/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.h
index 493d3a52356..bb7900f1c21 100644
--- a/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.h
+++ b/chromium/third_party/WebKit/Source/core/css/RuntimeCSSEnabled.h
@@ -30,7 +30,7 @@
#ifndef RuntimeCSSEnabled_h
#define RuntimeCSSEnabled_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
#include "wtf/Vector.h"
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/core/css/SVGCSSComputedStyleDeclaration.cpp b/chromium/third_party/WebKit/Source/core/css/SVGCSSComputedStyleDeclaration.cpp
index c972f873786..584b67705a6 100644
--- a/chromium/third_party/WebKit/Source/core/css/SVGCSSComputedStyleDeclaration.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/SVGCSSComputedStyleDeclaration.cpp
@@ -22,7 +22,7 @@
#include "core/css/CSSComputedStyleDeclaration.h"
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
#include "core/css/CSSPrimitiveValueMappings.h"
#include "core/dom/Document.h"
#include "core/rendering/style/RenderStyle.h"
@@ -30,7 +30,7 @@
namespace WebCore {
-static PassRefPtr<CSSPrimitiveValue> glyphOrientationToCSSPrimitiveValue(EGlyphOrientation orientation)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> glyphOrientationToCSSPrimitiveValue(EGlyphOrientation orientation)
{
switch (orientation) {
case GO_0DEG:
@@ -42,26 +42,29 @@ static PassRefPtr<CSSPrimitiveValue> glyphOrientationToCSSPrimitiveValue(EGlyphO
case GO_270DEG:
return CSSPrimitiveValue::create(270.0f, CSSPrimitiveValue::CSS_DEG);
default:
- return 0;
+ return nullptr;
}
}
-static PassRefPtr<CSSValue> strokeDashArrayToCSSValueList(const Vector<SVGLength>& dashes)
+static PassRefPtrWillBeRawPtr<CSSValue> strokeDashArrayToCSSValueList(PassRefPtr<SVGLengthList> passDashes)
{
- if (dashes.isEmpty())
+ RefPtr<SVGLengthList> dashes = passDashes;
+
+ if (dashes->isEmpty())
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- const Vector<SVGLength>::const_iterator end = dashes.end();
- for (Vector<SVGLength>::const_iterator it = dashes.begin(); it != end; ++it)
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ SVGLengthList::ConstIterator it = dashes->begin();
+ SVGLengthList::ConstIterator itEnd = dashes->end();
+ for (; it != itEnd; ++it)
list->append(SVGLength::toCSSPrimitiveValue(*it));
return list.release();
}
-static PassRefPtr<CSSValue> paintOrderToCSSValueList(EPaintOrder paintorder)
+static PassRefPtrWillBeRawPtr<CSSValue> paintOrderToCSSValueList(EPaintOrder paintorder)
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
do {
EPaintOrderType paintOrderType = (EPaintOrderType)(paintorder & ((1 << kPaintOrderBitwidth) - 1));
switch (paintOrderType) {
@@ -80,19 +83,24 @@ static PassRefPtr<CSSValue> paintOrderToCSSValueList(EPaintOrder paintorder)
return list.release();
}
-PassRefPtr<SVGPaint> CSSComputedStyleDeclaration::adjustSVGPaintForCurrentColor(PassRefPtr<SVGPaint> newPaint, RenderStyle& style) const
+PassRefPtrWillBeRawPtr<SVGPaint> CSSComputedStyleDeclaration::adjustSVGPaintForCurrentColor(PassRefPtrWillBeRawPtr<SVGPaint> newPaint, RenderStyle& style) const
{
- RefPtr<SVGPaint> paint = newPaint;
+ RefPtrWillBeRawPtr<SVGPaint> paint = newPaint;
if (paint->paintType() == SVGPaint::SVG_PAINTTYPE_CURRENTCOLOR || paint->paintType() == SVGPaint::SVG_PAINTTYPE_URI_CURRENTCOLOR)
paint->setColor(style.color());
return paint.release();
}
-PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSPropertyID propertyID, EUpdateLayout updateLayout) const
+static inline String serializeAsFragmentIdentifier(const AtomicString& resource)
+{
+ return "#" + resource;
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSPropertyID propertyID, EUpdateLayout updateLayout) const
{
Node* node = m_node.get();
if (!node)
- return 0;
+ return nullptr;
// Make sure our layout is up to date before we allow a query on these attributes.
if (updateLayout)
@@ -100,11 +108,11 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSProp
RenderStyle* style = node->computedStyle();
if (!style)
- return 0;
+ return nullptr;
const SVGRenderStyle* svgStyle = style->svgStyle();
if (!svgStyle)
- return 0;
+ return nullptr;
switch (propertyID) {
case CSSPropertyClipRule:
@@ -143,15 +151,15 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSProp
return CSSPrimitiveValue::create(svgStyle->writingMode());
case CSSPropertyClipPath:
if (!svgStyle->clipperResource().isEmpty())
- return CSSPrimitiveValue::create(svgStyle->clipperResource(), CSSPrimitiveValue::CSS_URI);
+ return CSSPrimitiveValue::create(serializeAsFragmentIdentifier(svgStyle->clipperResource()), CSSPrimitiveValue::CSS_URI);
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
case CSSPropertyMask:
if (!svgStyle->maskerResource().isEmpty())
- return CSSPrimitiveValue::create(svgStyle->maskerResource(), CSSPrimitiveValue::CSS_URI);
+ return CSSPrimitiveValue::create(serializeAsFragmentIdentifier(svgStyle->maskerResource()), CSSPrimitiveValue::CSS_URI);
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
case CSSPropertyFilter:
if (!svgStyle->filterResource().isEmpty())
- return CSSPrimitiveValue::create(svgStyle->filterResource(), CSSPrimitiveValue::CSS_URI);
+ return CSSPrimitiveValue::create(serializeAsFragmentIdentifier(svgStyle->filterResource()), CSSPrimitiveValue::CSS_URI);
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
case CSSPropertyFloodColor:
return currentColorOrValidColor(*style, svgStyle->floodColor());
@@ -161,19 +169,17 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSProp
return currentColorOrValidColor(*style, svgStyle->stopColor());
case CSSPropertyFill:
return adjustSVGPaintForCurrentColor(SVGPaint::create(svgStyle->fillPaintType(), svgStyle->fillPaintUri(), svgStyle->fillPaintColor()), *style);
- case CSSPropertyKerning:
- return SVGLength::toCSSPrimitiveValue(svgStyle->kerning());
case CSSPropertyMarkerEnd:
if (!svgStyle->markerEndResource().isEmpty())
- return CSSPrimitiveValue::create(svgStyle->markerEndResource(), CSSPrimitiveValue::CSS_URI);
+ return CSSPrimitiveValue::create(serializeAsFragmentIdentifier(svgStyle->markerEndResource()), CSSPrimitiveValue::CSS_URI);
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
case CSSPropertyMarkerMid:
if (!svgStyle->markerMidResource().isEmpty())
- return CSSPrimitiveValue::create(svgStyle->markerMidResource(), CSSPrimitiveValue::CSS_URI);
+ return CSSPrimitiveValue::create(serializeAsFragmentIdentifier(svgStyle->markerMidResource()), CSSPrimitiveValue::CSS_URI);
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
case CSSPropertyMarkerStart:
if (!svgStyle->markerStartResource().isEmpty())
- return CSSPrimitiveValue::create(svgStyle->markerStartResource(), CSSPrimitiveValue::CSS_URI);
+ return CSSPrimitiveValue::create(serializeAsFragmentIdentifier(svgStyle->markerStartResource()), CSSPrimitiveValue::CSS_URI);
return CSSPrimitiveValue::createIdentifier(CSSValueNone);
case CSSPropertyStroke:
return adjustSVGPaintForCurrentColor(SVGPaint::create(svgStyle->strokePaintType(), svgStyle->strokePaintUri(), svgStyle->strokePaintColor()), *style);
@@ -195,20 +201,20 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSProp
return SVGLength::toCSSPrimitiveValue(svgStyle->baselineShiftValue());
}
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
case CSSPropertyBufferedRendering:
return CSSPrimitiveValue::create(svgStyle->bufferedRendering());
case CSSPropertyGlyphOrientationHorizontal:
return glyphOrientationToCSSPrimitiveValue(svgStyle->glyphOrientationHorizontal());
case CSSPropertyGlyphOrientationVertical: {
- if (RefPtr<CSSPrimitiveValue> value = glyphOrientationToCSSPrimitiveValue(svgStyle->glyphOrientationVertical()))
+ if (RefPtrWillBeRawPtr<CSSPrimitiveValue> value = glyphOrientationToCSSPrimitiveValue(svgStyle->glyphOrientationVertical()))
return value.release();
if (svgStyle->glyphOrientationVertical() == GO_AUTO)
return CSSPrimitiveValue::createIdentifier(CSSValueAuto);
- return 0;
+ return nullptr;
}
case CSSPropertyPaintOrder:
return paintOrderToCSSValueList(svgStyle->paintOrder());
@@ -218,7 +224,6 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSProp
return CSSPrimitiveValue::create(svgStyle->maskType());
case CSSPropertyMarker:
case CSSPropertyEnableBackground:
- case CSSPropertyColorProfile:
// the above properties are not yet implemented in the engine
break;
default:
@@ -227,7 +232,7 @@ PassRefPtr<CSSValue> CSSComputedStyleDeclaration::getSVGPropertyCSSValue(CSSProp
ASSERT_WITH_MESSAGE(0, "unimplemented propertyID: %d", propertyID);
}
WTF_LOG_ERROR("unimplemented propertyID: %d", propertyID);
- return 0;
+ return nullptr;
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/SVGCSSParser.cpp b/chromium/third_party/WebKit/Source/core/css/SVGCSSParser.cpp
deleted file mode 100644
index 8c07b148933..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/SVGCSSParser.cpp
+++ /dev/null
@@ -1,427 +0,0 @@
-/*
- Copyright (C) 2008 Eric Seidel <eric@webkit.org>
- Copyright (C) 2004, 2005, 2007 Nikolas Zimmermann <zimmermann@kde.org>
- 2004, 2005, 2007, 2010 Rob Buis <buis@kde.org>
- Copyright (C) 2005, 2006 Apple Computer, Inc.
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Library General Public
- License as published by the Free Software Foundation; either
- version 2 of the License, or (at your option) any later version.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Library General Public License for more details.
-
- You should have received a copy of the GNU Library General Public License
- along with this library; see the file COPYING.LIB. If not, write to
- the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- Boston, MA 02110-1301, USA.
-*/
-
-#include "config.h"
-
-#include "CSSPropertyNames.h"
-#include "CSSValueKeywords.h"
-#include "RuntimeEnabledFeatures.h"
-#include "core/css/CSSParser.h"
-#include "core/css/CSSValueList.h"
-#include "core/rendering/RenderTheme.h"
-#include "core/svg/SVGPaint.h"
-
-using namespace std;
-
-namespace WebCore {
-
-static bool isSystemColor(int id)
-{
- return (id >= CSSValueActiveborder && id <= CSSValueWindowtext) || id == CSSValueMenu;
-}
-
-bool CSSParser::parseSVGValue(CSSPropertyID propId, bool important)
-{
- CSSParserValue* value = m_valueList->current();
- if (!value)
- return false;
-
- CSSValueID id = value->id;
-
- bool valid_primitive = false;
- RefPtr<CSSValue> parsedValue;
-
- switch (propId) {
- /* The comment to the right defines all valid value of these
- * properties as defined in SVG 1.1, Appendix N. Property index */
- case CSSPropertyAlignmentBaseline:
- // auto | baseline | before-edge | text-before-edge | middle |
- // central | after-edge | text-after-edge | ideographic | alphabetic |
- // hanging | mathematical | inherit
- if (id == CSSValueAuto || id == CSSValueBaseline || id == CSSValueMiddle ||
- (id >= CSSValueBeforeEdge && id <= CSSValueMathematical))
- valid_primitive = true;
- break;
-
- case CSSPropertyBaselineShift:
- // baseline | super | sub | <percentage> | <length> | inherit
- if (id == CSSValueBaseline || id == CSSValueSub ||
- id >= CSSValueSuper)
- valid_primitive = true;
- else
- valid_primitive = validUnit(value, FLength | FPercent, SVGAttributeMode);
- break;
-
- case CSSPropertyDominantBaseline:
- // auto | use-script | no-change | reset-size | ideographic |
- // alphabetic | hanging | mathematical | central | middle |
- // text-after-edge | text-before-edge | inherit
- if (id == CSSValueAuto || id == CSSValueMiddle ||
- (id >= CSSValueUseScript && id <= CSSValueResetSize) ||
- (id >= CSSValueCentral && id <= CSSValueMathematical))
- valid_primitive = true;
- break;
-
- case CSSPropertyEnableBackground:
- // accumulate | new [x] [y] [width] [height] | inherit
- if (id == CSSValueAccumulate) // TODO : new
- valid_primitive = true;
- break;
-
- case CSSPropertyMarkerStart:
- case CSSPropertyMarkerMid:
- case CSSPropertyMarkerEnd:
- case CSSPropertyMask:
- if (id == CSSValueNone)
- valid_primitive = true;
- else if (value->unit == CSSPrimitiveValue::CSS_URI) {
- parsedValue = CSSPrimitiveValue::create(value->string, CSSPrimitiveValue::CSS_URI);
- if (parsedValue)
- m_valueList->next();
- }
- break;
-
- case CSSPropertyClipRule: // nonzero | evenodd | inherit
- case CSSPropertyFillRule:
- if (id == CSSValueNonzero || id == CSSValueEvenodd)
- valid_primitive = true;
- break;
-
- case CSSPropertyStrokeMiterlimit: // <miterlimit> | inherit
- valid_primitive = validUnit(value, FNumber | FNonNeg, SVGAttributeMode);
- break;
-
- case CSSPropertyStrokeLinejoin: // miter | round | bevel | inherit
- if (id == CSSValueMiter || id == CSSValueRound || id == CSSValueBevel)
- valid_primitive = true;
- break;
-
- case CSSPropertyStrokeLinecap: // butt | round | square | inherit
- if (id == CSSValueButt || id == CSSValueRound || id == CSSValueSquare)
- valid_primitive = true;
- break;
-
- case CSSPropertyStrokeOpacity: // <opacity-value> | inherit
- case CSSPropertyFillOpacity:
- case CSSPropertyStopOpacity:
- case CSSPropertyFloodOpacity:
- valid_primitive = (!id && validUnit(value, FNumber | FPercent, SVGAttributeMode));
- break;
-
- case CSSPropertyShapeRendering:
- // auto | optimizeSpeed | crispEdges | geometricPrecision | inherit
- if (id == CSSValueAuto || id == CSSValueOptimizespeed ||
- id == CSSValueCrispedges || id == CSSValueGeometricprecision)
- valid_primitive = true;
- break;
-
- case CSSPropertyImageRendering: // auto | optimizeSpeed |
- case CSSPropertyColorRendering: // optimizeQuality | inherit
- if (id == CSSValueAuto || id == CSSValueOptimizespeed ||
- id == CSSValueOptimizequality)
- valid_primitive = true;
- break;
-
- case CSSPropertyBufferedRendering: // auto | dynamic | static
- if (id == CSSValueAuto || id == CSSValueDynamic || id == CSSValueStatic)
- valid_primitive = true;
- break;
-
- case CSSPropertyColorProfile: // auto | sRGB | <name> | <uri> inherit
- if (id == CSSValueAuto || id == CSSValueSrgb)
- valid_primitive = true;
- break;
-
- case CSSPropertyColorInterpolation: // auto | sRGB | linearRGB | inherit
- case CSSPropertyColorInterpolationFilters:
- if (id == CSSValueAuto || id == CSSValueSrgb || id == CSSValueLinearrgb)
- valid_primitive = true;
- break;
-
- /* Start of supported CSS properties with validation. This is needed for parseShortHand to work
- * correctly and allows optimization in applyRule(..)
- */
-
- case CSSPropertyTextAnchor: // start | middle | end | inherit
- if (id == CSSValueStart || id == CSSValueMiddle || id == CSSValueEnd)
- valid_primitive = true;
- break;
-
- case CSSPropertyGlyphOrientationVertical: // auto | <angle> | inherit
- if (id == CSSValueAuto) {
- valid_primitive = true;
- break;
- }
- /* fallthrough intentional */
- case CSSPropertyGlyphOrientationHorizontal: // <angle> (restricted to _deg_ per SVG 1.1 spec) | inherit
- if (value->unit == CSSPrimitiveValue::CSS_DEG || value->unit == CSSPrimitiveValue::CSS_NUMBER) {
- parsedValue = CSSPrimitiveValue::create(value->fValue, CSSPrimitiveValue::CSS_DEG);
-
- if (parsedValue)
- m_valueList->next();
- }
- break;
-
- case CSSPropertyFill: // <paint> | inherit
- case CSSPropertyStroke: // <paint> | inherit
- {
- if (id == CSSValueNone)
- parsedValue = SVGPaint::createNone();
- else if (id == CSSValueCurrentcolor)
- parsedValue = SVGPaint::createCurrentColor();
- else if (isSystemColor(id))
- parsedValue = SVGPaint::createColor(RenderTheme::theme().systemColor(id));
- else if (value->unit == CSSPrimitiveValue::CSS_URI) {
- RGBA32 c = Color::transparent;
- if (m_valueList->next()) {
- if (parseColorFromValue(m_valueList->current(), c))
- parsedValue = SVGPaint::createURIAndColor(value->string, c);
- else if (m_valueList->current()->id == CSSValueNone)
- parsedValue = SVGPaint::createURIAndNone(value->string);
- }
- if (!parsedValue)
- parsedValue = SVGPaint::createURI(value->string);
- } else
- parsedValue = parseSVGPaint();
-
- if (parsedValue)
- m_valueList->next();
- }
- break;
-
- case CSSPropertyStopColor: // TODO : icccolor
- case CSSPropertyFloodColor:
- case CSSPropertyLightingColor:
- if (isSystemColor(id))
- parsedValue = SVGColor::createFromColor(RenderTheme::theme().systemColor(id));
- else if ((id >= CSSValueAqua && id <= CSSValueTransparent) ||
- (id >= CSSValueAliceblue && id <= CSSValueYellowgreen) || id == CSSValueGrey)
- parsedValue = SVGColor::createFromString(value->string);
- else if (id == CSSValueCurrentcolor)
- parsedValue = SVGColor::createCurrentColor();
- else // TODO : svgcolor (iccColor)
- parsedValue = parseSVGColor();
-
- if (parsedValue)
- m_valueList->next();
-
- break;
-
- case CSSPropertyPaintOrder:
- if (!RuntimeEnabledFeatures::svgPaintOrderEnabled())
- return false;
-
- if (m_valueList->size() == 1 && id == CSSValueNormal)
- valid_primitive = true;
- else if ((parsedValue = parsePaintOrder()))
- m_valueList->next();
- break;
-
- case CSSPropertyVectorEffect: // none | non-scaling-stroke | inherit
- if (id == CSSValueNone || id == CSSValueNonScalingStroke)
- valid_primitive = true;
- break;
-
- case CSSPropertyWritingMode:
- // lr-tb | rl_tb | tb-rl | lr | rl | tb | inherit
- if (id == CSSValueLrTb || id == CSSValueRlTb || id == CSSValueTbRl || id == CSSValueLr || id == CSSValueRl || id == CSSValueTb)
- valid_primitive = true;
- break;
-
- case CSSPropertyStrokeWidth: // <length> | inherit
- case CSSPropertyStrokeDashoffset:
- valid_primitive = validUnit(value, FLength | FPercent, SVGAttributeMode);
- break;
- case CSSPropertyStrokeDasharray: // none | <dasharray> | inherit
- if (id == CSSValueNone)
- valid_primitive = true;
- else
- parsedValue = parseSVGStrokeDasharray();
-
- break;
-
- case CSSPropertyKerning: // auto | normal | <length> | inherit
- if (id == CSSValueAuto || id == CSSValueNormal)
- valid_primitive = true;
- else
- valid_primitive = validUnit(value, FLength, SVGAttributeMode);
- break;
-
- case CSSPropertyClipPath: // <uri> | none | inherit
- case CSSPropertyFilter:
- if (id == CSSValueNone)
- valid_primitive = true;
- else if (value->unit == CSSPrimitiveValue::CSS_URI) {
- parsedValue = CSSPrimitiveValue::create(value->string, (CSSPrimitiveValue::UnitTypes) value->unit);
- if (parsedValue)
- m_valueList->next();
- }
- break;
- case CSSPropertyMaskType: // luminance | alpha | inherit
- if (id == CSSValueLuminance || id == CSSValueAlpha)
- valid_primitive = true;
- break;
-
- /* shorthand properties */
- case CSSPropertyMarker:
- {
- ShorthandScope scope(this, propId);
- CSSParser::ImplicitScope implicitScope(this, PropertyImplicit);
- if (!parseValue(CSSPropertyMarkerStart, important))
- return false;
- if (m_valueList->current()) {
- rollbackLastProperties(1);
- return false;
- }
- CSSValue* value = m_parsedProperties.last().value();
- addProperty(CSSPropertyMarkerMid, value, important);
- addProperty(CSSPropertyMarkerEnd, value, important);
- return true;
- }
- default:
- // If you crash here, it's because you added a css property and are not handling it
- // in either this switch statement or the one in CSSParser::parseValue
- ASSERT_WITH_MESSAGE(0, "unimplemented propertyID: %d", propId);
- return false;
- }
-
- if (valid_primitive) {
- if (id != 0)
- parsedValue = CSSPrimitiveValue::createIdentifier(id);
- else if (value->unit == CSSPrimitiveValue::CSS_STRING)
- parsedValue = CSSPrimitiveValue::create(value->string, (CSSPrimitiveValue::UnitTypes) value->unit);
- else if (value->unit >= CSSPrimitiveValue::CSS_NUMBER && value->unit <= CSSPrimitiveValue::CSS_KHZ)
- parsedValue = CSSPrimitiveValue::create(value->fValue, (CSSPrimitiveValue::UnitTypes) value->unit);
- else if (value->unit >= CSSParserValue::Q_EMS)
- parsedValue = CSSPrimitiveValue::createAllowingMarginQuirk(value->fValue, CSSPrimitiveValue::CSS_EMS);
- if (isCalculation(value)) {
- // FIXME calc() http://webkit.org/b/16662 : actually create a CSSPrimitiveValue here, ie
- // parsedValue = CSSPrimitiveValue::create(m_parsedCalculation.release());
- m_parsedCalculation.release();
- parsedValue = 0;
- }
- m_valueList->next();
- }
- if (!parsedValue || (m_valueList->current() && !inShorthand()))
- return false;
-
- addProperty(propId, parsedValue.release(), important);
- return true;
-}
-
-PassRefPtr<CSSValue> CSSParser::parseSVGStrokeDasharray()
-{
- RefPtr<CSSValueList> ret = CSSValueList::createCommaSeparated();
- CSSParserValue* value = m_valueList->current();
- bool valid_primitive = true;
- while (value) {
- valid_primitive = validUnit(value, FLength | FPercent | FNonNeg, SVGAttributeMode);
- if (!valid_primitive)
- break;
- if (value->id != 0)
- ret->append(CSSPrimitiveValue::createIdentifier(value->id));
- else if (value->unit >= CSSPrimitiveValue::CSS_NUMBER && value->unit <= CSSPrimitiveValue::CSS_KHZ)
- ret->append(CSSPrimitiveValue::create(value->fValue, (CSSPrimitiveValue::UnitTypes) value->unit));
- value = m_valueList->next();
- if (value && value->unit == CSSParserValue::Operator && value->iValue == ',')
- value = m_valueList->next();
- }
- if (!valid_primitive)
- return 0;
- return ret.release();
-}
-
-PassRefPtr<CSSValue> CSSParser::parseSVGPaint()
-{
- RGBA32 c = Color::transparent;
- if (!parseColorFromValue(m_valueList->current(), c))
- return SVGPaint::createUnknown();
- return SVGPaint::createColor(Color(c));
-}
-
-PassRefPtr<CSSValue> CSSParser::parseSVGColor()
-{
- RGBA32 c = Color::transparent;
- if (!parseColorFromValue(m_valueList->current(), c))
- return 0;
- return SVGColor::createFromColor(Color(c));
-}
-
-// normal | [ fill || stroke || markers ]
-PassRefPtr<CSSValue> CSSParser::parsePaintOrder() const
-{
- if (m_valueList->size() > 3)
- return 0;
-
- CSSParserValue* value = m_valueList->current();
- if (!value)
- return 0;
-
- RefPtr<CSSValueList> parsedValues = CSSValueList::createSpaceSeparated();
-
- // The default paint-order is: Fill, Stroke, Markers.
- bool seenFill = false,
- seenStroke = false,
- seenMarkers = false;
-
- do {
- switch (value->id) {
- case CSSValueNormal:
- // normal inside [fill || stroke || markers] not valid
- return 0;
- case CSSValueFill:
- if (seenFill)
- return 0;
-
- seenFill = true;
- break;
- case CSSValueStroke:
- if (seenStroke)
- return 0;
-
- seenStroke = true;
- break;
- case CSSValueMarkers:
- if (seenMarkers)
- return 0;
-
- seenMarkers = true;
- break;
- default:
- return 0;
- }
-
- parsedValues->append(CSSPrimitiveValue::createIdentifier(value->id));
- } while ((value = m_valueList->next()));
-
- // fill out the rest of the paint order
- if (!seenFill)
- parsedValues->append(CSSPrimitiveValue::createIdentifier(CSSValueFill));
- if (!seenStroke)
- parsedValues->append(CSSPrimitiveValue::createIdentifier(CSSValueStroke));
- if (!seenMarkers)
- parsedValues->append(CSSPrimitiveValue::createIdentifier(CSSValueMarkers));
-
- return parsedValues.release();
-}
-
-}
diff --git a/chromium/third_party/WebKit/Source/core/css/SVGCSSPropertyNames.in b/chromium/third_party/WebKit/Source/core/css/SVGCSSPropertyNames.in
index 1cf28711f0f..98fb81438de 100644
--- a/chromium/third_party/WebKit/Source/core/css/SVGCSSPropertyNames.in
+++ b/chromium/third_party/WebKit/Source/core/css/SVGCSSPropertyNames.in
@@ -18,7 +18,6 @@ stop-opacity
// pointer-events
color-interpolation
color-interpolation-filters
-color-profile
color-rendering
fill
fill-opacity
@@ -45,7 +44,6 @@ baseline-shift
dominant-baseline
glyph-orientation-horizontal
glyph-orientation-vertical
-kerning
text-anchor
vector-effect
writing-mode
diff --git a/chromium/third_party/WebKit/Source/core/css/SVGCSSValueKeywords.in b/chromium/third_party/WebKit/Source/core/css/SVGCSSValueKeywords.in
index ccfad3ca78f..b4260b76325 100644
--- a/chromium/third_party/WebKit/Source/core/css/SVGCSSValueKeywords.in
+++ b/chromium/third_party/WebKit/Source/core/css/SVGCSSValueKeywords.in
@@ -259,7 +259,6 @@ reset-size
// CSS_PROP_GLYPH_ORIENTATION_HORIZONTAL
// CSS_PROP_GLYPH_ORIENTATION_VERTICAL
-// CSS_PROP_KERNING
// CSS_PROP_TEXT_ANCHOR
// start
// middle
diff --git a/chromium/third_party/WebKit/Source/core/css/SelectorChecker.cpp b/chromium/third_party/WebKit/Source/core/css/SelectorChecker.cpp
index 15474cedd1d..3c6755a57fc 100644
--- a/chromium/third_party/WebKit/Source/core/css/SelectorChecker.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/SelectorChecker.cpp
@@ -28,27 +28,26 @@
#include "config.h"
#include "core/css/SelectorChecker.h"
-#include "HTMLNames.h"
+#include "core/HTMLNames.h"
#include "core/css/CSSSelectorList.h"
#include "core/css/SiblingTraversalStrategies.h"
#include "core/dom/Document.h"
+#include "core/dom/ElementTraversal.h"
#include "core/dom/FullscreenElementStack.h"
#include "core/dom/NodeRenderStyle.h"
#include "core/dom/Text.h"
#include "core/dom/shadow/InsertionPoint.h"
#include "core/dom/shadow/ShadowRoot.h"
#include "core/editing/FrameSelection.h"
-#include "core/html/HTMLAnchorElement.h"
+#include "core/frame/LocalFrame.h"
#include "core/html/HTMLDocument.h"
#include "core/html/HTMLFrameElementBase.h"
#include "core/html/HTMLInputElement.h"
-#include "core/html/HTMLOptGroupElement.h"
#include "core/html/HTMLOptionElement.h"
#include "core/html/parser/HTMLParserIdioms.h"
#include "core/html/track/vtt/VTTElement.h"
#include "core/inspector/InspectorInstrumentation.h"
#include "core/page/FocusController.h"
-#include "core/frame/Frame.h"
#include "core/rendering/RenderObject.h"
#include "core/rendering/RenderScrollbar.h"
#include "core/rendering/style/RenderStyle.h"
@@ -66,32 +65,39 @@ SelectorChecker::SelectorChecker(Document& document, Mode mode)
{
}
-static bool matchesCustomPseudoElement(const Element* element, const CSSSelector* selector)
+static bool matchesCustomPseudoElement(const Element* element, const CSSSelector& selector)
{
ShadowRoot* root = element->containingShadowRoot();
- if (!root)
+ if (!root || root->type() != ShadowRoot::UserAgentShadowRoot)
return false;
- const AtomicString& pseudoId = selector->pseudoType() == CSSSelector::PseudoWebKitCustomElement ? element->shadowPseudoId() : element->pseudo();
- if (pseudoId != selector->value())
- return false;
- if (selector->pseudoType() == CSSSelector::PseudoWebKitCustomElement && root->type() != ShadowRoot::UserAgentShadowRoot)
+ if (element->shadowPseudoId() != selector.value())
return false;
+
return true;
}
-Element* SelectorChecker::parentElement(const SelectorCheckingContext& context) const
+Element* SelectorChecker::parentElement(const SelectorCheckingContext& context, bool allowToCrossBoundary) const
{
// CrossesBoundary means we don't care any context.scope. So we can walk up from a shadow root to its shadow host.
- if ((context.behaviorAtBoundary & SelectorChecker::BoundaryBehaviorMask) == SelectorChecker::CrossesBoundary)
+ if (allowToCrossBoundary)
+ return context.element->parentOrShadowHostElement();
+
+ // If context.scope is a shadow root, we should walk up to its shadow host.
+ if ((context.behaviorAtBoundary & SelectorChecker::ScopeIsShadowRoot) && context.scope == context.element->containingShadowRoot())
return context.element->parentOrShadowHostElement();
- // If context.scope is not a shadow host, we cannot walk up from a shadow root to its shadow host.
- if (!(context.behaviorAtBoundary & SelectorChecker::ScopeIsShadowHost))
+ if ((context.behaviorAtBoundary & SelectorChecker::BoundaryBehaviorMask) != SelectorChecker::StaysWithinTreeScope)
return context.element->parentElement();
- // If behaviorAtBoundary is StaysWithInTreeScope, we cannot walk up from a shadow root to its shadow host.
- return (context.behaviorAtBoundary & SelectorChecker::BoundaryBehaviorMask) != SelectorChecker::StaysWithinTreeScope ? context.element->parentOrShadowHostElement() : context.element->parentElement();
+ // If context.scope is some element in some shadow tree and querySelector initialized the context,
+ // e.g. shadowRoot.querySelector(':host *'),
+ // (a) context.element has the same treescope as context.scope, need to walk up to its shadow host.
+ // (b) Otherwise, should not walk up from a shadow root to a shadow host.
+ if (context.scope && context.scope->treeScope() == context.element->treeScope())
+ return context.element->parentOrShadowHostElement();
+
+ return context.element->parentElement();
}
bool SelectorChecker::scopeContainsLastMatchedElement(const SelectorCheckingContext& context) const
@@ -100,25 +106,21 @@ bool SelectorChecker::scopeContainsLastMatchedElement(const SelectorCheckingCont
return true;
ASSERT(context.scope);
- // If behaviorAtBoundary is not ScopeIsShadowHost, we can use "contains".
- if (!(context.behaviorAtBoundary & SelectorChecker::ScopeIsShadowHost))
- return context.scope->contains(context.element);
-
- // If a given element is scope, i.e. shadow host, matches.
- if (context.element == context.scope)
+ if (context.scope->treeScope() == context.element->treeScope())
return true;
- ShadowRoot* root = context.element->containingShadowRoot();
- if (!root)
- return false;
-
- // If a host of the containing shadow root is scope, matches.
- return root->host() == context.scope;
+ // Because Blink treats a shadow host's TreeScope as a separate one from its descendent shadow roots,
+ // if the last matched element is a shadow host, the condition above isn't met, even though it
+ // should be.
+ return context.element == context.scope->shadowHost() && (!context.previousElement || context.previousElement->isInDescendantTreeOf(context.element));
}
static inline bool nextSelectorExceedsScope(const SelectorChecker::SelectorCheckingContext& context)
{
- return context.element == context.scope && (context.behaviorAtBoundary & SelectorChecker::BoundaryBehaviorMask) != SelectorChecker::StaysWithinTreeScope;
+ if (context.scope && context.scope->isInShadowTree())
+ return context.element == context.scope->shadowHost();
+
+ return false;
}
// Recursive check of selectors and combinators
@@ -135,13 +137,16 @@ SelectorChecker::Match SelectorChecker::match(const SelectorCheckingContext& con
if (!checkOne(context, siblingTraversalStrategy, &specificity))
return SelectorFailsLocally;
- if (context.selector->m_match == CSSSelector::PseudoElement) {
+ if (context.selector->match() == CSSSelector::PseudoElement) {
if (context.selector->isCustomPseudoElement()) {
- if (!matchesCustomPseudoElement(context.element, context.selector))
+ if (!matchesCustomPseudoElement(context.element, *context.selector))
return SelectorFailsLocally;
} else if (context.selector->isContentPseudoElement()) {
if (!context.element->isInShadowTree() || !context.element->isInsertionPoint())
return SelectorFailsLocally;
+ } else if (context.selector->isShadowPseudoElement()) {
+ if (!context.element->isInShadowTree() || !context.previousElement)
+ return SelectorFailsCompletely;
} else {
if ((!context.elementStyle && m_mode == ResolvingStyle) || m_mode == QueryingRules)
return SelectorFailsLocally;
@@ -155,8 +160,7 @@ SelectorChecker::Match SelectorChecker::match(const SelectorCheckingContext& con
}
// Prepare next selector
- const CSSSelector* historySelector = context.selector->tagHistory();
- if (!historySelector) {
+ if (context.selector->isLastInTagHistory()) {
if (scopeContainsLastMatchedElement(context)) {
if (result)
result->specificity += specificity;
@@ -199,6 +203,11 @@ static inline SelectorChecker::SelectorCheckingContext prepareNextContextForRela
return nextContext;
}
+static inline bool isAuthorShadowRoot(const Node* node)
+{
+ return node && node->isShadowRoot() && toShadowRoot(node)->type() == ShadowRoot::AuthorShadowRoot;
+}
+
template<typename SiblingTraversalStrategy>
SelectorChecker::Match SelectorChecker::matchForSubSelector(const SelectorCheckingContext& context, const SiblingTraversalStrategy& siblingTraversalStrategy, MatchResult* result) const
{
@@ -212,17 +221,31 @@ SelectorChecker::Match SelectorChecker::matchForSubSelector(const SelectorChecki
nextContext.hasSelectionPseudo = dynamicPseudo == SELECTION;
if ((context.elementStyle || m_mode == CollectingCSSRules || m_mode == CollectingStyleRules || m_mode == QueryingRules) && dynamicPseudo != NOPSEUDO
&& !nextContext.hasSelectionPseudo
- && !(nextContext.hasScrollbarPseudo && nextContext.selector->m_match == CSSSelector::PseudoClass))
+ && !(nextContext.hasScrollbarPseudo && nextContext.selector->match() == CSSSelector::PseudoClass))
return SelectorFailsCompletely;
nextContext.isSubSelector = true;
return match(nextContext, siblingTraversalStrategy, result);
}
+static bool selectorMatchesShadowRoot(const CSSSelector* selector)
+{
+ return selector && selector->isShadowPseudoElement();
+}
+
+template<typename SiblingTraversalStrategy>
+SelectorChecker::Match SelectorChecker::matchForPseudoShadow(const ContainerNode* node, const SelectorCheckingContext& context, const SiblingTraversalStrategy& siblingTraversalStrategy, MatchResult* result) const
+{
+ if (!isAuthorShadowRoot(node))
+ return SelectorFailsCompletely;
+ return match(context, siblingTraversalStrategy, result);
+}
+
template<typename SiblingTraversalStrategy>
SelectorChecker::Match SelectorChecker::matchForRelation(const SelectorCheckingContext& context, const SiblingTraversalStrategy& siblingTraversalStrategy, MatchResult* result) const
{
SelectorCheckingContext nextContext = prepareNextContextForRelation(context);
+ nextContext.previousElement = context.element;
CSSSelector::Relation relation = context.selector->relation();
@@ -243,6 +266,10 @@ SelectorChecker::Match SelectorChecker::matchForRelation(const SelectorCheckingC
}
nextContext.isSubSelector = false;
nextContext.elementStyle = 0;
+
+ if (selectorMatchesShadowRoot(nextContext.selector))
+ return matchForPseudoShadow(context.element->containingShadowRoot(), nextContext, siblingTraversalStrategy, result);
+
for (nextContext.element = parentElement(context); nextContext.element; nextContext.element = parentElement(nextContext)) {
Match match = this->match(nextContext, siblingTraversalStrategy, result);
if (match == SelectorMatches || match == SelectorFailsCompletely)
@@ -256,20 +283,27 @@ SelectorChecker::Match SelectorChecker::matchForRelation(const SelectorCheckingC
if (context.selector->relationIsAffectedByPseudoContent())
return matchForShadowDistributed(context.element, siblingTraversalStrategy, nextContext, result);
+ nextContext.isSubSelector = false;
+ nextContext.elementStyle = 0;
+
+ if (selectorMatchesShadowRoot(nextContext.selector))
+ return matchForPseudoShadow(context.element->parentNode(), nextContext, siblingTraversalStrategy, result);
+
nextContext.element = parentElement(context);
if (!nextContext.element)
return SelectorFailsCompletely;
-
- nextContext.isSubSelector = false;
- nextContext.elementStyle = 0;
return match(nextContext, siblingTraversalStrategy, result);
}
case CSSSelector::DirectAdjacent:
+ // Shadow roots can't have sibling elements
+ if (selectorMatchesShadowRoot(nextContext.selector))
+ return SelectorFailsCompletely;
+
if (m_mode == ResolvingStyle) {
- if (Element* parent = parentElement(context))
+ if (ContainerNode* parent = context.element->parentElementOrShadowRoot())
parent->setChildrenAffectedByDirectAdjacentRules();
}
- nextContext.element = context.element->previousElementSibling();
+ nextContext.element = ElementTraversal::previousSibling(*context.element);
if (!nextContext.element)
return SelectorFailsAllSiblings;
nextContext.isSubSelector = false;
@@ -277,14 +311,18 @@ SelectorChecker::Match SelectorChecker::matchForRelation(const SelectorCheckingC
return match(nextContext, siblingTraversalStrategy, result);
case CSSSelector::IndirectAdjacent:
+ // Shadow roots can't have sibling elements
+ if (selectorMatchesShadowRoot(nextContext.selector))
+ return SelectorFailsCompletely;
+
if (m_mode == ResolvingStyle) {
- if (Element* parent = parentElement(context))
- parent->setChildrenAffectedByForwardPositionalRules();
+ if (ContainerNode* parent = context.element->parentElementOrShadowRoot())
+ parent->setChildrenAffectedByIndirectAdjacentRules();
}
- nextContext.element = context.element->previousElementSibling();
+ nextContext.element = ElementTraversal::previousSibling(*context.element);
nextContext.isSubSelector = false;
nextContext.elementStyle = 0;
- for (; nextContext.element; nextContext.element = nextContext.element->previousElementSibling()) {
+ for (; nextContext.element; nextContext.element = ElementTraversal::previousSibling(*nextContext.element)) {
Match match = this->match(nextContext, siblingTraversalStrategy, result);
if (match == SelectorMatches || match == SelectorFailsAllSiblings || match == SelectorFailsCompletely)
return match;
@@ -292,10 +330,9 @@ SelectorChecker::Match SelectorChecker::matchForRelation(const SelectorCheckingC
return SelectorFailsAllSiblings;
case CSSSelector::ShadowPseudo:
- case CSSSelector::ChildTree:
{
// If we're in the same tree-scope as the scoping element, then following a shadow descendant combinator would escape that and thus the scope.
- if (context.scope && context.scope->treeScope() == context.element->treeScope() && (context.behaviorAtBoundary & BoundaryBehaviorMask) != StaysWithinTreeScope)
+ if (context.scope && context.scope->shadowHost() && context.scope->shadowHost()->treeScope() == context.element->treeScope() && (context.behaviorAtBoundary & BoundaryBehaviorMask) != StaysWithinTreeScope)
return SelectorFailsCompletely;
Element* shadowHost = context.element->shadowHost();
@@ -307,11 +344,11 @@ SelectorChecker::Match SelectorChecker::matchForRelation(const SelectorCheckingC
return this->match(nextContext, siblingTraversalStrategy, result);
}
- case CSSSelector::DescendantTree:
+ case CSSSelector::ShadowDeep:
{
nextContext.isSubSelector = false;
nextContext.elementStyle = 0;
- for (nextContext.element = parentElement(context); nextContext.element; nextContext.element = parentElement(nextContext)) {
+ for (nextContext.element = parentElement(context, true); nextContext.element; nextContext.element = parentElement(nextContext, true)) {
Match match = this->match(nextContext, siblingTraversalStrategy, result);
if (match == SelectorMatches || match == SelectorFailsCompletely)
return match;
@@ -333,7 +370,7 @@ template<typename SiblingTraversalStrategy>
SelectorChecker::Match SelectorChecker::matchForShadowDistributed(const Element* element, const SiblingTraversalStrategy& siblingTraversalStrategy, SelectorCheckingContext& nextContext, MatchResult* result) const
{
ASSERT(element);
- Vector<InsertionPoint*, 8> insertionPoints;
+ WillBeHeapVector<RawPtrWillBeMember<InsertionPoint>, 8> insertionPoints;
const ContainerNode* scope = nextContext.scope;
BehaviorAtBoundary behaviorAtBoundary = nextContext.behaviorAtBoundary;
@@ -342,32 +379,44 @@ SelectorChecker::Match SelectorChecker::matchForShadowDistributed(const Element*
for (size_t i = 0; i < insertionPoints.size(); ++i) {
nextContext.element = insertionPoints[i];
- // If a given scope is a shadow host of an insertion point but behaviorAtBoundary doesn't have ScopeIsShadowHost,
+ // If a given scope is a shadow host of an insertion point but behaviorAtBoundary doesn't have ScopeIsShadowRoot,
// we need to update behaviorAtBoundary to make selectors like ":host > ::content" work correctly.
- if (scope == insertionPoints[i]->containingShadowRoot()->shadowHost() && !(behaviorAtBoundary & ScopeIsShadowHost))
- nextContext.behaviorAtBoundary = static_cast<BehaviorAtBoundary>(behaviorAtBoundary | ScopeIsShadowHost);
- else
+ if (m_mode == SharingRules) {
+ nextContext.behaviorAtBoundary = static_cast<BehaviorAtBoundary>(behaviorAtBoundary | ScopeIsShadowRoot);
+ nextContext.scope = insertionPoints[i]->containingShadowRoot();
+ } else if (scope == insertionPoints[i]->containingShadowRoot() && !(behaviorAtBoundary & ScopeIsShadowRoot)) {
+ nextContext.behaviorAtBoundary = static_cast<BehaviorAtBoundary>(behaviorAtBoundary | ScopeIsShadowRoot);
+ } else {
nextContext.behaviorAtBoundary = behaviorAtBoundary;
+ }
nextContext.isSubSelector = false;
nextContext.elementStyle = 0;
if (match(nextContext, siblingTraversalStrategy, result) == SelectorMatches)
return SelectorMatches;
}
- return SelectorFailsCompletely;
+ return SelectorFailsLocally;
}
-static inline bool containsHTMLSpace(const AtomicString& string)
+template<typename CharType>
+static inline bool containsHTMLSpaceTemplate(const CharType* string, unsigned length)
{
- for (unsigned i = 0; i < string.length(); i++)
- if (isHTMLSpace<UChar>(string[i]))
+ for (unsigned i = 0; i < length; ++i)
+ if (isHTMLSpace<CharType>(string[i]))
return true;
return false;
}
-static bool attributeValueMatches(const Attribute* attributeItem, CSSSelector::Match match, const AtomicString& selectorValue, bool caseSensitive)
+static inline bool containsHTMLSpace(const AtomicString& string)
+{
+ if (LIKELY(string.is8Bit()))
+ return containsHTMLSpaceTemplate<LChar>(string.characters8(), string.length());
+ return containsHTMLSpaceTemplate<UChar>(string.characters16(), string.length());
+}
+
+static bool attributeValueMatches(const Attribute& attributeItem, CSSSelector::Match match, const AtomicString& selectorValue, bool caseSensitive)
{
- const AtomicString& value = attributeItem->value();
+ const AtomicString& value = attributeItem.value();
if (value.isNull())
return false;
@@ -441,18 +490,28 @@ static bool anyAttributeMatches(Element& element, CSSSelector::Match match, cons
return false;
const AtomicString& selectorValue = selector.value();
- // Case sensitivity for attribute matching is looser than hasAttribute or
- // Element::shouldIgnoreAttributeCase() for now. Unclear if that's correct.
- bool caseSensitive = !element.document().isHTMLDocument() || HTMLDocument::isCaseSensitiveAttribute(selectorAttr);
- for (size_t i = 0; i < element.attributeCount(); ++i) {
- const Attribute* attributeItem = element.attributeItem(i);
+ AttributeCollection attributes = element.attributes();
+ AttributeCollection::const_iterator end = attributes.end();
+ for (AttributeCollection::const_iterator it = attributes.begin(); it != end; ++it) {
+ const Attribute& attributeItem = *it;
- if (!attributeItem->matches(selectorAttr))
+ if (!attributeItem.matches(selectorAttr))
continue;
- if (attributeValueMatches(attributeItem, match, selectorValue, caseSensitive))
+ if (attributeValueMatches(attributeItem, match, selectorValue, true))
return true;
+
+ // Case sensitivity for attribute matching is looser than hasAttribute or
+ // Element::shouldIgnoreAttributeCase() for now. Unclear if that's correct.
+ bool caseSensitive = !element.document().isHTMLDocument() || HTMLDocument::isCaseSensitiveAttribute(selectorAttr);
+
+ // If case-insensitive, re-check, and count if result differs.
+ // See http://code.google.com/p/chromium/issues/detail?id=327060
+ if (!caseSensitive && attributeValueMatches(attributeItem, match, selectorValue, false)) {
+ UseCounter::count(element.document(), UseCounter::CaseInsensitiveAttrSelectorMatch);
+ return true;
+ }
}
return false;
@@ -463,33 +522,35 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
{
ASSERT(context.element);
Element& element = *context.element;
- const CSSSelector* const & selector = context.selector;
- ASSERT(selector);
+ ASSERT(context.selector);
+ const CSSSelector& selector = *context.selector;
+
bool elementIsHostInItsShadowTree = isHostInItsShadowTree(element, context.behaviorAtBoundary, context.scope);
- if (selector->m_match == CSSSelector::Tag)
- return SelectorChecker::tagMatches(element, selector->tagQName(), elementIsHostInItsShadowTree ? MatchingHostInItsShadowTree : MatchingElement);
+ // Only :host and :ancestor should match the host: http://drafts.csswg.org/css-scoping/#host-element
+ if (elementIsHostInItsShadowTree && !selector.isHostPseudoClass()
+ && !(context.behaviorAtBoundary & TreatShadowHostAsNormalScope))
+ return false;
- if (selector->m_match == CSSSelector::Class)
- return element.hasClass() && element.classNames().contains(selector->value()) && !elementIsHostInItsShadowTree;
+ if (selector.match() == CSSSelector::Tag)
+ return SelectorChecker::tagMatches(element, selector.tagQName());
- if (selector->m_match == CSSSelector::Id)
- return element.hasID() && element.idForStyleResolution() == selector->value() && !elementIsHostInItsShadowTree;
+ if (selector.match() == CSSSelector::Class)
+ return element.hasClass() && element.classNames().contains(selector.value());
- if (selector->isAttributeSelector()) {
- if (elementIsHostInItsShadowTree)
- return false;
- if (!anyAttributeMatches(element, static_cast<CSSSelector::Match>(selector->m_match), *selector))
- return false;
- }
+ if (selector.match() == CSSSelector::Id)
+ return element.hasID() && element.idForStyleResolution() == selector.value();
+
+ if (selector.isAttributeSelector())
+ return anyAttributeMatches(element, selector.match(), selector);
- if (selector->m_match == CSSSelector::PseudoClass) {
+ if (selector.match() == CSSSelector::PseudoClass) {
// Handle :not up front.
- if (selector->pseudoType() == CSSSelector::PseudoNot) {
+ if (selector.pseudoType() == CSSSelector::PseudoNot) {
SelectorCheckingContext subContext(context);
subContext.isSubSelector = true;
- ASSERT(selector->selectorList());
- for (subContext.selector = selector->selectorList()->first(); subContext.selector; subContext.selector = subContext.selector->tagHistory()) {
+ ASSERT(selector.selectorList());
+ for (subContext.selector = selector.selectorList()->first(); subContext.selector; subContext.selector = subContext.selector->tagHistory()) {
// :not cannot nest. I don't really know why this is a
// restriction in CSS3, but it is, so let's honor it.
// the parser enforces that this never occurs
@@ -497,6 +558,10 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
// We select between :visited and :link when applying. We don't know which one applied (or not) yet.
if (subContext.selector->pseudoType() == CSSSelector::PseudoVisited || (subContext.selector->pseudoType() == CSSSelector::PseudoLink && subContext.visitedMatchType == VisitedMatchEnabled))
return true;
+ // context.scope is not available if m_mode == SharingRules.
+ // We cannot determine whether :host or :scope matches a given element or not.
+ if (m_mode == SharingRules && (subContext.selector->isHostPseudoClass() || subContext.selector->pseudoType() == CSSSelector::PseudoScope))
+ return true;
if (!checkOne(subContext, DOMSiblingTraversalStrategy()))
return true;
}
@@ -505,12 +570,12 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
// (since there are no elements involved).
return checkScrollbarPseudoClass(context, &element.document(), selector);
} else if (context.hasSelectionPseudo) {
- if (selector->pseudoType() == CSSSelector::PseudoWindowInactive)
+ if (selector.pseudoType() == CSSSelector::PseudoWindowInactive)
return !element.document().page()->focusController().isActive();
}
// Normal element pseudo class checking.
- switch (selector->pseudoType()) {
+ switch (selector.pseudoType()) {
// Pseudo classes:
case CSSSelector::PseudoNot:
break; // Already handled up above.
@@ -541,8 +606,8 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
}
case CSSSelector::PseudoFirstChild:
// first-child matches the first child that is an element
- if (Element* parent = element.parentElement()) {
- bool result = siblingTraversalStrategy.isFirstChild(&element);
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
+ bool result = siblingTraversalStrategy.isFirstChild(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element.renderStyle();
parent->setChildrenAffectedByFirstChildRules();
@@ -554,8 +619,8 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
break;
case CSSSelector::PseudoFirstOfType:
// first-of-type matches the first element of its type
- if (Element* parent = element.parentElement()) {
- bool result = siblingTraversalStrategy.isFirstOfType(&element, element.tagQName());
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
+ bool result = siblingTraversalStrategy.isFirstOfType(element, element.tagQName());
if (m_mode == ResolvingStyle)
parent->setChildrenAffectedByForwardPositionalRules();
return result;
@@ -563,8 +628,8 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
break;
case CSSSelector::PseudoLastChild:
// last-child matches the last child that is an element
- if (Element* parent = element.parentElement()) {
- bool result = parent->isFinishedParsingChildren() && siblingTraversalStrategy.isLastChild(&element);
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
+ bool result = parent->isFinishedParsingChildren() && siblingTraversalStrategy.isLastChild(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element.renderStyle();
parent->setChildrenAffectedByLastChildRules();
@@ -576,18 +641,18 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
break;
case CSSSelector::PseudoLastOfType:
// last-of-type matches the last element of its type
- if (Element* parent = element.parentElement()) {
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
if (m_mode == ResolvingStyle)
parent->setChildrenAffectedByBackwardPositionalRules();
if (!parent->isFinishedParsingChildren())
return false;
- return siblingTraversalStrategy.isLastOfType(&element, element.tagQName());
+ return siblingTraversalStrategy.isLastOfType(element, element.tagQName());
}
break;
case CSSSelector::PseudoOnlyChild:
- if (Element* parent = element.parentElement()) {
- bool firstChild = siblingTraversalStrategy.isFirstChild(&element);
- bool onlyChild = firstChild && parent->isFinishedParsingChildren() && siblingTraversalStrategy.isLastChild(&element);
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
+ bool firstChild = siblingTraversalStrategy.isFirstChild(element);
+ bool onlyChild = firstChild && parent->isFinishedParsingChildren() && siblingTraversalStrategy.isLastChild(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element.renderStyle();
parent->setChildrenAffectedByFirstChildRules();
@@ -602,69 +667,68 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
break;
case CSSSelector::PseudoOnlyOfType:
// FIXME: This selector is very slow.
- if (Element* parent = element.parentElement()) {
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
if (m_mode == ResolvingStyle) {
parent->setChildrenAffectedByForwardPositionalRules();
parent->setChildrenAffectedByBackwardPositionalRules();
}
if (!parent->isFinishedParsingChildren())
return false;
- return siblingTraversalStrategy.isFirstOfType(&element, element.tagQName()) && siblingTraversalStrategy.isLastOfType(&element, element.tagQName());
+ return siblingTraversalStrategy.isFirstOfType(element, element.tagQName()) && siblingTraversalStrategy.isLastOfType(element, element.tagQName());
}
break;
case CSSSelector::PseudoNthChild:
- if (!selector->parseNth())
+ if (!selector.parseNth())
break;
- if (Element* parent = element.parentElement()) {
- int count = 1 + siblingTraversalStrategy.countElementsBefore(&element);
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
+ int count = 1 + siblingTraversalStrategy.countElementsBefore(element);
if (m_mode == ResolvingStyle) {
RenderStyle* childStyle = context.elementStyle ? context.elementStyle : element.renderStyle();
- element.setChildIndex(count);
if (childStyle)
childStyle->setUnique();
parent->setChildrenAffectedByForwardPositionalRules();
}
- if (selector->matchNth(count))
+ if (selector.matchNth(count))
return true;
}
break;
case CSSSelector::PseudoNthOfType:
- if (!selector->parseNth())
+ if (!selector.parseNth())
break;
- if (Element* parent = element.parentElement()) {
- int count = 1 + siblingTraversalStrategy.countElementsOfTypeBefore(&element, element.tagQName());
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
+ int count = 1 + siblingTraversalStrategy.countElementsOfTypeBefore(element, element.tagQName());
if (m_mode == ResolvingStyle)
parent->setChildrenAffectedByForwardPositionalRules();
- if (selector->matchNth(count))
+ if (selector.matchNth(count))
return true;
}
break;
case CSSSelector::PseudoNthLastChild:
- if (!selector->parseNth())
+ if (!selector.parseNth())
break;
- if (Element* parent = element.parentElement()) {
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
if (m_mode == ResolvingStyle)
parent->setChildrenAffectedByBackwardPositionalRules();
if (!parent->isFinishedParsingChildren())
return false;
- int count = 1 + siblingTraversalStrategy.countElementsAfter(&element);
- if (selector->matchNth(count))
+ int count = 1 + siblingTraversalStrategy.countElementsAfter(element);
+ if (selector.matchNth(count))
return true;
}
break;
case CSSSelector::PseudoNthLastOfType:
- if (!selector->parseNth())
+ if (!selector.parseNth())
break;
- if (Element* parent = element.parentElement()) {
+ if (ContainerNode* parent = element.parentElementOrDocumentFragment()) {
if (m_mode == ResolvingStyle)
parent->setChildrenAffectedByBackwardPositionalRules();
if (!parent->isFinishedParsingChildren())
return false;
- int count = 1 + siblingTraversalStrategy.countElementsOfTypeAfter(&element, element.tagQName());
- if (selector->matchNth(count))
+ int count = 1 + siblingTraversalStrategy.countElementsOfTypeAfter(element, element.tagQName());
+ if (selector.matchNth(count))
return true;
}
break;
@@ -676,8 +740,8 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
{
SelectorCheckingContext subContext(context);
subContext.isSubSelector = true;
- ASSERT(selector->selectorList());
- for (subContext.selector = selector->selectorList()->first(); subContext.selector; subContext.selector = CSSSelectorList::next(subContext.selector)) {
+ ASSERT(selector.selectorList());
+ for (subContext.selector = selector.selectorList()->first(); subContext.selector; subContext.selector = CSSSelectorList::next(*subContext.selector)) {
if (match(subContext, siblingTraversalStrategy) == SelectorMatches)
return true;
}
@@ -699,7 +763,7 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
if (context.elementStyle)
context.elementStyle->setAffectedByDrag();
else
- element.setChildrenAffectedByDrag();
+ element.setChildrenOrSiblingsAffectedByDrag();
}
if (element.renderer() && element.renderer()->isDragging())
return true;
@@ -709,18 +773,18 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
if (context.elementStyle)
context.elementStyle->setAffectedByFocus();
else
- element.setChildrenAffectedByFocus();
+ element.setChildrenOrSiblingsAffectedByFocus();
}
return matchesFocusPseudoClass(element);
case CSSSelector::PseudoHover:
// If we're in quirks mode, then hover should never match anchors with no
// href and *:hover should not match anything. This is important for sites like wsj.com.
- if (m_strictParsing || context.isSubSelector || (selector->m_match == CSSSelector::Tag && selector->tagQName() != anyQName() && !isHTMLAnchorElement(element)) || element.isLink()) {
+ if (m_strictParsing || context.isSubSelector || element.isLink()) {
if (m_mode == ResolvingStyle) {
if (context.elementStyle)
context.elementStyle->setAffectedByHover();
else
- element.setChildrenAffectedByHover();
+ element.setChildrenOrSiblingsAffectedByHover();
}
if (element.hovered() || InspectorInstrumentation::forcePseudoState(&element, CSSSelector::PseudoHover))
return true;
@@ -729,19 +793,19 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
case CSSSelector::PseudoActive:
// If we're in quirks mode, then :active should never match anchors with no
// href and *:active should not match anything.
- if (m_strictParsing || context.isSubSelector || (selector->m_match == CSSSelector::Tag && selector->tagQName() != anyQName() && !isHTMLAnchorElement(element)) || element.isLink()) {
+ if (m_strictParsing || context.isSubSelector || element.isLink()) {
if (m_mode == ResolvingStyle) {
if (context.elementStyle)
context.elementStyle->setAffectedByActive();
else
- element.setChildrenAffectedByActive();
+ element.setChildrenOrSiblingsAffectedByActive();
}
if (element.active() || InspectorInstrumentation::forcePseudoState(&element, CSSSelector::PseudoActive))
return true;
}
break;
case CSSSelector::PseudoEnabled:
- if (element.isFormControlElement() || element.hasTagName(optionTag) || isHTMLOptGroupElement(element))
+ if (element.isFormControlElement() || isHTMLOptionElement(element) || isHTMLOptGroupElement(element))
return !element.isDisabledFormControl();
break;
case CSSSelector::PseudoFullPageMedia:
@@ -750,7 +814,7 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
case CSSSelector::PseudoDefault:
return element.isDefaultButtonForForm();
case CSSSelector::PseudoDisabled:
- if (element.isFormControlElement() || element.hasTagName(optionTag) || isHTMLOptGroupElement(element))
+ if (element.isFormControlElement() || isHTMLOptionElement(element) || isHTMLOptGroupElement(element))
return element.isDisabledFormControl();
break;
case CSSSelector::PseudoReadOnly:
@@ -769,7 +833,7 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
return element.willValidate() && !element.isValidFormControlElement();
case CSSSelector::PseudoChecked:
{
- if (element.hasTagName(inputTag)) {
+ if (isHTMLInputElement(element)) {
HTMLInputElement& inputElement = toHTMLInputElement(element);
// Even though WinIE allows checked and indeterminate to
// co-exist, the CSS selector spec says that you can't be
@@ -778,7 +842,7 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
// test for matching the pseudo.
if (inputElement.shouldAppearChecked() && !inputElement.shouldAppearIndeterminate())
return true;
- } else if (element.hasTagName(optionTag) && toHTMLOptionElement(element).selected())
+ } else if (isHTMLOptionElement(element) && toHTMLOptionElement(element).selected())
return true;
break;
}
@@ -795,7 +859,7 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
value = toVTTElement(element).language();
else
value = element.computeInheritedLanguage();
- const AtomicString& argument = selector->argument();
+ const AtomicString& argument = selector.argument();
if (value.isEmpty() || !value.startsWith(argument, false))
break;
if (value.length() != argument.length() && value[argument.length()] != '-')
@@ -807,9 +871,9 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
// element is an element in the document, the 'full-screen' pseudoclass applies to
// that element. Also, an <iframe>, <object> or <embed> element whose child browsing
// context's Document is in the fullscreen state has the 'full-screen' pseudoclass applied.
- if (element.isFrameElementBase() && element.containsFullScreenElement())
+ if (isHTMLFrameElementBase(element) && element.containsFullScreenElement())
return true;
- if (FullscreenElementStack* fullscreen = FullscreenElementStack::fromIfExists(&element.document())) {
+ if (FullscreenElementStack* fullscreen = FullscreenElementStack::fromIfExists(element.document())) {
if (!fullscreen->webkitIsFullScreen())
return false;
return element == fullscreen->webkitCurrentFullScreenElement();
@@ -820,13 +884,9 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
case CSSSelector::PseudoFullScreenDocument:
// While a Document is in the fullscreen state, the 'full-screen-document' pseudoclass applies
// to all elements of that Document.
- if (!FullscreenElementStack::isFullScreen(&element.document()))
+ if (!FullscreenElementStack::isFullScreen(element.document()))
return false;
return true;
- case CSSSelector::PseudoSeamlessDocument:
- // While a document is rendered in a seamless iframe, the 'seamless-document' pseudoclass applies
- // to all elements of that Document.
- return element.document().shouldDisplaySeamlesslyWithParent();
case CSSSelector::PseudoInRange:
element.document().setContainsValidityStyleRules();
return element.isInRange();
@@ -840,7 +900,9 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
case CSSSelector::PseudoScope:
{
- const Node* contextualReferenceNode = !context.scope || (context.behaviorAtBoundary & BoundaryBehaviorMask) == CrossesBoundary ? element.document().documentElement() : context.scope;
+ if (m_mode == SharingRules)
+ return true;
+ const Node* contextualReferenceNode = !context.scope ? element.document().documentElement() : context.scope;
if (element == contextualReferenceNode)
return true;
break;
@@ -852,14 +914,20 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
break;
case CSSSelector::PseudoHost:
+ case CSSSelector::PseudoHostContext:
{
+ if (m_mode == SharingRules)
+ return true;
// :host only matches a shadow host when :host is in a shadow tree of the shadow host.
- if (!context.scope || !(context.behaviorAtBoundary & ScopeIsShadowHost) || context.scope != element)
+ if (!context.scope)
+ return false;
+ const ContainerNode* shadowHost = context.scope->shadowHost();
+ if (!shadowHost || shadowHost != element)
return false;
ASSERT(element.shadow());
// For empty parameter case, i.e. just :host or :host().
- if (!selector->selectorList()) // Use *'s specificity. So just 0.
+ if (!selector.selectorList()) // Use *'s specificity. So just 0.
return true;
SelectorCheckingContext subContext(context);
@@ -869,22 +937,30 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
unsigned maxSpecificity = 0;
// If one of simple selectors matches an element, returns SelectorMatches. Just "OR".
- for (subContext.selector = selector->selectorList()->first(); subContext.selector; subContext.selector = CSSSelectorList::next(subContext.selector)) {
+ for (subContext.selector = selector.selectorList()->first(); subContext.selector; subContext.selector = CSSSelectorList::next(*subContext.selector)) {
subContext.behaviorAtBoundary = ScopeIsShadowHostInPseudoHostParameter;
subContext.scope = context.scope;
// Use NodeRenderingTraversal to traverse a composed ancestor list of a given element.
- for (Element* nextElement = &element; nextElement; nextElement = NodeRenderingTraversal::parentElement(nextElement)) {
+ Element* nextElement = &element;
+ SelectorCheckingContext hostContext(subContext);
+ do {
MatchResult subResult;
- subContext.element = nextElement;
- if (match(subContext, siblingTraversalStrategy, &subResult) == SelectorMatches) {
+ hostContext.element = nextElement;
+ if (match(hostContext, siblingTraversalStrategy, &subResult) == SelectorMatches) {
matched = true;
// Consider div:host(div:host(div:host(div:host...))).
- maxSpecificity = std::max(maxSpecificity, subContext.selector->specificity() + subResult.specificity);
+ maxSpecificity = std::max(maxSpecificity, hostContext.selector->specificity() + subResult.specificity);
break;
}
- subContext.behaviorAtBoundary = CrossesBoundary;
- subContext.scope = 0;
- }
+ hostContext.behaviorAtBoundary = DoesNotCrossBoundary;
+ hostContext.scope = 0;
+
+ if (selector.pseudoType() == CSSSelector::PseudoHost)
+ break;
+
+ hostContext.elementStyle = 0;
+ nextElement = NodeRenderingTraversal::parentElement(nextElement);
+ } while (nextElement);
}
if (matched) {
if (specificity)
@@ -913,14 +989,14 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
break;
}
return false;
- }
- else if (selector->m_match == CSSSelector::PseudoElement && selector->pseudoType() == CSSSelector::PseudoCue) {
+ } else if (selector.match() == CSSSelector::PseudoElement && selector.pseudoType() == CSSSelector::PseudoCue) {
SelectorCheckingContext subContext(context);
subContext.isSubSelector = true;
subContext.behaviorAtBoundary = StaysWithinTreeScope;
- const CSSSelector* const & selector = context.selector;
- for (subContext.selector = selector->selectorList()->first(); subContext.selector; subContext.selector = CSSSelectorList::next(subContext.selector)) {
+ const CSSSelector* contextSelector = context.selector;
+ ASSERT(contextSelector);
+ for (subContext.selector = contextSelector->selectorList()->first(); subContext.selector; subContext.selector = CSSSelectorList::next(*subContext.selector)) {
if (match(subContext, siblingTraversalStrategy) == SelectorMatches)
return true;
}
@@ -930,21 +1006,21 @@ bool SelectorChecker::checkOne(const SelectorCheckingContext& context, const Sib
return true;
}
-bool SelectorChecker::checkScrollbarPseudoClass(const SelectorCheckingContext& context, Document* document, const CSSSelector* selector) const
+bool SelectorChecker::checkScrollbarPseudoClass(const SelectorCheckingContext& context, Document* document, const CSSSelector& selector) const
{
RenderScrollbar* scrollbar = context.scrollbar;
ScrollbarPart part = context.scrollbarPart;
// FIXME: This is a temporary hack for resizers and scrollbar corners. Eventually :window-inactive should become a real
// pseudo class and just apply to everything.
- if (selector->pseudoType() == CSSSelector::PseudoWindowInactive)
+ if (selector.pseudoType() == CSSSelector::PseudoWindowInactive)
return !document->page()->focusController().isActive();
if (!scrollbar)
return false;
- ASSERT(selector->m_match == CSSSelector::PseudoClass);
- switch (selector->pseudoType()) {
+ ASSERT(selector.match() == CSSSelector::PseudoClass);
+ switch (selector.pseudoType()) {
case CSSSelector::PseudoEnabled:
return scrollbar->enabled();
case CSSSelector::PseudoDisabled:
@@ -1011,19 +1087,19 @@ bool SelectorChecker::checkScrollbarPseudoClass(const SelectorCheckingContext& c
}
}
-unsigned SelectorChecker::determineLinkMatchType(const CSSSelector* selector)
+unsigned SelectorChecker::determineLinkMatchType(const CSSSelector& selector)
{
unsigned linkMatchType = MatchAll;
// Statically determine if this selector will match a link in visited, unvisited or any state, or never.
// :visited never matches other elements than the innermost link element.
- for (; selector; selector = selector->tagHistory()) {
- switch (selector->pseudoType()) {
+ for (const CSSSelector* current = &selector; current; current = current->tagHistory()) {
+ switch (current->pseudoType()) {
case CSSSelector::PseudoNot:
{
// :not(:visited) is equivalent to :link. Parser enforces that :not can't nest.
- ASSERT(selector->selectorList());
- for (const CSSSelector* subSelector = selector->selectorList()->first(); subSelector; subSelector = subSelector->tagHistory()) {
+ ASSERT(current->selectorList());
+ for (const CSSSelector* subSelector = current->selectorList()->first(); subSelector; subSelector = subSelector->tagHistory()) {
CSSSelector::PseudoType subType = subSelector->pseudoType();
if (subType == CSSSelector::PseudoVisited)
linkMatchType &= ~SelectorChecker::MatchVisited;
@@ -1042,7 +1118,7 @@ unsigned SelectorChecker::determineLinkMatchType(const CSSSelector* selector)
// We don't support :link and :visited inside :-webkit-any.
break;
}
- CSSSelector::Relation relation = selector->relation();
+ CSSSelector::Relation relation = current->relation();
if (relation == CSSSelector::SubSelector)
continue;
if (relation != CSSSelector::Descendant && relation != CSSSelector::Child)
diff --git a/chromium/third_party/WebKit/Source/core/css/SelectorChecker.h b/chromium/third_party/WebKit/Source/core/css/SelectorChecker.h
index 13d7d7dc1fc..55fddb9b942 100644
--- a/chromium/third_party/WebKit/Source/core/css/SelectorChecker.h
+++ b/chromium/third_party/WebKit/Source/core/css/SelectorChecker.h
@@ -49,26 +49,22 @@ public:
explicit SelectorChecker(Document&, Mode);
enum BehaviorAtBoundary {
DoesNotCrossBoundary = 0,
- CrossesBoundary = 1,
+ // FIXME: refactor to remove BoundaryBehavior (i.e. DoesNotCrossBoundary and StaysWithinTreeScope).
StaysWithinTreeScope = 2,
BoundaryBehaviorMask = 3, // 2bit for boundary behavior
ScopeContainsLastMatchedElement = 4,
- ScopeIsShadowHost = 8,
+ ScopeIsShadowRoot = 8,
TreatShadowHostAsNormalScope = 16,
- ScopeIsShadowHostInPseudoHostParameter = CrossesBoundary | ScopeIsShadowHost | TreatShadowHostAsNormalScope
- };
-
- enum MatchingTagType {
- MatchingElement = 0,
- MatchingHostInItsShadowTree
+ ScopeIsShadowHostInPseudoHostParameter = ScopeIsShadowRoot | TreatShadowHostAsNormalScope
};
struct SelectorCheckingContext {
// Initial selector constructor
- SelectorCheckingContext(const CSSSelector* selector, Element* element, VisitedMatchType visitedMatchType)
- : selector(selector)
+ SelectorCheckingContext(const CSSSelector& selector, Element* element, VisitedMatchType visitedMatchType)
+ : selector(&selector)
, element(element)
+ , previousElement(0)
, scope(0)
, visitedMatchType(visitedMatchType)
, pseudoId(NOPSEUDO)
@@ -83,6 +79,7 @@ public:
const CSSSelector* selector;
Element* element;
+ Element* previousElement;
const ContainerNode* scope;
VisitedMatchType visitedMatchType;
PseudoId pseudoId;
@@ -114,13 +111,13 @@ public:
Mode mode() const { return m_mode; }
- static bool tagMatches(const Element&, const QualifiedName&, MatchingTagType = MatchingElement);
- static bool isCommonPseudoClassSelector(const CSSSelector*);
+ static bool tagMatches(const Element&, const QualifiedName&);
+ static bool isCommonPseudoClassSelector(const CSSSelector&);
static bool matchesFocusPseudoClass(const Element&);
static bool checkExactAttribute(const Element&, const QualifiedName& selectorAttributeName, const StringImpl* value);
enum LinkMatchMask { MatchLink = 1, MatchVisited = 2, MatchAll = MatchLink | MatchVisited };
- static unsigned determineLinkMatchType(const CSSSelector*);
+ static unsigned determineLinkMatchType(const CSSSelector&);
static bool isHostInItsShadowTree(const Element&, BehaviorAtBoundary, const ContainerNode* scope);
@@ -131,9 +128,11 @@ private:
Match matchForRelation(const SelectorCheckingContext&, const SiblingTraversalStrategy&, MatchResult*) const;
template<typename SiblingTraversalStrategy>
Match matchForShadowDistributed(const Element*, const SiblingTraversalStrategy&, SelectorCheckingContext& nextContext, MatchResult* = 0) const;
+ template<typename SiblingTraversalStrategy>
+ Match matchForPseudoShadow(const ContainerNode*, const SelectorCheckingContext&, const SiblingTraversalStrategy&, MatchResult*) const;
- bool checkScrollbarPseudoClass(const SelectorCheckingContext&, Document*, const CSSSelector*) const;
- Element* parentElement(const SelectorCheckingContext&) const;
+ bool checkScrollbarPseudoClass(const SelectorCheckingContext&, Document*, const CSSSelector&) const;
+ Element* parentElement(const SelectorCheckingContext&, bool allowToCrossBoundary = false) const;
bool scopeContainsLastMatchedElement(const SelectorCheckingContext&) const;
static bool isFrameFocused(const Element&);
@@ -143,23 +142,23 @@ private:
Mode m_mode;
};
-inline bool SelectorChecker::isCommonPseudoClassSelector(const CSSSelector* selector)
+inline bool SelectorChecker::isCommonPseudoClassSelector(const CSSSelector& selector)
{
- if (selector->m_match != CSSSelector::PseudoClass)
+ if (selector.match() != CSSSelector::PseudoClass)
return false;
- CSSSelector::PseudoType pseudoType = selector->pseudoType();
+ CSSSelector::PseudoType pseudoType = selector.pseudoType();
return pseudoType == CSSSelector::PseudoLink
|| pseudoType == CSSSelector::PseudoAnyLink
|| pseudoType == CSSSelector::PseudoVisited
|| pseudoType == CSSSelector::PseudoFocus;
}
-inline bool SelectorChecker::tagMatches(const Element& element, const QualifiedName& tagQName, MatchingTagType matchingTagType)
+inline bool SelectorChecker::tagMatches(const Element& element, const QualifiedName& tagQName)
{
if (tagQName == anyQName())
return true;
const AtomicString& localName = tagQName.localName();
- if (localName != starAtom && (localName != element.localName() || matchingTagType == MatchingHostInItsShadowTree))
+ if (localName != starAtom && localName != element.localName())
return false;
const AtomicString& namespaceURI = tagQName.namespaceURI();
return namespaceURI == starAtom || namespaceURI == element.namespaceURI();
@@ -169,10 +168,10 @@ inline bool SelectorChecker::checkExactAttribute(const Element& element, const Q
{
if (!element.hasAttributesWithoutUpdate())
return false;
- unsigned size = element.attributeCount();
- for (unsigned i = 0; i < size; ++i) {
- const Attribute* attribute = element.attributeItem(i);
- if (attribute->matches(selectorAttributeName) && (!value || attribute->value().impl() == value))
+ AttributeCollection attributes = element.attributes();
+ AttributeCollection::const_iterator end = attributes.end();
+ for (AttributeCollection::const_iterator it = attributes.begin(); it != end; ++it) {
+ if (it->matches(selectorAttributeName) && (!value || it->value().impl() == value))
return true;
}
return false;
@@ -180,7 +179,7 @@ inline bool SelectorChecker::checkExactAttribute(const Element& element, const Q
inline bool SelectorChecker::isHostInItsShadowTree(const Element& element, BehaviorAtBoundary behaviorAtBoundary, const ContainerNode* scope)
{
- return (behaviorAtBoundary & (ScopeIsShadowHost | TreatShadowHostAsNormalScope)) == ScopeIsShadowHost && scope == element;
+ return scope && scope->isInShadowTree() && scope->shadowHost() == element;
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.cpp b/chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.cpp
deleted file mode 100644
index 557f0438a56..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.cpp
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
- * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
- * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com)
- * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com)
- * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013 Apple Inc. All rights reserved.
- * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org>
- * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org>
- * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
- * Copyright (c) 2011, Code Aurora Forum. All rights reserved.
- * Copyright (C) Research In Motion Limited 2011. All rights reserved.
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#include "config.h"
-#include "core/css/SelectorCheckerFastPath.h"
-
-#include "HTMLNames.h"
-#include "core/dom/Element.h"
-#include "core/html/HTMLDocument.h"
-
-namespace WebCore {
-
-using namespace HTMLNames;
-
-namespace {
-
-template <bool checkValue(const Element&, const CSSSelector*)>
-inline bool fastCheckSingleSelector(const CSSSelector*& selector, const Element*& element, const CSSSelector*& topChildOrSubselector, const Element*& topChildOrSubselectorMatchElement)
-{
- for (; element; element = element->parentElement()) {
- if (checkValue(*element, selector)) {
- if (selector->relation() == CSSSelector::Descendant)
- topChildOrSubselector = 0;
- else if (!topChildOrSubselector) {
- ASSERT(selector->relation() == CSSSelector::Child || selector->relation() == CSSSelector::SubSelector);
- topChildOrSubselector = selector;
- topChildOrSubselectorMatchElement = element;
- }
- if (selector->relation() != CSSSelector::SubSelector)
- element = element->parentElement();
- selector = selector->tagHistory();
- return true;
- }
- if (topChildOrSubselector) {
- // Child or subselector check failed.
- // If the match element is null, topChildOrSubselector was also the very topmost selector and had to match
- // the original element we were checking.
- if (!topChildOrSubselectorMatchElement)
- return false;
- // There may be other matches down the ancestor chain.
- // Rewind to the topmost child or subselector and the element it matched, continue checking ancestors.
- selector = topChildOrSubselector;
- element = topChildOrSubselectorMatchElement->parentElement();
- topChildOrSubselector = 0;
- return true;
- }
- }
- return false;
-}
-
-inline bool checkClassValue(const Element& element, const CSSSelector* selector)
-{
- return element.hasClass() && element.classNames().contains(selector->value());
-}
-
-inline bool checkIDValue(const Element& element, const CSSSelector* selector)
-{
- return element.hasID() && element.idForStyleResolution() == selector->value();
-}
-
-inline bool checkExactAttributeValue(const Element& element, const CSSSelector* selector)
-{
- return SelectorChecker::checkExactAttribute(element, selector->attribute(), selector->value().impl());
-}
-
-inline bool checkTagValue(const Element& element, const CSSSelector* selector)
-{
- return SelectorChecker::tagMatches(element, selector->tagQName());
-}
-
-}
-
-SelectorCheckerFastPath::SelectorCheckerFastPath(const CSSSelector* selector, const Element& element)
- : m_selector(selector)
- , m_element(element)
-{
-}
-
-bool SelectorCheckerFastPath::matchesRightmostSelector(SelectorChecker::VisitedMatchType visitedMatchType) const
-{
- ASSERT(SelectorCheckerFastPath::canUse(m_selector));
-
- switch (m_selector->m_match) {
- case CSSSelector::Tag:
- return checkTagValue(m_element, m_selector);
- case CSSSelector::Class:
- return checkClassValue(m_element, m_selector);
- case CSSSelector::Id:
- return checkIDValue(m_element, m_selector);
- case CSSSelector::Exact:
- case CSSSelector::Set:
- return checkExactAttributeValue(m_element, m_selector);
- case CSSSelector::PseudoClass:
- return commonPseudoClassSelectorMatches(visitedMatchType);
- default:
- ASSERT_NOT_REACHED();
- }
- return false;
-}
-
-bool SelectorCheckerFastPath::matches() const
-{
- ASSERT(matchesRightmostSelector(SelectorChecker::VisitedMatchEnabled));
- const CSSSelector* selector = m_selector;
- const Element* element = &m_element;
-
- const CSSSelector* topChildOrSubselector = 0;
- const Element* topChildOrSubselectorMatchElement = 0;
- if (selector->relation() == CSSSelector::Child || selector->relation() == CSSSelector::SubSelector)
- topChildOrSubselector = selector;
-
- if (selector->relation() != CSSSelector::SubSelector)
- element = element->parentElement();
-
- selector = selector->tagHistory();
-
- // We know this compound selector has descendant, child and subselector combinators only and all components are simple.
- while (selector) {
- switch (selector->m_match) {
- case CSSSelector::Class:
- if (!fastCheckSingleSelector<checkClassValue>(selector, element, topChildOrSubselector, topChildOrSubselectorMatchElement))
- return false;
- break;
- case CSSSelector::Id:
- if (!fastCheckSingleSelector<checkIDValue>(selector, element, topChildOrSubselector, topChildOrSubselectorMatchElement))
- return false;
- break;
- case CSSSelector::Tag:
- if (!fastCheckSingleSelector<checkTagValue>(selector, element, topChildOrSubselector, topChildOrSubselectorMatchElement))
- return false;
- break;
- case CSSSelector::Set:
- case CSSSelector::Exact:
- if (!fastCheckSingleSelector<checkExactAttributeValue>(selector, element, topChildOrSubselector, topChildOrSubselectorMatchElement))
- return false;
- break;
- default:
- ASSERT_NOT_REACHED();
- }
- }
- return true;
-}
-
-static inline bool isFastCheckableRelation(CSSSelector::Relation relation)
-{
- return relation == CSSSelector::Descendant || relation == CSSSelector::Child || relation == CSSSelector::SubSelector;
-}
-
-static inline bool isFastCheckableMatch(const CSSSelector* selector)
-{
- if (selector->m_match == CSSSelector::Set) {
- // Style attribute is generated lazily but the fast path doesn't trigger it.
- // Disallow them here rather than making the fast path more branchy.
- return selector->attribute() != styleAttr;
- }
- if (selector->m_match == CSSSelector::Exact)
- return selector->attribute() != styleAttr && HTMLDocument::isCaseSensitiveAttribute(selector->attribute());
- return selector->m_match == CSSSelector::Tag || selector->m_match == CSSSelector::Id || selector->m_match == CSSSelector::Class;
-}
-
-static inline bool isFastCheckableRightmostSelector(const CSSSelector* selector)
-{
- if (!isFastCheckableRelation(selector->relation()))
- return false;
- return isFastCheckableMatch(selector) || SelectorChecker::isCommonPseudoClassSelector(selector);
-}
-
-bool SelectorCheckerFastPath::canUse(const CSSSelector* selector)
-{
- if (!isFastCheckableRightmostSelector(selector))
- return false;
- for (selector = selector->tagHistory(); selector; selector = selector->tagHistory()) {
- if (!isFastCheckableRelation(selector->relation()))
- return false;
- if (!isFastCheckableMatch(selector))
- return false;
- }
- return true;
-}
-
-bool SelectorCheckerFastPath::commonPseudoClassSelectorMatches(SelectorChecker::VisitedMatchType visitedMatchType) const
-{
- ASSERT(SelectorChecker::isCommonPseudoClassSelector(m_selector));
- switch (m_selector->pseudoType()) {
- case CSSSelector::PseudoLink:
- case CSSSelector::PseudoAnyLink:
- return m_element.isLink();
- case CSSSelector::PseudoVisited:
- return m_element.isLink() && visitedMatchType == SelectorChecker::VisitedMatchEnabled;
- case CSSSelector::PseudoFocus:
- return SelectorChecker::matchesFocusPseudoClass(m_element);
- default:
- ASSERT_NOT_REACHED();
- }
- return true;
-}
-
-
-}
diff --git a/chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.h b/chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.h
deleted file mode 100644
index 1a37b9ac35a..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/SelectorCheckerFastPath.h
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
- * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com)
- * Copyright (C) 2006, 2007 Nicholas Shanks (webkit@nickshanks.com)
- * Copyright (C) 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013 Apple Inc. All rights reserved.
- * Copyright (C) 2007 Alexey Proskuryakov <ap@webkit.org>
- * Copyright (C) 2007, 2008 Eric Seidel <eric@webkit.org>
- * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
- * Copyright (c) 2011, Code Aurora Forum. All rights reserved.
- * Copyright (C) Research In Motion Limited 2011. All rights reserved.
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public License
- * along with this library; see the file COPYING.LIB. If not, write to
- * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- */
-
-#ifndef SelectorCheckerFastPath_h
-#define SelectorCheckerFastPath_h
-
-#include "core/css/CSSSelector.h"
-#include "core/css/SelectorChecker.h"
-
-namespace WebCore {
-
-class SelectorCheckerFastPath {
-public:
- SelectorCheckerFastPath(const CSSSelector*, const Element&);
-
- bool matches() const;
- bool matchesRightmostSelector(SelectorChecker::VisitedMatchType) const;
- bool matchesRightmostAttributeSelector() const;
-
- static bool canUse(const CSSSelector*);
-
-private:
- bool commonPseudoClassSelectorMatches(SelectorChecker::VisitedMatchType) const;
-
- const CSSSelector* m_selector;
- const Element& m_element;
-};
-
-inline bool SelectorCheckerFastPath::matchesRightmostAttributeSelector() const
-{
- if (m_selector->m_match == CSSSelector::Exact || m_selector->m_match == CSSSelector::Set)
- return SelectorChecker::checkExactAttribute(m_element, m_selector->attribute(), m_selector->value().impl());
- ASSERT(!m_selector->isAttributeSelector());
- return true;
-}
-
-}
-
-#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/SelectorFilter.cpp b/chromium/third_party/WebKit/Source/core/css/SelectorFilter.cpp
index 50d13de6b48..c0c6a97a16a 100644
--- a/chromium/third_party/WebKit/Source/core/css/SelectorFilter.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/SelectorFilter.cpp
@@ -108,45 +108,44 @@ void SelectorFilter::pushParent(Element& parent)
pushParentStackFrame(parent);
}
-static inline void collectDescendantSelectorIdentifierHashes(const CSSSelector* selector, unsigned*& hash)
+static inline void collectDescendantSelectorIdentifierHashes(const CSSSelector& selector, unsigned*& hash)
{
- switch (selector->m_match) {
+ switch (selector.match()) {
case CSSSelector::Id:
- if (!selector->value().isEmpty())
- (*hash++) = selector->value().impl()->existingHash() * IdAttributeSalt;
+ if (!selector.value().isEmpty())
+ (*hash++) = selector.value().impl()->existingHash() * IdAttributeSalt;
break;
case CSSSelector::Class:
- if (!selector->value().isEmpty())
- (*hash++) = selector->value().impl()->existingHash() * ClassAttributeSalt;
+ if (!selector.value().isEmpty())
+ (*hash++) = selector.value().impl()->existingHash() * ClassAttributeSalt;
break;
case CSSSelector::Tag:
- if (selector->tagQName().localName() != starAtom)
- (*hash++) = selector->tagQName().localName().impl()->existingHash() * TagNameSalt;
+ if (selector.tagQName().localName() != starAtom)
+ (*hash++) = selector.tagQName().localName().impl()->existingHash() * TagNameSalt;
break;
default:
break;
}
}
-void SelectorFilter::collectIdentifierHashes(const CSSSelector* selector, unsigned* identifierHashes, unsigned maximumIdentifierCount)
+void SelectorFilter::collectIdentifierHashes(const CSSSelector& selector, unsigned* identifierHashes, unsigned maximumIdentifierCount)
{
unsigned* hash = identifierHashes;
unsigned* end = identifierHashes + maximumIdentifierCount;
- CSSSelector::Relation relation = selector->relation();
- bool relationIsAffectedByPseudoContent = selector->relationIsAffectedByPseudoContent();
+ CSSSelector::Relation relation = selector.relation();
+ bool relationIsAffectedByPseudoContent = selector.relationIsAffectedByPseudoContent();
// Skip the topmost selector. It is handled quickly by the rule hashes.
bool skipOverSubselectors = true;
- for (selector = selector->tagHistory(); selector; selector = selector->tagHistory()) {
+ for (const CSSSelector* current = selector.tagHistory(); current; current = current->tagHistory()) {
// Only collect identifiers that match ancestors.
switch (relation) {
case CSSSelector::SubSelector:
if (!skipOverSubselectors)
- collectDescendantSelectorIdentifierHashes(selector, hash);
+ collectDescendantSelectorIdentifierHashes(*current, hash);
break;
case CSSSelector::DirectAdjacent:
case CSSSelector::IndirectAdjacent:
- case CSSSelector::ShadowPseudo:
skipOverSubselectors = true;
break;
case CSSSelector::Descendant:
@@ -157,16 +156,16 @@ void SelectorFilter::collectIdentifierHashes(const CSSSelector* selector, unsign
return;
}
// Fall through.
- case CSSSelector::ChildTree:
- case CSSSelector::DescendantTree:
+ case CSSSelector::ShadowPseudo:
+ case CSSSelector::ShadowDeep:
skipOverSubselectors = false;
- collectDescendantSelectorIdentifierHashes(selector, hash);
+ collectDescendantSelectorIdentifierHashes(*current, hash);
break;
}
if (hash == end)
return;
- relation = selector->relation();
- relationIsAffectedByPseudoContent = selector->relationIsAffectedByPseudoContent();
+ relation = current->relation();
+ relationIsAffectedByPseudoContent = current->relationIsAffectedByPseudoContent();
}
*hash = 0;
}
diff --git a/chromium/third_party/WebKit/Source/core/css/SelectorFilter.h b/chromium/third_party/WebKit/Source/core/css/SelectorFilter.h
index 905edb6dd30..8a2e85280c1 100644
--- a/chromium/third_party/WebKit/Source/core/css/SelectorFilter.h
+++ b/chromium/third_party/WebKit/Source/core/css/SelectorFilter.h
@@ -50,7 +50,7 @@ public:
template <unsigned maximumIdentifierCount>
inline bool fastRejectSelector(const unsigned* identifierHashes) const;
- static void collectIdentifierHashes(const CSSSelector*, unsigned* identifierHashes, unsigned maximumIdentifierCount);
+ static void collectIdentifierHashes(const CSSSelector&, unsigned* identifierHashes, unsigned maximumIdentifierCount);
private:
struct ParentStackFrame {
diff --git a/chromium/third_party/WebKit/Source/core/css/SiblingTraversalStrategies.h b/chromium/third_party/WebKit/Source/core/css/SiblingTraversalStrategies.h
index b082fa6df0e..dce3c41af18 100644
--- a/chromium/third_party/WebKit/Source/core/css/SiblingTraversalStrategies.h
+++ b/chromium/third_party/WebKit/Source/core/css/SiblingTraversalStrategies.h
@@ -30,63 +30,64 @@
#define SiblingTraversalStrategies_h
#include "core/dom/Element.h"
+#include "core/dom/ElementTraversal.h"
#include "core/rendering/style/RenderStyle.h"
namespace WebCore {
struct DOMSiblingTraversalStrategy {
- bool isFirstChild(Element*) const;
- bool isLastChild(Element*) const;
- bool isFirstOfType(Element*, const QualifiedName&) const;
- bool isLastOfType(Element*, const QualifiedName&) const;
-
- int countElementsBefore(Element*) const;
- int countElementsAfter(Element*) const;
- int countElementsOfTypeBefore(Element*, const QualifiedName&) const;
- int countElementsOfTypeAfter(Element*, const QualifiedName&) const;
+ bool isFirstChild(Element&) const;
+ bool isLastChild(Element&) const;
+ bool isFirstOfType(Element&, const QualifiedName&) const;
+ bool isLastOfType(Element&, const QualifiedName&) const;
+
+ int countElementsBefore(Element&) const;
+ int countElementsAfter(Element&) const;
+ int countElementsOfTypeBefore(Element&, const QualifiedName&) const;
+ int countElementsOfTypeAfter(Element&, const QualifiedName&) const;
};
-inline bool DOMSiblingTraversalStrategy::isFirstChild(Element* element) const
+inline bool DOMSiblingTraversalStrategy::isFirstChild(Element& element) const
{
- return !element->previousElementSibling();
+ return !ElementTraversal::previousSibling(element);
}
-inline bool DOMSiblingTraversalStrategy::isLastChild(Element* element) const
+inline bool DOMSiblingTraversalStrategy::isLastChild(Element& element) const
{
- return !element->nextElementSibling();
+ return !ElementTraversal::nextSibling(element);
}
-inline bool DOMSiblingTraversalStrategy::isFirstOfType(Element* element, const QualifiedName& type) const
+inline bool DOMSiblingTraversalStrategy::isFirstOfType(Element& element, const QualifiedName& type) const
{
- for (const Element* sibling = element->previousElementSibling(); sibling; sibling = sibling->previousElementSibling()) {
+ for (const Element* sibling = ElementTraversal::previousSibling(element); sibling; sibling = ElementTraversal::previousSibling(*sibling)) {
if (sibling->hasTagName(type))
return false;
}
return true;
}
-inline bool DOMSiblingTraversalStrategy::isLastOfType(Element* element, const QualifiedName& type) const
+inline bool DOMSiblingTraversalStrategy::isLastOfType(Element& element, const QualifiedName& type) const
{
- for (const Element* sibling = element->nextElementSibling(); sibling; sibling = sibling->nextElementSibling()) {
+ for (const Element* sibling = ElementTraversal::nextSibling(element); sibling; sibling = ElementTraversal::nextSibling(*sibling)) {
if (sibling->hasTagName(type))
return false;
}
return true;
}
-inline int DOMSiblingTraversalStrategy::countElementsBefore(Element* element) const
+inline int DOMSiblingTraversalStrategy::countElementsBefore(Element& element) const
{
int count = 0;
- for (const Element* sibling = element->previousElementSibling(); sibling; sibling = sibling->previousElementSibling())
+ for (const Element* sibling = ElementTraversal::previousSibling(element); sibling; sibling = ElementTraversal::previousSibling(*sibling))
count++;
return count;
}
-inline int DOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element* element, const QualifiedName& type) const
+inline int DOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element& element, const QualifiedName& type) const
{
int count = 0;
- for (const Element* sibling = element->previousElementSibling(); sibling; sibling = sibling->previousElementSibling()) {
+ for (const Element* sibling = ElementTraversal::previousSibling(element); sibling; sibling = ElementTraversal::previousSibling(*sibling)) {
if (sibling->hasTagName(type))
++count;
}
@@ -94,19 +95,19 @@ inline int DOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element* eleme
return count;
}
-inline int DOMSiblingTraversalStrategy::countElementsAfter(Element* element) const
+inline int DOMSiblingTraversalStrategy::countElementsAfter(Element& element) const
{
int count = 0;
- for (const Element* sibling = element->nextElementSibling(); sibling; sibling = sibling->nextElementSibling())
+ for (const Element* sibling = ElementTraversal::nextSibling(element); sibling; sibling = ElementTraversal::nextSibling(*sibling))
++count;
return count;
}
-inline int DOMSiblingTraversalStrategy::countElementsOfTypeAfter(Element* element, const QualifiedName& type) const
+inline int DOMSiblingTraversalStrategy::countElementsOfTypeAfter(Element& element, const QualifiedName& type) const
{
int count = 0;
- for (const Element* sibling = element->nextElementSibling(); sibling; sibling = sibling->nextElementSibling()) {
+ for (const Element* sibling = ElementTraversal::nextSibling(element); sibling; sibling = ElementTraversal::nextSibling(*sibling)) {
if (sibling->hasTagName(type))
++count;
}
@@ -114,29 +115,31 @@ inline int DOMSiblingTraversalStrategy::countElementsOfTypeAfter(Element* elemen
return count;
}
-struct ShadowDOMSiblingTraversalStrategy {
- ShadowDOMSiblingTraversalStrategy(const Vector<Node*, 32>& siblings, int nth)
+class ShadowDOMSiblingTraversalStrategy FINAL {
+ STACK_ALLOCATED();
+public:
+ ShadowDOMSiblingTraversalStrategy(const WillBeHeapVector<RawPtrWillBeMember<Node>, 32>& siblings, int nth)
: m_siblings(siblings)
, m_nth(nth)
{
}
- bool isFirstChild(Element*) const;
- bool isLastChild(Element*) const;
- bool isFirstOfType(Element*, const QualifiedName&) const;
- bool isLastOfType(Element*, const QualifiedName&) const;
+ bool isFirstChild(Element&) const;
+ bool isLastChild(Element&) const;
+ bool isFirstOfType(Element&, const QualifiedName&) const;
+ bool isLastOfType(Element&, const QualifiedName&) const;
- int countElementsBefore(Element*) const;
- int countElementsAfter(Element*) const;
- int countElementsOfTypeBefore(Element*, const QualifiedName&) const;
- int countElementsOfTypeAfter(Element*, const QualifiedName&) const;
+ int countElementsBefore(Element&) const;
+ int countElementsAfter(Element&) const;
+ int countElementsOfTypeBefore(Element&, const QualifiedName&) const;
+ int countElementsOfTypeAfter(Element&, const QualifiedName&) const;
private:
- const Vector<Node*, 32>& m_siblings;
+ const WillBeHeapVector<RawPtrWillBeMember<Node>, 32>& m_siblings;
int m_nth;
};
-inline bool ShadowDOMSiblingTraversalStrategy::isFirstChild(Element* element) const
+inline bool ShadowDOMSiblingTraversalStrategy::isFirstChild(Element& element) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -148,7 +151,7 @@ inline bool ShadowDOMSiblingTraversalStrategy::isFirstChild(Element* element) co
return true;
}
-inline bool ShadowDOMSiblingTraversalStrategy::isLastChild(Element* element) const
+inline bool ShadowDOMSiblingTraversalStrategy::isLastChild(Element& element) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -160,7 +163,7 @@ inline bool ShadowDOMSiblingTraversalStrategy::isLastChild(Element* element) con
return true;
}
-inline bool ShadowDOMSiblingTraversalStrategy::isFirstOfType(Element* element, const QualifiedName& type) const
+inline bool ShadowDOMSiblingTraversalStrategy::isFirstOfType(Element& element, const QualifiedName& type) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -172,7 +175,7 @@ inline bool ShadowDOMSiblingTraversalStrategy::isFirstOfType(Element* element, c
return true;
}
-inline bool ShadowDOMSiblingTraversalStrategy::isLastOfType(Element* element, const QualifiedName& type) const
+inline bool ShadowDOMSiblingTraversalStrategy::isLastOfType(Element& element, const QualifiedName& type) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -184,7 +187,7 @@ inline bool ShadowDOMSiblingTraversalStrategy::isLastOfType(Element* element, co
return true;
}
-inline int ShadowDOMSiblingTraversalStrategy::countElementsBefore(Element* element) const
+inline int ShadowDOMSiblingTraversalStrategy::countElementsBefore(Element& element) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -197,7 +200,7 @@ inline int ShadowDOMSiblingTraversalStrategy::countElementsBefore(Element* eleme
return count;
}
-inline int ShadowDOMSiblingTraversalStrategy::countElementsAfter(Element* element) const
+inline int ShadowDOMSiblingTraversalStrategy::countElementsAfter(Element& element) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -210,7 +213,7 @@ inline int ShadowDOMSiblingTraversalStrategy::countElementsAfter(Element* elemen
return count;
}
-inline int ShadowDOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element* element, const QualifiedName& type) const
+inline int ShadowDOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element& element, const QualifiedName& type) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
@@ -223,7 +226,7 @@ inline int ShadowDOMSiblingTraversalStrategy::countElementsOfTypeBefore(Element*
return count;
}
-inline int ShadowDOMSiblingTraversalStrategy::countElementsOfTypeAfter(Element* element, const QualifiedName& type) const
+inline int ShadowDOMSiblingTraversalStrategy::countElementsOfTypeAfter(Element& element, const QualifiedName& type) const
{
ASSERT(element == toElement(m_siblings[m_nth]));
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleColor.h b/chromium/third_party/WebKit/Source/core/css/StyleColor.h
index 1f58584f9a9..3c26609cb20 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleColor.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleColor.h
@@ -32,79 +32,30 @@
#define StyleColor_h
#include "platform/graphics/Color.h"
-#include "wtf/FastAllocBase.h"
namespace WebCore {
class StyleColor {
- WTF_MAKE_FAST_ALLOCATED;
public:
- StyleColor()
- : m_color()
- , m_valid(false)
- , m_currentColor(false) { }
- StyleColor(Color color)
- : m_color(color)
- , m_valid(true)
- , m_currentColor(false) { }
- StyleColor(RGBA32 color, bool valid = true, bool currentColor = false)
- : m_color(color)
- , m_valid(valid)
- , m_currentColor(currentColor) { }
- StyleColor(int r, int g, int b)
- : m_color(Color(r, g, b))
- , m_valid(true)
- , m_currentColor(false) { }
- StyleColor(int r, int g, int b, int a)
- : m_color(Color(r, g, b, a))
- , m_valid(true)
- , m_currentColor(false) { }
- StyleColor(const StyleColor& other)
- : m_color(other.m_color)
- , m_valid(other.m_valid)
- , m_currentColor(other.m_currentColor) { }
+ StyleColor(Color color) : m_color(color), m_currentColor(false) { }
+ static StyleColor currentColor() { return StyleColor(); }
- Color color() const { return m_color; }
- bool isValid() const { return m_valid; }
bool isCurrentColor() const { return m_currentColor; }
- bool hasAlpha() const { return m_color.hasAlpha(); }
+ Color color() const { ASSERT(!isCurrentColor()); return m_color; }
- void setRGB(int r, int g, int b)
- {
- m_color.setRGB(r, g, b);
- m_valid = true;
- m_currentColor = false;
- }
-
- RGBA32 rgb() const { return m_color.rgb(); } // Preserve the alpha.
- int red() const { return m_color.red(); }
- int green() const { return m_color.green(); }
- int blue() const { return m_color.blue(); }
- int alpha() const { return m_color.alpha(); }
-
- static const StyleColor invalid()
- {
- return StyleColor(false, false);
- }
- static const StyleColor currentColor()
- {
- return StyleColor(true, true);
- }
+ Color resolve(Color currentColor) const { return m_currentColor ? currentColor : m_color; }
private:
- StyleColor(bool invalid, bool currentColor)
- : m_color()
- , m_valid(invalid)
- , m_currentColor(currentColor) { }
-
+ StyleColor() : m_currentColor(true) { }
Color m_color;
- bool m_valid;
bool m_currentColor;
};
inline bool operator==(const StyleColor& a, const StyleColor& b)
{
- return a.rgb() == b.rgb() && a.isValid() == b.isValid() && a.isCurrentColor() == b.isCurrentColor();
+ if (a.isCurrentColor() || b.isCurrentColor())
+ return a.isCurrentColor() && b.isCurrentColor();
+ return a.color() == b.color();
}
inline bool operator!=(const StyleColor& a, const StyleColor& b)
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleMedia.cpp b/chromium/third_party/WebKit/Source/core/css/StyleMedia.cpp
index 791ef27328f..c18d26c592c 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleMedia.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StyleMedia.cpp
@@ -28,14 +28,13 @@
#include "core/css/MediaList.h"
#include "core/css/MediaQueryEvaluator.h"
-#include "core/css/resolver/StyleResolver.h"
#include "core/dom/Document.h"
-#include "core/frame/Frame.h"
#include "core/frame/FrameView.h"
+#include "core/frame/LocalFrame.h"
namespace WebCore {
-StyleMedia::StyleMedia(Frame* frame)
+StyleMedia::StyleMedia(LocalFrame* frame)
: DOMWindowProperty(frame)
{
}
@@ -60,14 +59,11 @@ bool StyleMedia::matchMedium(const String& query) const
if (!documentElement)
return false;
- StyleResolver& styleResolver = document->ensureStyleResolver();
- RefPtr<RenderStyle> rootStyle = styleResolver.styleForElement(documentElement, 0 /*defaultParent*/, DisallowStyleSharing, MatchOnlyUserAgentRules);
-
- RefPtr<MediaQuerySet> media = MediaQuerySet::create();
+ RefPtrWillBeRawPtr<MediaQuerySet> media = MediaQuerySet::create();
if (!media->set(query))
return false;
- MediaQueryEvaluator screenEval(type(), m_frame, rootStyle.get());
+ MediaQueryEvaluator screenEval(type(), m_frame);
return screenEval.eval(media.get());
}
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleMedia.h b/chromium/third_party/WebKit/Source/core/css/StyleMedia.h
index e2cd69be117..c08bd104930 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleMedia.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleMedia.h
@@ -28,22 +28,25 @@
#define StyleMedia_h
#include "core/frame/DOMWindowProperty.h"
+#include "platform/heap/Handle.h"
#include "wtf/RefCounted.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
-class Frame;
+class LocalFrame;
-class StyleMedia : public RefCounted<StyleMedia>, public DOMWindowProperty {
+class StyleMedia : public RefCountedWillBeGarbageCollectedFinalized<StyleMedia>, public DOMWindowProperty {
public:
- static PassRefPtr<StyleMedia> create(Frame* frame) { return adoptRef(new StyleMedia(frame));}
+ static PassRefPtrWillBeRawPtr<StyleMedia> create(LocalFrame* frame) { return adoptRefWillBeNoop(new StyleMedia(frame));}
AtomicString type() const;
bool matchMedium(const String&) const;
+ void trace(Visitor*) { }
+
private:
- explicit StyleMedia(Frame*);
+ explicit StyleMedia(LocalFrame*);
};
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleMedia.idl b/chromium/third_party/WebKit/Source/core/css/StyleMedia.idl
index 370eee8f913..b897eb0690b 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleMedia.idl
+++ b/chromium/third_party/WebKit/Source/core/css/StyleMedia.idl
@@ -25,7 +25,8 @@
*/
[
- NoInterfaceObject
+ NoInterfaceObject,
+ WillBeGarbageCollected
] interface StyleMedia {
readonly attribute DOMString type;
boolean matchMedium([Default=Undefined] optional DOMString mediaquery);
diff --git a/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.cpp b/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.cpp
index 825781430ab..4d00705a09c 100644
--- a/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.cpp
@@ -23,14 +23,12 @@
#include "config.h"
#include "core/css/StylePropertySerializer.h"
-#include "CSSValueKeywords.h"
-#include "StylePropertyShorthand.h"
+#include "core/CSSValueKeywords.h"
+#include "core/StylePropertyShorthand.h"
#include "core/css/RuntimeCSSEnabled.h"
#include "wtf/BitArray.h"
#include "wtf/text/StringBuilder.h"
-using namespace std;
-
namespace WebCore {
static bool isInitialOrInherit(const String& value)
@@ -45,14 +43,23 @@ StylePropertySerializer::StylePropertySerializer(const StylePropertySet& propert
{
}
-String StylePropertySerializer::asText() const
+String StylePropertySerializer::getPropertyText(CSSPropertyID propertyID, const String& value, bool isImportant, bool isNotFirstDecl) const
{
StringBuilder result;
+ if (isNotFirstDecl)
+ result.append(' ');
+ result.append(getPropertyName(propertyID));
+ result.appendLiteral(": ");
+ result.append(value);
+ if (isImportant)
+ result.appendLiteral(" !important");
+ result.append(';');
+ return result.toString();
+}
- int positionXPropertyIndex = -1;
- int positionYPropertyIndex = -1;
- int repeatXPropertyIndex = -1;
- int repeatYPropertyIndex = -1;
+String StylePropertySerializer::asText() const
+{
+ StringBuilder result;
BitArray<numCSSProperties> shorthandPropertyUsed;
BitArray<numCSSProperties> shorthandPropertyAppeared;
@@ -69,22 +76,17 @@ String StylePropertySerializer::asText() const
String value;
switch (propertyID) {
- case CSSPropertyVariable:
- if (numDecls++)
- result.append(' ');
- result.append(property.cssText());
- continue;
+ case CSSPropertyBackgroundAttachment:
+ case CSSPropertyBackgroundClip:
+ case CSSPropertyBackgroundColor:
+ case CSSPropertyBackgroundImage:
+ case CSSPropertyBackgroundOrigin:
case CSSPropertyBackgroundPositionX:
- positionXPropertyIndex = n;
- continue;
case CSSPropertyBackgroundPositionY:
- positionYPropertyIndex = n;
- continue;
+ case CSSPropertyBackgroundSize:
case CSSPropertyBackgroundRepeatX:
- repeatXPropertyIndex = n;
- continue;
case CSSPropertyBackgroundRepeatY:
- repeatYPropertyIndex = n;
+ shorthandPropertyAppeared.set(CSSPropertyBackground - firstCSSProperty);
continue;
case CSSPropertyContent:
if (property.value()->isValueList())
@@ -229,80 +231,11 @@ String StylePropertySerializer::asText() const
if (value == "initial" && !CSSProperty::isInheritedProperty(propertyID))
continue;
- if (numDecls++)
- result.append(' ');
- result.append(getPropertyName(propertyID));
- result.appendLiteral(": ");
- result.append(value);
- if (property.isImportant())
- result.appendLiteral(" !important");
- result.append(';');
- }
-
- // FIXME: This is a not-so-nice way to turn x/y positions into single background-position in output.
- // It is required because background-position-x/y are non-standard properties and WebKit generated output
- // would not work in Firefox (<rdar://problem/5143183>)
- // It would be a better solution if background-position was CSS_PAIR.
- if (positionXPropertyIndex != -1 && positionYPropertyIndex != -1 && m_propertySet.propertyAt(positionXPropertyIndex).isImportant() == m_propertySet.propertyAt(positionYPropertyIndex).isImportant()) {
- StylePropertySet::PropertyReference positionXProperty = m_propertySet.propertyAt(positionXPropertyIndex);
- StylePropertySet::PropertyReference positionYProperty = m_propertySet.propertyAt(positionYPropertyIndex);
-
- if (numDecls++)
- result.append(' ');
- result.appendLiteral("background-position: ");
- if (positionXProperty.value()->isValueList() || positionYProperty.value()->isValueList())
- result.append(getLayeredShorthandValue(backgroundPositionShorthand()));
- else {
- result.append(positionXProperty.value()->cssText());
- result.append(' ');
- result.append(positionYProperty.value()->cssText());
- }
- if (positionXProperty.isImportant())
- result.appendLiteral(" !important");
- result.append(';');
- } else {
- if (positionXPropertyIndex != -1) {
- if (numDecls++)
- result.append(' ');
- result.append(m_propertySet.propertyAt(positionXPropertyIndex).cssText());
- }
- if (positionYPropertyIndex != -1) {
- if (numDecls++)
- result.append(' ');
- result.append(m_propertySet.propertyAt(positionYPropertyIndex).cssText());
- }
+ result.append(getPropertyText(propertyID, value, property.isImportant(), numDecls++));
}
- // FIXME: We need to do the same for background-repeat.
- if (repeatXPropertyIndex != -1 && repeatYPropertyIndex != -1 && m_propertySet.propertyAt(repeatXPropertyIndex).isImportant() == m_propertySet.propertyAt(repeatYPropertyIndex).isImportant()) {
- StylePropertySet::PropertyReference repeatXProperty = m_propertySet.propertyAt(repeatXPropertyIndex);
- StylePropertySet::PropertyReference repeatYProperty = m_propertySet.propertyAt(repeatYPropertyIndex);
-
- if (numDecls++)
- result.append(' ');
- result.appendLiteral("background-repeat: ");
- if (repeatXProperty.value()->isValueList() || repeatYProperty.value()->isValueList())
- result.append(getLayeredShorthandValue(backgroundRepeatShorthand()));
- else {
- result.append(repeatXProperty.value()->cssText());
- result.append(' ');
- result.append(repeatYProperty.value()->cssText());
- }
- if (repeatXProperty.isImportant())
- result.appendLiteral(" !important");
- result.append(';');
- } else {
- if (repeatXPropertyIndex != -1) {
- if (numDecls++)
- result.append(' ');
- result.append(m_propertySet.propertyAt(repeatXPropertyIndex).cssText());
- }
- if (repeatYPropertyIndex != -1) {
- if (numDecls++)
- result.append(' ');
- result.append(m_propertySet.propertyAt(repeatYPropertyIndex).cssText());
- }
- }
+ if (shorthandPropertyAppeared.get(CSSPropertyBackground - firstCSSProperty))
+ appendBackgroundPropertyAsText(result, numDecls);
ASSERT(!numDecls ^ !result.isEmpty());
return result.toString();
@@ -319,7 +252,7 @@ String StylePropertySerializer::getPropertyValue(CSSPropertyID propertyID) const
case CSSPropertyBackgroundPosition:
return getLayeredShorthandValue(backgroundPositionShorthand());
case CSSPropertyBackgroundRepeat:
- return getLayeredShorthandValue(backgroundRepeatShorthand());
+ return backgroundRepeatPropertyValue();
case CSSPropertyBackground:
return getLayeredShorthandValue(backgroundShorthand());
case CSSPropertyBorder:
@@ -378,6 +311,7 @@ String StylePropertySerializer::getPropertyValue(CSSPropertyID propertyID) const
return getShorthandValue(webkitTextEmphasisShorthand());
case CSSPropertyWebkitTextStroke:
return getShorthandValue(webkitTextStrokeShorthand());
+ case CSSPropertyTransformOrigin:
case CSSPropertyWebkitTransformOrigin:
return getShorthandValue(webkitTransformOriginShorthand());
case CSSPropertyWebkitTransition:
@@ -385,7 +319,7 @@ String StylePropertySerializer::getPropertyValue(CSSPropertyID propertyID) const
case CSSPropertyWebkitAnimation:
return getLayeredShorthandValue(webkitAnimationShorthand());
case CSSPropertyMarker: {
- RefPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(CSSPropertyMarkerStart);
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(CSSPropertyMarkerStart);
if (value)
return value->cssText();
return String();
@@ -399,8 +333,8 @@ String StylePropertySerializer::getPropertyValue(CSSPropertyID propertyID) const
String StylePropertySerializer::borderSpacingValue(const StylePropertyShorthand& shorthand) const
{
- RefPtr<CSSValue> horizontalValue = m_propertySet.getPropertyCSSValue(shorthand.properties()[0]);
- RefPtr<CSSValue> verticalValue = m_propertySet.getPropertyCSSValue(shorthand.properties()[1]);
+ RefPtrWillBeRawPtr<CSSValue> horizontalValue = m_propertySet.getPropertyCSSValue(shorthand.properties()[0]);
+ RefPtrWillBeRawPtr<CSSValue> verticalValue = m_propertySet.getPropertyCSSValue(shorthand.properties()[1]);
// While standard border-spacing property does not allow specifying border-spacing-vertical without
// specifying border-spacing-horizontal <http://www.w3.org/TR/CSS21/tables.html#separated-borders>,
@@ -539,7 +473,7 @@ String StylePropertySerializer::getLayeredShorthandValue(const StylePropertyShor
const unsigned size = shorthand.length();
// Begin by collecting the properties into an array.
- Vector< RefPtr<CSSValue> > values(size);
+ WillBeHeapVector<RefPtrWillBeMember<CSSValue> > values(size);
size_t numLayers = 0;
for (unsigned i = 0; i < size; ++i) {
@@ -547,9 +481,10 @@ String StylePropertySerializer::getLayeredShorthandValue(const StylePropertyShor
if (values[i]) {
if (values[i]->isBaseValueList()) {
CSSValueList* valueList = toCSSValueList(values[i].get());
- numLayers = max(valueList->length(), numLayers);
- } else
- numLayers = max<size_t>(1U, numLayers);
+ numLayers = std::max(valueList->length(), numLayers);
+ } else {
+ numLayers = std::max<size_t>(1U, numLayers);
+ }
}
}
@@ -565,7 +500,7 @@ String StylePropertySerializer::getLayeredShorthandValue(const StylePropertyShor
bool useSingleWordShorthand = false;
bool foundPositionYCSSProperty = false;
for (unsigned j = 0; j < size; j++) {
- RefPtr<CSSValue> value;
+ RefPtrWillBeRawPtr<CSSValue> value = nullptr;
if (values[j]) {
if (values[j]->isBaseValueList())
value = toCSSValueList(values[j].get())->item(i);
@@ -575,9 +510,11 @@ String StylePropertySerializer::getLayeredShorthandValue(const StylePropertyShor
// Color only belongs in the last layer.
if (shorthand.properties()[j] == CSSPropertyBackgroundColor) {
if (i != numLayers - 1)
- value = 0;
- } else if (i) // Other singletons only belong in the first layer.
- value = 0;
+ value = nullptr;
+ } else if (i) {
+ // Other singletons only belong in the first layer.
+ value = nullptr;
+ }
}
}
@@ -590,8 +527,8 @@ String StylePropertySerializer::getLayeredShorthandValue(const StylePropertyShor
// BUG 49055: make sure the value was not reset in the layer check just above.
if ((j < size - 1 && shorthand.properties()[j + 1] == CSSPropertyBackgroundRepeatY && value)
|| (j < size - 1 && shorthand.properties()[j + 1] == CSSPropertyWebkitMaskRepeatY && value)) {
- RefPtr<CSSValue> yValue;
- RefPtr<CSSValue> nextValue = values[j + 1];
+ RefPtrWillBeRawPtr<CSSValue> yValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> nextValue = values[j + 1];
if (nextValue->isValueList())
yValue = toCSSValueList(nextValue.get())->itemWithoutBoundsCheck(i);
else
@@ -687,7 +624,7 @@ String StylePropertySerializer::getShorthandValue(const StylePropertyShorthand&
StringBuilder result;
for (unsigned i = 0; i < shorthand.length(); ++i) {
if (!m_propertySet.isPropertyImplicit(shorthand.properties()[i])) {
- RefPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(shorthand.properties()[i]);
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(shorthand.properties()[i]);
if (!value)
return String();
String valueText = value->cssText();
@@ -716,7 +653,7 @@ String StylePropertySerializer::getCommonValue(const StylePropertyShorthand& sho
String res;
bool lastPropertyWasImportant = false;
for (unsigned i = 0; i < shorthand.length(); ++i) {
- RefPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(shorthand.properties()[i]);
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(shorthand.properties()[i]);
// FIXME: CSSInitialValue::cssText should generate the right value.
if (!value)
return String();
@@ -764,4 +701,172 @@ String StylePropertySerializer::borderPropertyValue(CommonValueMode valueMode) c
return result.isEmpty() ? String() : result.toString();
}
+static void appendBackgroundRepeatValue(StringBuilder& builder, const CSSValue& repeatXCSSValue, const CSSValue& repeatYCSSValue)
+{
+ // FIXME: Ensure initial values do not appear in CSS_VALUE_LISTS.
+ DEFINE_STATIC_REF_WILL_BE_PERSISTENT(CSSPrimitiveValue, initialRepeatValue, (CSSPrimitiveValue::create(CSSValueRepeat)));
+ const CSSPrimitiveValue& repeatX = repeatXCSSValue.isInitialValue() ? *initialRepeatValue : toCSSPrimitiveValue(repeatXCSSValue);
+ const CSSPrimitiveValue& repeatY = repeatYCSSValue.isInitialValue() ? *initialRepeatValue : toCSSPrimitiveValue(repeatYCSSValue);
+ CSSValueID repeatXValueId = repeatX.getValueID();
+ CSSValueID repeatYValueId = repeatY.getValueID();
+ if (repeatXValueId == repeatYValueId) {
+ builder.append(repeatX.cssText());
+ } else if (repeatXValueId == CSSValueNoRepeat && repeatYValueId == CSSValueRepeat) {
+ builder.append("repeat-y");
+ } else if (repeatXValueId == CSSValueRepeat && repeatYValueId == CSSValueNoRepeat) {
+ builder.append("repeat-x");
+ } else {
+ builder.append(repeatX.cssText());
+ builder.append(" ");
+ builder.append(repeatY.cssText());
+ }
+}
+
+String StylePropertySerializer::backgroundRepeatPropertyValue() const
+{
+ RefPtrWillBeRawPtr<CSSValue> repeatX = m_propertySet.getPropertyCSSValue(CSSPropertyBackgroundRepeatX);
+ RefPtrWillBeRawPtr<CSSValue> repeatY = m_propertySet.getPropertyCSSValue(CSSPropertyBackgroundRepeatY);
+ if (!repeatX || !repeatY)
+ return String();
+ if (m_propertySet.propertyIsImportant(CSSPropertyBackgroundRepeatX) != m_propertySet.propertyIsImportant(CSSPropertyBackgroundRepeatY))
+ return String();
+ if (repeatX->cssValueType() == repeatY->cssValueType()
+ && (repeatX->cssValueType() == CSSValue::CSS_INITIAL || repeatX->cssValueType() == CSSValue::CSS_INHERIT)) {
+ return repeatX->cssText();
+ }
+
+ RefPtrWillBeRawPtr<CSSValueList> repeatXList;
+ if (repeatX->cssValueType() == CSSValue::CSS_PRIMITIVE_VALUE) {
+ repeatXList = CSSValueList::createCommaSeparated();
+ repeatXList->append(repeatX);
+ } else if (repeatX->cssValueType() == CSSValue::CSS_VALUE_LIST) {
+ repeatXList = toCSSValueList(repeatX.get());
+ } else {
+ return String();
+ }
+
+ RefPtrWillBeRawPtr<CSSValueList> repeatYList;
+ if (repeatY->cssValueType() == CSSValue::CSS_PRIMITIVE_VALUE) {
+ repeatYList = CSSValueList::createCommaSeparated();
+ repeatYList->append(repeatY);
+ } else if (repeatY->cssValueType() == CSSValue::CSS_VALUE_LIST) {
+ repeatYList = toCSSValueList(repeatY.get());
+ } else {
+ return String();
+ }
+
+ size_t shorthandLength = lowestCommonMultiple(repeatXList->length(), repeatYList->length());
+ StringBuilder builder;
+ for (size_t i = 0; i < shorthandLength; ++i) {
+ if (i)
+ builder.append(", ");
+ appendBackgroundRepeatValue(builder,
+ *repeatXList->item(i % repeatXList->length()),
+ *repeatYList->item(i % repeatYList->length()));
+ }
+ return builder.toString();
+}
+
+void StylePropertySerializer::appendBackgroundPropertyAsText(StringBuilder& result, unsigned& numDecls) const
+{
+ if (isPropertyShorthandAvailable(backgroundShorthand())) {
+ String backgroundValue = getPropertyValue(CSSPropertyBackground);
+ bool isImportant = m_propertySet.propertyIsImportant(CSSPropertyBackgroundImage);
+ result.append(getPropertyText(CSSPropertyBackground, backgroundValue, isImportant, numDecls++));
+ return;
+ }
+ if (shorthandHasOnlyInitialOrInheritedValue(backgroundShorthand())) {
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(CSSPropertyBackgroundImage);
+ bool isImportant = m_propertySet.propertyIsImportant(CSSPropertyBackgroundImage);
+ result.append(getPropertyText(CSSPropertyBackground, value->cssText(), isImportant, numDecls++));
+ return;
+ }
+
+ // backgroundShorthandProperty without layered shorhand properties
+ const CSSPropertyID backgroundPropertyIds[] = {
+ CSSPropertyBackgroundImage,
+ CSSPropertyBackgroundAttachment,
+ CSSPropertyBackgroundColor,
+ CSSPropertyBackgroundSize,
+ CSSPropertyBackgroundOrigin,
+ CSSPropertyBackgroundClip
+ };
+
+ for (unsigned i = 0; i < WTF_ARRAY_LENGTH(backgroundPropertyIds); ++i) {
+ CSSPropertyID propertyID = backgroundPropertyIds[i];
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(propertyID);
+ if (!value)
+ continue;
+ result.append(getPropertyText(propertyID, value->cssText(), m_propertySet.propertyIsImportant(propertyID), numDecls++));
+ }
+
+ // FIXME: This is a not-so-nice way to turn x/y positions into single background-position in output.
+ // It is required because background-position-x/y are non-standard properties and WebKit generated output
+ // would not work in Firefox (<rdar://problem/5143183>)
+ // It would be a better solution if background-position was CSS_PAIR.
+ if (shorthandHasOnlyInitialOrInheritedValue(backgroundPositionShorthand())) {
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(CSSPropertyBackgroundPositionX);
+ bool isImportant = m_propertySet.propertyIsImportant(CSSPropertyBackgroundPositionX);
+ result.append(getPropertyText(CSSPropertyBackgroundPosition, value->cssText(), isImportant, numDecls++));
+ } else if (isPropertyShorthandAvailable(backgroundPositionShorthand())) {
+ String positionValue = m_propertySet.getPropertyValue(CSSPropertyBackgroundPosition);
+ bool isImportant = m_propertySet.propertyIsImportant(CSSPropertyBackgroundPositionX);
+ if (!positionValue.isNull())
+ result.append(getPropertyText(CSSPropertyBackgroundPosition, positionValue, isImportant, numDecls++));
+ } else {
+ // should check background-position-x or background-position-y.
+ if (RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(CSSPropertyBackgroundPositionX)) {
+ if (!value->isImplicitInitialValue()) {
+ bool isImportant = m_propertySet.propertyIsImportant(CSSPropertyBackgroundPositionX);
+ result.append(getPropertyText(CSSPropertyBackgroundPositionX, value->cssText(), isImportant, numDecls++));
+ }
+ }
+ if (RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(CSSPropertyBackgroundPositionY)) {
+ if (!value->isImplicitInitialValue()) {
+ bool isImportant = m_propertySet.propertyIsImportant(CSSPropertyBackgroundPositionY);
+ result.append(getPropertyText(CSSPropertyBackgroundPositionY, value->cssText(), isImportant, numDecls++));
+ }
+ }
+ }
+
+ String repeatValue = m_propertySet.getPropertyValue(CSSPropertyBackgroundRepeat);
+ if (!repeatValue.isNull())
+ result.append(getPropertyText(CSSPropertyBackgroundRepeat, repeatValue, m_propertySet.propertyIsImportant(CSSPropertyBackgroundRepeatX), numDecls++));
+}
+
+bool StylePropertySerializer::isPropertyShorthandAvailable(const StylePropertyShorthand& shorthand) const
+{
+ ASSERT(shorthand.length() > 0);
+
+ bool isImportant = m_propertySet.propertyIsImportant(shorthand.properties()[0]);
+ for (unsigned i = 0; i < shorthand.length(); ++i) {
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(shorthand.properties()[i]);
+ if (!value || (value->isInitialValue() && !value->isImplicitInitialValue()) || value->isInheritedValue())
+ return false;
+ if (isImportant != m_propertySet.propertyIsImportant(shorthand.properties()[i]))
+ return false;
+ }
+ return true;
+}
+
+bool StylePropertySerializer::shorthandHasOnlyInitialOrInheritedValue(const StylePropertyShorthand& shorthand) const
+{
+ ASSERT(shorthand.length() > 0);
+ bool isImportant = m_propertySet.propertyIsImportant(shorthand.properties()[0]);
+ bool isInitialValue = true;
+ bool isInheritedValue = true;
+ for (unsigned i = 0; i < shorthand.length(); ++i) {
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet.getPropertyCSSValue(shorthand.properties()[i]);
+ if (!value)
+ return false;
+ if (!value->isInitialValue())
+ isInitialValue = false;
+ if (!value->isInheritedValue())
+ isInheritedValue = false;
+ if (isImportant != m_propertySet.propertyIsImportant(shorthand.properties()[i]))
+ return false;
+ }
+ return isInitialValue || isInheritedValue;
+}
+
}
diff --git a/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.h b/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.h
index 55d1027b5bd..ed9bc6ab478 100644
--- a/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.h
+++ b/chromium/third_party/WebKit/Source/core/css/StylePropertySerializer.h
@@ -45,6 +45,11 @@ private:
String getShorthandValue(const StylePropertyShorthand&) const;
String fontValue() const;
void appendFontLonghandValueIfExplicit(CSSPropertyID, StringBuilder& result, String& value) const;
+ String backgroundRepeatPropertyValue() const;
+ String getPropertyText(CSSPropertyID, const String& value, bool isImportant, bool isNotFirstDecl) const;
+ bool isPropertyShorthandAvailable(const StylePropertyShorthand&) const;
+ bool shorthandHasOnlyInitialOrInheritedValue(const StylePropertyShorthand&) const;
+ void appendBackgroundPropertyAsText(StringBuilder& result, unsigned& numDecls) const;
const StylePropertySet& m_propertySet;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/StylePropertySet.cpp b/chromium/third_party/WebKit/Source/core/css/StylePropertySet.cpp
index c7e0ae63811..2581c01e911 100644
--- a/chromium/third_party/WebKit/Source/core/css/StylePropertySet.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StylePropertySet.cpp
@@ -23,14 +23,14 @@
#include "config.h"
#include "core/css/StylePropertySet.h"
-#include "RuntimeEnabledFeatures.h"
-#include "StylePropertyShorthand.h"
-#include "core/css/CSSParser.h"
+#include "core/StylePropertyShorthand.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSValuePool.h"
-#include "core/css/CSSVariableValue.h"
#include "core/css/RuntimeCSSEnabled.h"
#include "core/css/StylePropertySerializer.h"
#include "core/css/StyleSheetContents.h"
+#include "core/frame/UseCounter.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "wtf/text/StringBuilder.h"
#ifndef NDEBUG
@@ -38,8 +38,6 @@
#include <stdio.h>
#endif
-using namespace std;
-
namespace WebCore {
static size_t sizeForImmutableStylePropertySetWithPropertyCount(unsigned count)
@@ -50,8 +48,12 @@ static size_t sizeForImmutableStylePropertySetWithPropertyCount(unsigned count)
PassRefPtr<ImmutableStylePropertySet> ImmutableStylePropertySet::create(const CSSProperty* properties, unsigned count, CSSParserMode cssParserMode)
{
ASSERT(count <= MaxArraySize);
+#if ENABLE(OILPAN)
+ void* slot = Heap::allocate<StylePropertySet>(sizeForImmutableStylePropertySetWithPropertyCount(count));
+#else
void* slot = WTF::fastMalloc(sizeForImmutableStylePropertySetWithPropertyCount(count));
- return adoptRef(new (slot) ImmutableStylePropertySet(properties, count, cssParserMode));
+#endif // ENABLE(OILPAN)
+ return adoptRefWillBeRefCountedGarbageCollected(new (slot) ImmutableStylePropertySet(properties, count, cssParserMode));
}
PassRefPtr<ImmutableStylePropertySet> StylePropertySet::immutableCopyIfNeeded() const
@@ -79,19 +81,47 @@ ImmutableStylePropertySet::ImmutableStylePropertySet(const CSSProperty* properti
: StylePropertySet(cssParserMode, length)
{
StylePropertyMetadata* metadataArray = const_cast<StylePropertyMetadata*>(this->metadataArray());
- CSSValue** valueArray = const_cast<CSSValue**>(this->valueArray());
+ RawPtrWillBeMember<CSSValue>* valueArray = const_cast<RawPtrWillBeMember<CSSValue>*>(this->valueArray());
for (unsigned i = 0; i < m_arraySize; ++i) {
metadataArray[i] = properties[i].metadata();
valueArray[i] = properties[i].value();
+#if !ENABLE(OILPAN)
valueArray[i]->ref();
+#endif
}
}
ImmutableStylePropertySet::~ImmutableStylePropertySet()
{
- CSSValue** valueArray = const_cast<CSSValue**>(this->valueArray());
+#if !ENABLE(OILPAN)
+ RawPtrWillBeMember<CSSValue>* valueArray = const_cast<RawPtrWillBeMember<CSSValue>*>(this->valueArray());
for (unsigned i = 0; i < m_arraySize; ++i)
valueArray[i]->deref();
+#endif
+}
+
+int ImmutableStylePropertySet::findPropertyIndex(CSSPropertyID propertyID) const
+{
+ // Convert here propertyID into an uint16_t to compare it with the metadata's m_propertyID to avoid
+ // the compiler converting it to an int multiple times in the loop.
+ uint16_t id = static_cast<uint16_t>(propertyID);
+ for (int n = m_arraySize - 1 ; n >= 0; --n) {
+ if (metadataArray()[n].m_propertyID == id) {
+ // Only enabled or internal properties should be part of the style.
+ ASSERT(RuntimeCSSEnabled::isCSSPropertyEnabled(propertyID) || isInternalProperty(propertyID));
+ return n;
+ }
+ }
+
+ return -1;
+}
+
+void ImmutableStylePropertySet::traceAfterDispatch(Visitor* visitor)
+{
+ const RawPtrWillBeMember<CSSValue>* values = valueArray();
+ for (unsigned i = 0; i < m_arraySize; i++)
+ visitor->trace(values[i]);
+ StylePropertySet::traceAfterDispatch(visitor);
}
MutableStylePropertySet::MutableStylePropertySet(const StylePropertySet& other)
@@ -108,40 +138,38 @@ MutableStylePropertySet::MutableStylePropertySet(const StylePropertySet& other)
String StylePropertySet::getPropertyValue(CSSPropertyID propertyID) const
{
- RefPtr<CSSValue> value = getPropertyCSSValue(propertyID);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(propertyID);
if (value)
return value->cssText();
return StylePropertySerializer(*this).getPropertyValue(propertyID);
}
-PassRefPtr<CSSValue> StylePropertySet::getPropertyCSSValue(CSSPropertyID propertyID) const
+PassRefPtrWillBeRawPtr<CSSValue> StylePropertySet::getPropertyCSSValue(CSSPropertyID propertyID) const
{
int foundPropertyIndex = findPropertyIndex(propertyID);
if (foundPropertyIndex == -1)
- return 0;
+ return nullptr;
return propertyAt(foundPropertyIndex).value();
}
-unsigned StylePropertySet::variableCount() const
+void StylePropertySet::trace(Visitor* visitor)
{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- unsigned count = 0;
- for (unsigned i = 0; i < propertyCount(); ++i) {
- if (propertyAt(i).id() == CSSPropertyVariable)
- count++;
- }
- return count;
+ if (m_isMutable)
+ toMutableStylePropertySet(this)->traceAfterDispatch(visitor);
+ else
+ toImmutableStylePropertySet(this)->traceAfterDispatch(visitor);
}
-String StylePropertySet::variableValue(const AtomicString& name) const
+#if ENABLE(OILPAN)
+void StylePropertySet::finalizeGarbageCollectedObject()
{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- size_t index = findVariableIndex(name);
- if (index == kNotFound)
- return String();
- return toCSSVariableValue(propertyAt(index).value())->value();
+ if (m_isMutable)
+ toMutableStylePropertySet(this)->~MutableStylePropertySet();
+ else
+ toImmutableStylePropertySet(this)->~ImmutableStylePropertySet();
}
+#endif
bool MutableStylePropertySet::removeShorthandProperty(CSSPropertyID propertyID)
{
@@ -237,10 +265,10 @@ bool MutableStylePropertySet::setProperty(CSSPropertyID propertyID, const String
// When replacing an existing property value, this moves the property to the end of the list.
// Firefox preserves the position, and MSIE moves the property to the beginning.
- return CSSParser::parseValue(this, propertyID, value, important, cssParserMode(), contextStyleSheet);
+ return BisonCSSParser::parseValue(this, propertyID, value, important, cssParserMode(), contextStyleSheet);
}
-void MutableStylePropertySet::setProperty(CSSPropertyID propertyID, PassRefPtr<CSSValue> prpValue, bool important)
+void MutableStylePropertySet::setProperty(CSSPropertyID propertyID, PassRefPtrWillBeRawPtr<CSSValue> prpValue, bool important)
{
StylePropertyShorthand shorthand = shorthandForProperty(propertyID);
if (!shorthand.length()) {
@@ -250,7 +278,7 @@ void MutableStylePropertySet::setProperty(CSSPropertyID propertyID, PassRefPtr<C
removePropertiesInSet(shorthand.properties(), shorthand.length());
- RefPtr<CSSValue> value = prpValue;
+ RefPtrWillBeRawPtr<CSSValue> value = prpValue;
for (unsigned i = 0; i < shorthand.length(); ++i)
m_propertyVector.append(CSSProperty(shorthand.properties()[i], value, important));
}
@@ -279,28 +307,6 @@ unsigned getIndexInShorthandVectorForPrefixingVariant(const CSSProperty& propert
return indexOfShorthandForLonghand(prefixedShorthand, shorthands);
}
-bool MutableStylePropertySet::setVariableValue(const AtomicString& name, const String& value, bool important)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- if (value.isEmpty())
- return removeVariable(name);
-
- size_t index = findVariableIndex(name);
- if (index != kNotFound) {
- const CSSValue* cssValue = m_propertyVector.at(index).value();
- if (toCSSVariableValue(cssValue)->value() == value)
- return false;
- }
-
- CSSProperty property(CSSPropertyVariable, CSSVariableValue::create(name, value), important);
- if (index == kNotFound) {
- m_propertyVector.append(property);
- return true;
- }
- m_propertyVector.at(index) = property;
- return false;
-}
-
void MutableStylePropertySet::appendPrefixingVariantProperty(const CSSProperty& property)
{
m_propertyVector.append(property);
@@ -335,17 +341,17 @@ void MutableStylePropertySet::parseDeclaration(const String& styleDeclaration, S
{
m_propertyVector.clear();
- CSSParserContext context(cssParserMode());
+ CSSParserContext context(cssParserMode(), UseCounter::getFrom(contextStyleSheet));
if (contextStyleSheet) {
context = contextStyleSheet->parserContext();
context.setMode(cssParserMode());
}
- CSSParser parser(context, UseCounter::getFrom(contextStyleSheet));
+ BisonCSSParser parser(context);
parser.parseDeclaration(this, styleDeclaration, 0, contextStyleSheet);
}
-void MutableStylePropertySet::addParsedProperties(const Vector<CSSProperty, 256>& properties)
+void MutableStylePropertySet::addParsedProperties(const WillBeHeapVector<CSSProperty, 256>& properties)
{
m_propertyVector.reserveCapacity(m_propertyVector.size() + properties.size());
for (unsigned i = 0; i < properties.size(); ++i)
@@ -364,11 +370,6 @@ String StylePropertySet::asText() const
return StylePropertySerializer(*this).asText();
}
-bool StylePropertySet::hasCSSOMWrapper() const
-{
- return m_isMutable && toMutableStylePropertySet(this)->m_cssomWrapper;
-}
-
void MutableStylePropertySet::mergeAndOverrideOnConflict(const StylePropertySet* other)
{
unsigned size = other->propertyCount();
@@ -382,13 +383,6 @@ void MutableStylePropertySet::mergeAndOverrideOnConflict(const StylePropertySet*
}
}
-void StylePropertySet::addSubresourceStyleURLs(ListHashSet<KURL>& urls, StyleSheetContents* contextStyleSheet) const
-{
- unsigned size = propertyCount();
- for (unsigned i = 0; i < size; ++i)
- propertyAt(i).value()->addSubresourceStyleURLs(urls, contextStyleSheet);
-}
-
bool StylePropertySet::hasFailedOrCanceledSubresources() const
{
unsigned size = propertyCount();
@@ -417,9 +411,6 @@ static const CSSPropertyID staticBlockProperties[] = {
CSSPropertyPageBreakAfter,
CSSPropertyPageBreakBefore,
CSSPropertyPageBreakInside,
- CSSPropertyWebkitRegionBreakAfter,
- CSSPropertyWebkitRegionBreakBefore,
- CSSPropertyWebkitRegionBreakInside,
CSSPropertyTextAlign,
CSSPropertyTextAlignLast,
CSSPropertyTextIndent,
@@ -440,7 +431,7 @@ void MutableStylePropertySet::clear()
m_propertyVector.clear();
}
-PassRefPtr<MutableStylePropertySet> StylePropertySet::copyBlockProperties() const
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> StylePropertySet::copyBlockProperties() const
{
return copyPropertiesInSet(blockProperties());
}
@@ -450,59 +441,35 @@ void MutableStylePropertySet::removeBlockProperties()
removePropertiesInSet(blockProperties().data(), blockProperties().size());
}
+inline bool containsId(const CSSPropertyID* set, unsigned length, CSSPropertyID id)
+{
+ for (unsigned i = 0; i < length; ++i) {
+ if (set[i] == id)
+ return true;
+ }
+ return false;
+}
+
bool MutableStylePropertySet::removePropertiesInSet(const CSSPropertyID* set, unsigned length)
{
if (m_propertyVector.isEmpty())
return false;
- // FIXME: This is always used with static sets and in that case constructing the hash repeatedly is pretty pointless.
- HashSet<CSSPropertyID> toRemove;
- for (unsigned i = 0; i < length; ++i)
- toRemove.add(set[i]);
-
- Vector<CSSProperty> newProperties;
+ WillBeHeapVector<CSSProperty> newProperties;
newProperties.reserveInitialCapacity(m_propertyVector.size());
- unsigned size = m_propertyVector.size();
- for (unsigned n = 0; n < size; ++n) {
- const CSSProperty& property = m_propertyVector.at(n);
+ unsigned initialSize = m_propertyVector.size();
+ const CSSProperty* properties = m_propertyVector.data();
+ for (unsigned n = 0; n < initialSize; ++n) {
+ const CSSProperty& property = properties[n];
// Not quite sure if the isImportant test is needed but it matches the existing behavior.
- if (!property.isImportant()) {
- if (toRemove.contains(property.id()))
- continue;
- }
+ if (!property.isImportant() && containsId(set, length, property.id()))
+ continue;
newProperties.append(property);
}
- bool changed = newProperties.size() != m_propertyVector.size();
m_propertyVector = newProperties;
- return changed;
-}
-
-int StylePropertySet::findPropertyIndex(CSSPropertyID propertyID) const
-{
- // Convert here propertyID into an uint16_t to compare it with the metadata's m_propertyID to avoid
- // the compiler converting it to an int multiple times in the loop.
- uint16_t id = static_cast<uint16_t>(propertyID);
- for (int n = propertyCount() - 1 ; n >= 0; --n) {
- if (id == propertyAt(n).propertyMetadata().m_propertyID) {
- // Only enabled or internal properties should be part of the style.
- ASSERT(RuntimeCSSEnabled::isCSSPropertyEnabled(propertyID) || isInternalProperty(propertyID));
- return n;
- }
- }
- return -1;
-}
-
-size_t StylePropertySet::findVariableIndex(const AtomicString& name) const
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- for (int i = propertyCount() - 1; i >= 0; --i) {
- const PropertyReference& property = propertyAt(i);
- if (property.id() == CSSPropertyVariable && toCSSVariableValue(property.value())->name() == name)
- return i;
- }
- return kNotFound;
+ return initialSize != m_propertyVector.size();
}
CSSProperty* MutableStylePropertySet::findCSSPropertyWithID(CSSPropertyID propertyID)
@@ -549,116 +516,58 @@ void MutableStylePropertySet::removeEquivalentProperties(const CSSStyleDeclarati
removeProperty(propertiesToRemove[i]);
}
-bool MutableStylePropertySet::removeVariable(const AtomicString& name)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- size_t index = findVariableIndex(name);
- if (index == kNotFound)
- return false;
- m_propertyVector.remove(index);
- return true;
-}
-
-bool MutableStylePropertySet::clearVariables()
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- CSSPropertyID variablesId = CSSPropertyVariable;
- return removePropertiesInSet(&variablesId, 1);
-}
-
-PassRefPtr<MutableStylePropertySet::VariablesIterator> MutableStylePropertySet::VariablesIterator::create(MutableStylePropertySet* propertySet)
-{
- ASSERT(RuntimeEnabledFeatures::cssVariablesEnabled());
- const size_t propertyCount = propertySet->propertyCount();
- size_t variableCount = 0;
- Vector<AtomicString> remainingNames(propertyCount);
- for (int i = propertyCount; i--; ) {
- const PropertyReference& property = propertySet->propertyAt(i);
- if (property.id() == CSSPropertyVariable)
- remainingNames[variableCount++] = toCSSVariableValue(property.value())->name();
- }
- remainingNames.shrink(variableCount);
-
- RefPtr<VariablesIterator> iterator = adoptRef(new VariablesIterator(propertySet));
- // FIXME: Make use of the Vector move constructor when rvalues are supported on all platforms.
- iterator->takeRemainingNames(remainingNames);
- return iterator.release();
-}
-
-void MutableStylePropertySet::VariablesIterator::addedVariable(const AtomicString& name)
-{
- ASSERT(!m_remainingNames.contains(name));
- ASSERT(!m_newNames.contains(name));
- m_newNames.append(name);
-}
-
-void MutableStylePropertySet::VariablesIterator::removedVariable(const AtomicString& name)
-{
- size_t index = m_remainingNames.find(name);
- if (index != kNotFound)
- m_remainingNames.remove(index);
- index = m_newNames.find(name);
- if (index != kNotFound)
- m_newNames.remove(index);
-}
-
-void MutableStylePropertySet::VariablesIterator::clearedVariables()
-{
- m_remainingNames.clear();
- m_newNames.clear();
-}
-
-void MutableStylePropertySet::VariablesIterator::advance()
-{
- if (!atEnd())
- m_remainingNames.removeLast();
- if (!m_newNames.isEmpty()) {
- m_remainingNames.appendVector(m_newNames);
- m_newNames.clear();
- }
-}
-
-PassRefPtr<MutableStylePropertySet> StylePropertySet::mutableCopy() const
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> StylePropertySet::mutableCopy() const
{
- return adoptRef(new MutableStylePropertySet(*this));
+ return adoptRefWillBeRefCountedGarbageCollected(new MutableStylePropertySet(*this));
}
-PassRefPtr<MutableStylePropertySet> StylePropertySet::copyPropertiesInSet(const Vector<CSSPropertyID>& properties) const
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> StylePropertySet::copyPropertiesInSet(const Vector<CSSPropertyID>& properties) const
{
- Vector<CSSProperty, 256> list;
+ WillBeHeapVector<CSSProperty, 256> list;
list.reserveInitialCapacity(properties.size());
for (unsigned i = 0; i < properties.size(); ++i) {
- RefPtr<CSSValue> value = getPropertyCSSValue(properties[i]);
+ RefPtrWillBeRawPtr<CSSValue> value = getPropertyCSSValue(properties[i]);
if (value)
list.append(CSSProperty(properties[i], value.release(), false));
}
return MutableStylePropertySet::create(list.data(), list.size());
}
-PropertySetCSSStyleDeclaration* MutableStylePropertySet::cssStyleDeclaration()
-{
- return m_cssomWrapper.get();
-}
-
CSSStyleDeclaration* MutableStylePropertySet::ensureCSSStyleDeclaration()
{
+ // FIXME: get rid of this weirdness of a CSSStyleDeclaration inside of a
+ // style property set.
if (m_cssomWrapper) {
ASSERT(!static_cast<CSSStyleDeclaration*>(m_cssomWrapper.get())->parentRule());
ASSERT(!m_cssomWrapper->parentElement());
return m_cssomWrapper.get();
}
- m_cssomWrapper = adoptPtr(new PropertySetCSSStyleDeclaration(this));
+ m_cssomWrapper = adoptPtrWillBeNoop(new PropertySetCSSStyleDeclaration(*this));
return m_cssomWrapper.get();
}
-CSSStyleDeclaration* MutableStylePropertySet::ensureInlineCSSStyleDeclaration(Element* parentElement)
+int MutableStylePropertySet::findPropertyIndex(CSSPropertyID propertyID) const
{
- if (m_cssomWrapper) {
- ASSERT(m_cssomWrapper->parentElement() == parentElement);
- return m_cssomWrapper.get();
+ // Convert here propertyID into an uint16_t to compare it with the metadata's m_propertyID to avoid
+ // the compiler converting it to an int multiple times in the loop.
+ uint16_t id = static_cast<uint16_t>(propertyID);
+ const CSSProperty* properties = m_propertyVector.data();
+ for (int n = m_propertyVector.size() - 1 ; n >= 0; --n) {
+ if (properties[n].metadata().m_propertyID == id) {
+ // Only enabled or internal properties should be part of the style.
+ ASSERT(RuntimeCSSEnabled::isCSSPropertyEnabled(propertyID) || isInternalProperty(propertyID));
+ return n;
+ }
}
- m_cssomWrapper = adoptPtr(new InlineCSSStyleDeclaration(this, parentElement));
- return m_cssomWrapper.get();
+
+ return -1;
+}
+
+void MutableStylePropertySet::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_cssomWrapper);
+ visitor->trace(m_propertyVector);
+ StylePropertySet::traceAfterDispatch(visitor);
}
unsigned StylePropertySet::averageSizeInBytes()
@@ -668,7 +577,7 @@ unsigned StylePropertySet::averageSizeInBytes()
}
// See the function above if you need to update this.
-struct SameSizeAsStylePropertySet : public RefCounted<SameSizeAsStylePropertySet> {
+struct SameSizeAsStylePropertySet : public RefCountedWillBeRefCountedGarbageCollected<SameSizeAsStylePropertySet> {
unsigned bitfield;
};
COMPILE_ASSERT(sizeof(StylePropertySet) == sizeof(SameSizeAsStylePropertySet), style_property_set_should_stay_small);
@@ -680,23 +589,18 @@ void StylePropertySet::showStyle()
}
#endif
-PassRefPtr<MutableStylePropertySet> MutableStylePropertySet::create(CSSParserMode cssParserMode)
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> MutableStylePropertySet::create(CSSParserMode cssParserMode)
{
- return adoptRef(new MutableStylePropertySet(cssParserMode));
+ return adoptRefWillBeRefCountedGarbageCollected(new MutableStylePropertySet(cssParserMode));
}
-PassRefPtr<MutableStylePropertySet> MutableStylePropertySet::create(const CSSProperty* properties, unsigned count)
+PassRefPtrWillBeRawPtr<MutableStylePropertySet> MutableStylePropertySet::create(const CSSProperty* properties, unsigned count)
{
- return adoptRef(new MutableStylePropertySet(properties, count));
+ return adoptRefWillBeRefCountedGarbageCollected(new MutableStylePropertySet(properties, count));
}
String StylePropertySet::PropertyReference::cssName() const
{
- if (id() == CSSPropertyVariable) {
- if (!propertyValue()->isVariableValue())
- return emptyString(); // Should not happen, but if it does, avoid a bad cast.
- return "var-" + toCSSVariableValue(propertyValue())->name();
- }
return getPropertyNameString(id());
}
diff --git a/chromium/third_party/WebKit/Source/core/css/StylePropertySet.h b/chromium/third_party/WebKit/Source/core/css/StylePropertySet.h
index 1003f3b93e5..3e1a42786e0 100644
--- a/chromium/third_party/WebKit/Source/core/css/StylePropertySet.h
+++ b/chromium/third_party/WebKit/Source/core/css/StylePropertySet.h
@@ -21,11 +21,10 @@
#ifndef StylePropertySet_h
#define StylePropertySet_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
#include "core/css/CSSParserMode.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSProperty.h"
-#include "core/css/CSSVariablesIterator.h"
#include "core/css/PropertySetCSSStyleDeclaration.h"
#include "wtf/ListHashSet.h"
#include "wtf/Vector.h"
@@ -42,12 +41,20 @@ class MutableStylePropertySet;
class StylePropertyShorthand;
class StyleSheetContents;
-class StylePropertySet : public RefCounted<StylePropertySet> {
+class StylePropertySet : public RefCountedWillBeRefCountedGarbageCollected<StylePropertySet> {
friend class PropertyReference;
public:
+
+#if ENABLE(OILPAN)
+ // When oilpan is enabled override the finalize method to dispatch to the subclasses'
+ // destructor. This can be removed once the MutableStylePropertySet's OwnPtr is moved
+ // to the heap.
+ void finalizeGarbageCollectedObject();
+#else
// Override RefCounted's deref() to ensure operator delete is called on
// the appropriate subclass type.
void deref();
+#endif
class PropertyReference {
public:
@@ -87,32 +94,26 @@ public:
bool isEmpty() const;
PropertyReference propertyAt(unsigned index) const { return PropertyReference(*this, index); }
int findPropertyIndex(CSSPropertyID) const;
- size_t findVariableIndex(const AtomicString& name) const;
- PassRefPtr<CSSValue> getPropertyCSSValue(CSSPropertyID) const;
+ PassRefPtrWillBeRawPtr<CSSValue> getPropertyCSSValue(CSSPropertyID) const;
String getPropertyValue(CSSPropertyID) const;
- unsigned variableCount() const;
- String variableValue(const AtomicString& name) const;
bool propertyIsImportant(CSSPropertyID) const;
CSSPropertyID getPropertyShorthand(CSSPropertyID) const;
bool isPropertyImplicit(CSSPropertyID) const;
- PassRefPtr<MutableStylePropertySet> copyBlockProperties() const;
+ PassRefPtrWillBeRawPtr<MutableStylePropertySet> copyBlockProperties() const;
CSSParserMode cssParserMode() const { return static_cast<CSSParserMode>(m_cssParserMode); }
- void addSubresourceStyleURLs(ListHashSet<KURL>&, StyleSheetContents* contextStyleSheet) const;
-
- PassRefPtr<MutableStylePropertySet> mutableCopy() const;
+ PassRefPtrWillBeRawPtr<MutableStylePropertySet> mutableCopy() const;
PassRefPtr<ImmutableStylePropertySet> immutableCopyIfNeeded() const;
- PassRefPtr<MutableStylePropertySet> copyPropertiesInSet(const Vector<CSSPropertyID>&) const;
+ PassRefPtrWillBeRawPtr<MutableStylePropertySet> copyPropertiesInSet(const Vector<CSSPropertyID>&) const;
String asText() const;
bool isMutable() const { return m_isMutable; }
- bool hasCSSOMWrapper() const;
bool hasFailedOrCanceledSubresources() const;
@@ -124,6 +125,9 @@ public:
bool propertyMatches(CSSPropertyID, const CSSValue*) const;
+ void trace(Visitor*);
+ void traceAfterDispatch(Visitor*) { }
+
protected:
enum { MaxArraySize = (1 << 28) - 1 };
@@ -154,8 +158,16 @@ public:
unsigned propertyCount() const { return m_arraySize; }
- const CSSValue** valueArray() const;
+ const RawPtrWillBeMember<CSSValue>* valueArray() const;
const StylePropertyMetadata* metadataArray() const;
+ int findPropertyIndex(CSSPropertyID) const;
+
+ void traceAfterDispatch(Visitor*);
+
+ void* operator new(std::size_t, void* location)
+ {
+ return location;
+ }
void* m_storage;
@@ -163,14 +175,14 @@ private:
ImmutableStylePropertySet(const CSSProperty*, unsigned count, CSSParserMode);
};
-inline const CSSValue** ImmutableStylePropertySet::valueArray() const
+inline const RawPtrWillBeMember<CSSValue>* ImmutableStylePropertySet::valueArray() const
{
- return reinterpret_cast<const CSSValue**>(const_cast<const void**>(&(this->m_storage)));
+ return reinterpret_cast<const RawPtrWillBeMember<CSSValue>*>(const_cast<const void**>(&(this->m_storage)));
}
inline const StylePropertyMetadata* ImmutableStylePropertySet::metadataArray() const
{
- return reinterpret_cast<const StylePropertyMetadata*>(&reinterpret_cast<const char*>(&(this->m_storage))[m_arraySize * sizeof(CSSValue*)]);
+ return reinterpret_cast<const StylePropertyMetadata*>(&reinterpret_cast<const char*>(&(this->m_storage))[m_arraySize * sizeof(RawPtrWillBeMember<CSSValue>)]);
}
DEFINE_TYPE_CASTS(ImmutableStylePropertySet, StylePropertySet, set, !set->isMutable(), !set.isMutable());
@@ -183,18 +195,17 @@ inline ImmutableStylePropertySet* toImmutableStylePropertySet(const RefPtr<Style
class MutableStylePropertySet : public StylePropertySet {
public:
~MutableStylePropertySet() { }
- static PassRefPtr<MutableStylePropertySet> create(CSSParserMode = HTMLQuirksMode);
- static PassRefPtr<MutableStylePropertySet> create(const CSSProperty* properties, unsigned count);
+ static PassRefPtrWillBeRawPtr<MutableStylePropertySet> create(CSSParserMode = HTMLQuirksMode);
+ static PassRefPtrWillBeRawPtr<MutableStylePropertySet> create(const CSSProperty* properties, unsigned count);
unsigned propertyCount() const { return m_propertyVector.size(); }
- PropertySetCSSStyleDeclaration* cssStyleDeclaration();
- void addParsedProperties(const Vector<CSSProperty, 256>&);
+ void addParsedProperties(const WillBeHeapVector<CSSProperty, 256>&);
void addParsedProperty(const CSSProperty&);
// These expand shorthand properties into multiple properties.
bool setProperty(CSSPropertyID, const String& value, bool important = false, StyleSheetContents* contextStyleSheet = 0);
- void setProperty(CSSPropertyID, PassRefPtr<CSSValue>, bool important = false);
+ void setProperty(CSSPropertyID, PassRefPtrWillBeRawPtr<CSSValue>, bool important = false);
// These do not. FIXME: This is too messy, we can do better.
bool setProperty(CSSPropertyID, CSSValueID identifier, bool important = false);
@@ -202,7 +213,6 @@ public:
void appendPrefixingVariantProperty(const CSSProperty&);
void setPrefixingVariantProperty(const CSSProperty&);
void setProperty(const CSSProperty&, CSSProperty* slot = 0);
- bool setVariableValue(const AtomicString& name, const String& value, bool important = false);
bool removeProperty(CSSPropertyID, String* returnText = 0);
void removePrefixedOrUnprefixedProperty(CSSPropertyID);
@@ -210,10 +220,6 @@ public:
bool removePropertiesInSet(const CSSPropertyID* set, unsigned length);
void removeEquivalentProperties(const StylePropertySet*);
void removeEquivalentProperties(const CSSStyleDeclaration*);
- bool removeVariable(const AtomicString& name);
- bool clearVariables();
-
- PassRefPtr<CSSVariablesIterator> variablesIterator() { return VariablesIterator::create(this); }
void mergeAndOverrideOnConflict(const StylePropertySet*);
@@ -221,40 +227,22 @@ public:
void parseDeclaration(const String& styleDeclaration, StyleSheetContents* contextStyleSheet);
CSSStyleDeclaration* ensureCSSStyleDeclaration();
- CSSStyleDeclaration* ensureInlineCSSStyleDeclaration(Element* parentElement);
+ int findPropertyIndex(CSSPropertyID) const;
- Vector<CSSProperty, 4> m_propertyVector;
+ void traceAfterDispatch(Visitor*);
private:
- class VariablesIterator : public CSSVariablesIterator {
- public:
- virtual ~VariablesIterator() { }
- static PassRefPtr<VariablesIterator> create(MutableStylePropertySet*);
- private:
- explicit VariablesIterator(MutableStylePropertySet* propertySet) : m_propertySet(propertySet) { }
- void takeRemainingNames(Vector<AtomicString>& remainingNames) { m_remainingNames.swap(remainingNames); }
- virtual void advance() OVERRIDE;
- virtual bool atEnd() const OVERRIDE { return m_remainingNames.isEmpty(); }
- virtual AtomicString name() const OVERRIDE { return m_remainingNames.last(); }
- virtual String value() const OVERRIDE { return m_propertySet->variableValue(name()); }
- virtual void addedVariable(const AtomicString& name) OVERRIDE;
- virtual void removedVariable(const AtomicString& name) OVERRIDE;
- virtual void clearedVariables() OVERRIDE;
-
- RefPtr<MutableStylePropertySet> m_propertySet;
- Vector<AtomicString> m_remainingNames;
- Vector<AtomicString> m_newNames;
- };
-
explicit MutableStylePropertySet(CSSParserMode);
explicit MutableStylePropertySet(const StylePropertySet&);
MutableStylePropertySet(const CSSProperty* properties, unsigned count);
bool removeShorthandProperty(CSSPropertyID);
CSSProperty* findCSSPropertyWithID(CSSPropertyID);
- OwnPtr<PropertySetCSSStyleDeclaration> m_cssomWrapper;
+ OwnPtrWillBeMember<PropertySetCSSStyleDeclaration> m_cssomWrapper;
friend class StylePropertySet;
+
+ WillBeHeapVector<CSSProperty, 4> m_propertyVector;
};
DEFINE_TYPE_CASTS(MutableStylePropertySet, StylePropertySet, set, set->isMutable(), set.isMutable());
@@ -290,6 +278,7 @@ inline bool StylePropertySet::isEmpty() const
return !propertyCount();
}
+#if !ENABLE(OILPAN)
inline void StylePropertySet::deref()
{
if (!derefBase())
@@ -300,6 +289,14 @@ inline void StylePropertySet::deref()
else
delete toImmutableStylePropertySet(this);
}
+#endif // !ENABLE(OILPAN)
+
+inline int StylePropertySet::findPropertyIndex(CSSPropertyID propertyID) const
+{
+ if (m_isMutable)
+ return toMutableStylePropertySet(this)->findPropertyIndex(propertyID);
+ return toImmutableStylePropertySet(this)->findPropertyIndex(propertyID);
+}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/StylePropertyShorthandCustom.cpp b/chromium/third_party/WebKit/Source/core/css/StylePropertyShorthandCustom.cpp
index b157746c8b9..9284ca7e8bb 100644
--- a/chromium/third_party/WebKit/Source/core/css/StylePropertyShorthandCustom.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StylePropertyShorthandCustom.cpp
@@ -20,7 +20,7 @@
*/
#include "config.h"
-#include "StylePropertyShorthand.h"
+#include "core/StylePropertyShorthand.h"
namespace WebCore {
@@ -86,6 +86,31 @@ const StylePropertyShorthand& webkitAnimationShorthandForParsing()
return webkitAnimationLonghandsForParsing;
}
+// Similar to animations, we have property after timing-function and delay after duration
+const StylePropertyShorthand& transitionShorthandForParsing()
+{
+ static const CSSPropertyID transitionProperties[] = {
+ CSSPropertyTransitionDuration,
+ CSSPropertyTransitionTimingFunction,
+ CSSPropertyTransitionDelay,
+ CSSPropertyTransitionProperty
+ };
+ DEFINE_STATIC_LOCAL(StylePropertyShorthand, transitionLonghands, (CSSPropertyTransition, transitionProperties, WTF_ARRAY_LENGTH(transitionProperties)));
+ return transitionLonghands;
+}
+
+const StylePropertyShorthand& webkitTransitionShorthandForParsing()
+{
+ static const CSSPropertyID webkitTransitionProperties[] = {
+ CSSPropertyWebkitTransitionDuration,
+ CSSPropertyWebkitTransitionTimingFunction,
+ CSSPropertyWebkitTransitionDelay,
+ CSSPropertyWebkitTransitionProperty
+ };
+ DEFINE_STATIC_LOCAL(StylePropertyShorthand, webkitTransitionLonghands, (CSSPropertyWebkitTransition, webkitTransitionProperties, WTF_ARRAY_LENGTH(webkitTransitionProperties)));
+ return webkitTransitionLonghands;
+}
+
// Returns an empty list if the property is not a shorthand, otherwise the list of longhands for parsing.
const StylePropertyShorthand& parsingShorthandForProperty(CSSPropertyID propertyID)
{
@@ -96,6 +121,10 @@ const StylePropertyShorthand& parsingShorthandForProperty(CSSPropertyID property
return borderShorthandForParsing();
case CSSPropertyWebkitAnimation:
return webkitAnimationShorthandForParsing();
+ case CSSPropertyTransition:
+ return transitionShorthandForParsing();
+ case CSSPropertyWebkitTransition:
+ return webkitTransitionShorthandForParsing();
default:
return shorthandForProperty(propertyID);
}
@@ -113,6 +142,22 @@ bool isExpandedShorthand(CSSPropertyID id)
return shorthandForProperty(id).length();
}
+bool isExpandedShorthandForAll(CSSPropertyID propertyId)
+{
+ // FIXME: isExpandedShorthand says "font" is not an expanded shorthand,
+ // but font is expanded to font-family, font-size, and so on.
+ // StylePropertySerializer::asText should not generate css text like
+ // "font: initial; font-family: initial;...". To avoid this, we need to
+ // treat "font" as an expanded shorthand.
+ // And while applying "all" property, we cannot apply "font" property
+ // directly. This causes ASSERT crash, because StyleBuilder assume that
+ // all given properties are not expanded shorthands.
+ // "marker" has the same issue.
+ if (propertyId == CSSPropertyMarker || propertyId == CSSPropertyFont)
+ return true;
+ return shorthandForProperty(propertyId).length();
+}
+
unsigned indexOfShorthandForLonghand(CSSPropertyID shorthandID, const Vector<StylePropertyShorthand, 4>& shorthands)
{
for (unsigned i = 0; i < shorthands.size(); ++i) {
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleRule.cpp b/chromium/third_party/WebKit/Source/core/css/StyleRule.cpp
index 299f7a2300d..7735706796f 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleRule.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StyleRule.cpp
@@ -22,14 +22,12 @@
#include "config.h"
#include "core/css/StyleRule.h"
-#include "RuntimeEnabledFeatures.h"
#include "core/css/CSSFilterRule.h"
#include "core/css/CSSFontFaceRule.h"
#include "core/css/CSSImportRule.h"
#include "core/css/CSSKeyframesRule.h"
#include "core/css/CSSMediaRule.h"
#include "core/css/CSSPageRule.h"
-#include "core/css/CSSRegionRule.h"
#include "core/css/CSSStyleRule.h"
#include "core/css/CSSSupportsRule.h"
#include "core/css/CSSViewportRule.h"
@@ -38,22 +36,100 @@
namespace WebCore {
-struct SameSizeAsStyleRuleBase : public WTF::RefCountedBase {
+struct SameSizeAsStyleRuleBase : public RefCountedWillBeRefCountedGarbageCollected<SameSizeAsStyleRuleBase> {
unsigned bitfields;
};
COMPILE_ASSERT(sizeof(StyleRuleBase) <= sizeof(SameSizeAsStyleRuleBase), StyleRuleBase_should_stay_small);
-PassRefPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSStyleSheet* parentSheet) const
+PassRefPtrWillBeRawPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSStyleSheet* parentSheet) const
{
return createCSSOMWrapper(parentSheet, 0);
}
-PassRefPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSRule* parentRule) const
+PassRefPtrWillBeRawPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSRule* parentRule) const
{
return createCSSOMWrapper(0, parentRule);
}
+void StyleRuleBase::trace(Visitor* visitor)
+{
+ switch (type()) {
+ case Style:
+ toStyleRule(this)->traceAfterDispatch(visitor);
+ return;
+ case Page:
+ toStyleRulePage(this)->traceAfterDispatch(visitor);
+ return;
+ case FontFace:
+ toStyleRuleFontFace(this)->traceAfterDispatch(visitor);
+ return;
+ case Media:
+ toStyleRuleMedia(this)->traceAfterDispatch(visitor);
+ return;
+ case Supports:
+ toStyleRuleSupports(this)->traceAfterDispatch(visitor);
+ return;
+ case Import:
+ toStyleRuleImport(this)->traceAfterDispatch(visitor);
+ return;
+ case Keyframes:
+ toStyleRuleKeyframes(this)->traceAfterDispatch(visitor);
+ return;
+ case Viewport:
+ toStyleRuleViewport(this)->traceAfterDispatch(visitor);
+ return;
+ case Filter:
+ toStyleRuleFilter(this)->traceAfterDispatch(visitor);
+ return;
+ case Unknown:
+ case Charset:
+ case Keyframe:
+ ASSERT_NOT_REACHED();
+ return;
+ }
+ ASSERT_NOT_REACHED();
+}
+
+void StyleRuleBase::finalizeGarbageCollectedObject()
+{
+ switch (type()) {
+ case Style:
+ toStyleRule(this)->~StyleRule();
+ return;
+ case Page:
+ toStyleRulePage(this)->~StyleRulePage();
+ return;
+ case FontFace:
+ toStyleRuleFontFace(this)->~StyleRuleFontFace();
+ return;
+ case Media:
+ toStyleRuleMedia(this)->~StyleRuleMedia();
+ return;
+ case Supports:
+ toStyleRuleSupports(this)->~StyleRuleSupports();
+ return;
+ case Import:
+ toStyleRuleImport(this)->~StyleRuleImport();
+ return;
+ case Keyframes:
+ toStyleRuleKeyframes(this)->~StyleRuleKeyframes();
+ return;
+ case Viewport:
+ toStyleRuleViewport(this)->~StyleRuleViewport();
+ return;
+ case Filter:
+ toStyleRuleFilter(this)->~StyleRuleFilter();
+ return;
+ case Unknown:
+ case Charset:
+ case Keyframe:
+ ASSERT_NOT_REACHED();
+ return;
+ }
+ ASSERT_NOT_REACHED();
+}
+
void StyleRuleBase::destroy()
{
switch (type()) {
@@ -72,9 +148,6 @@ void StyleRuleBase::destroy()
case Supports:
delete toStyleRuleSupports(this);
return;
- case Region:
- delete toStyleRuleRegion(this);
- return;
case Import:
delete toStyleRuleImport(this);
return;
@@ -96,7 +169,7 @@ void StyleRuleBase::destroy()
ASSERT_NOT_REACHED();
}
-PassRefPtr<StyleRuleBase> StyleRuleBase::copy() const
+PassRefPtrWillBeRawPtr<StyleRuleBase> StyleRuleBase::copy() const
{
switch (type()) {
case Style:
@@ -109,12 +182,10 @@ PassRefPtr<StyleRuleBase> StyleRuleBase::copy() const
return toStyleRuleMedia(this)->copy();
case Supports:
return toStyleRuleSupports(this)->copy();
- case Region:
- return toStyleRuleRegion(this)->copy();
case Import:
// FIXME: Copy import rules.
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
case Keyframes:
return toStyleRuleKeyframes(this)->copy();
case Viewport:
@@ -125,15 +196,15 @@ PassRefPtr<StyleRuleBase> StyleRuleBase::copy() const
case Charset:
case Keyframe:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSStyleSheet* parentSheet, CSSRule* parentRule) const
+PassRefPtrWillBeRawPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSStyleSheet* parentSheet, CSSRule* parentRule) const
{
- RefPtr<CSSRule> rule;
+ RefPtrWillBeRawPtr<CSSRule> rule = nullptr;
StyleRuleBase* self = const_cast<StyleRuleBase*>(this);
switch (type()) {
case Style:
@@ -151,9 +222,6 @@ PassRefPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSStyleSheet* parentSheet
case Supports:
rule = CSSSupportsRule::create(toStyleRuleSupports(self), parentSheet);
break;
- case Region:
- rule = CSSRegionRule::create(toStyleRuleRegion(self), parentSheet);
- break;
case Import:
rule = CSSImportRule::create(toStyleRuleImport(self), parentSheet);
break;
@@ -170,7 +238,7 @@ PassRefPtr<CSSRule> StyleRuleBase::createCSSOMWrapper(CSSStyleSheet* parentSheet
case Charset:
case Keyframe:
ASSERT_NOT_REACHED();
- return 0;
+ return nullptr;
}
if (parentRule)
rule->setParentRule(parentRule);
@@ -198,11 +266,11 @@ StyleRule::~StyleRule()
{
}
-MutableStylePropertySet* StyleRule::mutableProperties()
+MutableStylePropertySet& StyleRule::mutableProperties()
{
if (!m_properties->isMutable())
m_properties = m_properties->mutableCopy();
- return toMutableStylePropertySet(m_properties);
+ return *toMutableStylePropertySet(m_properties);
}
void StyleRule::setProperties(PassRefPtr<StylePropertySet> properties)
@@ -226,11 +294,11 @@ StyleRulePage::~StyleRulePage()
{
}
-MutableStylePropertySet* StyleRulePage::mutableProperties()
+MutableStylePropertySet& StyleRulePage::mutableProperties()
{
if (!m_properties->isMutable())
m_properties = m_properties->mutableCopy();
- return toMutableStylePropertySet(m_properties);
+ return *toMutableStylePropertySet(m_properties);
}
void StyleRulePage::setProperties(PassRefPtr<StylePropertySet> properties)
@@ -253,11 +321,11 @@ StyleRuleFontFace::~StyleRuleFontFace()
{
}
-MutableStylePropertySet* StyleRuleFontFace::mutableProperties()
+MutableStylePropertySet& StyleRuleFontFace::mutableProperties()
{
if (!m_properties->isMutable())
m_properties = m_properties->mutableCopy();
- return toMutableStylePropertySet(m_properties);
+ return *toMutableStylePropertySet(m_properties);
}
void StyleRuleFontFace::setProperties(PassRefPtr<StylePropertySet> properties)
@@ -265,7 +333,7 @@ void StyleRuleFontFace::setProperties(PassRefPtr<StylePropertySet> properties)
m_properties = properties;
}
-StyleRuleGroup::StyleRuleGroup(Type type, Vector<RefPtr<StyleRuleBase> >& adoptRule)
+StyleRuleGroup::StyleRuleGroup(Type type, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRule)
: StyleRuleBase(type)
{
m_childRules.swap(adoptRule);
@@ -279,7 +347,7 @@ StyleRuleGroup::StyleRuleGroup(const StyleRuleGroup& o)
m_childRules[i] = o.m_childRules[i]->copy();
}
-void StyleRuleGroup::wrapperInsertRule(unsigned index, PassRefPtr<StyleRuleBase> rule)
+void StyleRuleGroup::wrapperInsertRule(unsigned index, PassRefPtrWillBeRawPtr<StyleRuleBase> rule)
{
m_childRules.insert(index, rule);
}
@@ -289,7 +357,13 @@ void StyleRuleGroup::wrapperRemoveRule(unsigned index)
m_childRules.remove(index);
}
-StyleRuleMedia::StyleRuleMedia(PassRefPtr<MediaQuerySet> media, Vector<RefPtr<StyleRuleBase> >& adoptRules)
+void StyleRuleGroup::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_childRules);
+ StyleRuleBase::traceAfterDispatch(visitor);
+}
+
+StyleRuleMedia::StyleRuleMedia(PassRefPtrWillBeRawPtr<MediaQuerySet> media, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRules)
: StyleRuleGroup(Media, adoptRules)
, m_mediaQueries(media)
{
@@ -302,7 +376,13 @@ StyleRuleMedia::StyleRuleMedia(const StyleRuleMedia& o)
m_mediaQueries = o.m_mediaQueries->copy();
}
-StyleRuleSupports::StyleRuleSupports(const String& conditionText, bool conditionIsSupported, Vector<RefPtr<StyleRuleBase> >& adoptRules)
+void StyleRuleMedia::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_mediaQueries);
+ StyleRuleGroup::traceAfterDispatch(visitor);
+}
+
+StyleRuleSupports::StyleRuleSupports(const String& conditionText, bool conditionIsSupported, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRules)
: StyleRuleGroup(Supports, adoptRules)
, m_conditionText(conditionText)
, m_conditionIsSupported(conditionIsSupported)
@@ -316,20 +396,6 @@ StyleRuleSupports::StyleRuleSupports(const StyleRuleSupports& o)
{
}
-StyleRuleRegion::StyleRuleRegion(Vector<OwnPtr<CSSParserSelector> >* selectors, Vector<RefPtr<StyleRuleBase> >& adoptRules)
- : StyleRuleGroup(Region, adoptRules)
-{
- ASSERT(RuntimeEnabledFeatures::cssRegionsEnabled());
- m_selectorList.adoptSelectorVector(*selectors);
-}
-
-StyleRuleRegion::StyleRuleRegion(const StyleRuleRegion& o)
- : StyleRuleGroup(o)
- , m_selectorList(o.m_selectorList)
-{
- ASSERT(RuntimeEnabledFeatures::cssRegionsEnabled());
-}
-
StyleRuleViewport::StyleRuleViewport()
: StyleRuleBase(Viewport)
{
@@ -345,11 +411,11 @@ StyleRuleViewport::~StyleRuleViewport()
{
}
-MutableStylePropertySet* StyleRuleViewport::mutableProperties()
+MutableStylePropertySet& StyleRuleViewport::mutableProperties()
{
if (!m_properties->isMutable())
m_properties = m_properties->mutableCopy();
- return toMutableStylePropertySet(m_properties);
+ return *toMutableStylePropertySet(m_properties);
}
void StyleRuleViewport::setProperties(PassRefPtr<StylePropertySet> properties)
@@ -374,11 +440,11 @@ StyleRuleFilter::~StyleRuleFilter()
{
}
-MutableStylePropertySet* StyleRuleFilter::mutableProperties()
+MutableStylePropertySet& StyleRuleFilter::mutableProperties()
{
if (!m_properties->isMutable())
m_properties = m_properties->mutableCopy();
- return toMutableStylePropertySet(m_properties);
+ return *toMutableStylePropertySet(m_properties);
}
void StyleRuleFilter::setProperties(PassRefPtr<StylePropertySet> properties)
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleRule.h b/chromium/third_party/WebKit/Source/core/css/StyleRule.h
index e1216ebeedd..ab0853d7844 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleRule.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleRule.h
@@ -24,6 +24,7 @@
#include "core/css/CSSSelectorList.h"
#include "core/css/MediaList.h"
+#include "platform/heap/Handle.h"
#include "wtf/RefPtr.h"
namespace WebCore {
@@ -34,8 +35,8 @@ class CSSStyleSheet;
class MutableStylePropertySet;
class StylePropertySet;
-class StyleRuleBase : public WTF::RefCountedBase {
- WTF_MAKE_FAST_ALLOCATED;
+class StyleRuleBase : public RefCountedWillBeGarbageCollectedFinalized<StyleRuleBase> {
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
enum Type {
Unknown, // Not used.
@@ -49,7 +50,6 @@ public:
Keyframe, // Not used. These are internally non-rule StyleKeyframe objects.
Supports = 12,
Viewport = 15,
- Region = 16,
Filter = 17
};
@@ -61,213 +61,216 @@ public:
bool isMediaRule() const { return type() == Media; }
bool isPageRule() const { return type() == Page; }
bool isStyleRule() const { return type() == Style; }
- bool isRegionRule() const { return type() == Region; }
bool isSupportsRule() const { return type() == Supports; }
bool isViewportRule() const { return type() == Viewport; }
bool isImportRule() const { return type() == Import; }
bool isFilterRule() const { return type() == Filter; }
- PassRefPtr<StyleRuleBase> copy() const;
+ PassRefPtrWillBeRawPtr<StyleRuleBase> copy() const;
+#if !ENABLE(OILPAN)
void deref()
{
if (derefBase())
destroy();
}
+#endif // !ENABLE(OILPAN)
// FIXME: There shouldn't be any need for the null parent version.
- PassRefPtr<CSSRule> createCSSOMWrapper(CSSStyleSheet* parentSheet = 0) const;
- PassRefPtr<CSSRule> createCSSOMWrapper(CSSRule* parentRule) const;
+ PassRefPtrWillBeRawPtr<CSSRule> createCSSOMWrapper(CSSStyleSheet* parentSheet = 0) const;
+ PassRefPtrWillBeRawPtr<CSSRule> createCSSOMWrapper(CSSRule* parentRule) const;
+
+ void trace(Visitor*);
+ void traceAfterDispatch(Visitor*) { };
+ void finalizeGarbageCollectedObject();
protected:
StyleRuleBase(Type type) : m_type(type) { }
- StyleRuleBase(const StyleRuleBase& o) : WTF::RefCountedBase(), m_type(o.m_type) { }
+ StyleRuleBase(const StyleRuleBase& o) : m_type(o.m_type) { }
~StyleRuleBase() { }
private:
void destroy();
- PassRefPtr<CSSRule> createCSSOMWrapper(CSSStyleSheet* parentSheet, CSSRule* parentRule) const;
+ PassRefPtrWillBeRawPtr<CSSRule> createCSSOMWrapper(CSSStyleSheet* parentSheet, CSSRule* parentRule) const;
unsigned m_type : 5;
};
class StyleRule : public StyleRuleBase {
- WTF_MAKE_FAST_ALLOCATED;
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- static PassRefPtr<StyleRule> create() { return adoptRef(new StyleRule()); }
+ static PassRefPtrWillBeRawPtr<StyleRule> create() { return adoptRefWillBeNoop(new StyleRule()); }
~StyleRule();
const CSSSelectorList& selectorList() const { return m_selectorList; }
- const StylePropertySet* properties() const { return m_properties.get(); }
- MutableStylePropertySet* mutableProperties();
+ const StylePropertySet& properties() const { return *m_properties; }
+ MutableStylePropertySet& mutableProperties();
void parserAdoptSelectorVector(Vector<OwnPtr<CSSParserSelector> >& selectors) { m_selectorList.adoptSelectorVector(selectors); }
void wrapperAdoptSelectorList(CSSSelectorList& selectors) { m_selectorList.adopt(selectors); }
void setProperties(PassRefPtr<StylePropertySet>);
- PassRefPtr<StyleRule> copy() const { return adoptRef(new StyleRule(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRule> copy() const { return adoptRefWillBeNoop(new StyleRule(*this)); }
static unsigned averageSizeInBytes();
+ void traceAfterDispatch(Visitor* visitor) { StyleRuleBase::traceAfterDispatch(visitor); }
+
private:
StyleRule();
StyleRule(const StyleRule&);
- RefPtr<StylePropertySet> m_properties;
+ RefPtr<StylePropertySet> m_properties; // Cannot be null.
CSSSelectorList m_selectorList;
};
class StyleRuleFontFace : public StyleRuleBase {
public:
- static PassRefPtr<StyleRuleFontFace> create() { return adoptRef(new StyleRuleFontFace); }
+ static PassRefPtrWillBeRawPtr<StyleRuleFontFace> create() { return adoptRefWillBeNoop(new StyleRuleFontFace); }
~StyleRuleFontFace();
- const StylePropertySet* properties() const { return m_properties.get(); }
- MutableStylePropertySet* mutableProperties();
+ const StylePropertySet& properties() const { return *m_properties; }
+ MutableStylePropertySet& mutableProperties();
void setProperties(PassRefPtr<StylePropertySet>);
- PassRefPtr<StyleRuleFontFace> copy() const { return adoptRef(new StyleRuleFontFace(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRuleFontFace> copy() const { return adoptRefWillBeNoop(new StyleRuleFontFace(*this)); }
+
+ void traceAfterDispatch(Visitor* visitor) { StyleRuleBase::traceAfterDispatch(visitor); }
private:
StyleRuleFontFace();
StyleRuleFontFace(const StyleRuleFontFace&);
- RefPtr<StylePropertySet> m_properties;
+ RefPtr<StylePropertySet> m_properties; // Cannot be null.
};
class StyleRulePage : public StyleRuleBase {
public:
- static PassRefPtr<StyleRulePage> create() { return adoptRef(new StyleRulePage); }
+ static PassRefPtrWillBeRawPtr<StyleRulePage> create() { return adoptRefWillBeNoop(new StyleRulePage); }
~StyleRulePage();
const CSSSelector* selector() const { return m_selectorList.first(); }
- const StylePropertySet* properties() const { return m_properties.get(); }
- MutableStylePropertySet* mutableProperties();
+ const StylePropertySet& properties() const { return *m_properties; }
+ MutableStylePropertySet& mutableProperties();
void parserAdoptSelectorVector(Vector<OwnPtr<CSSParserSelector> >& selectors) { m_selectorList.adoptSelectorVector(selectors); }
void wrapperAdoptSelectorList(CSSSelectorList& selectors) { m_selectorList.adopt(selectors); }
void setProperties(PassRefPtr<StylePropertySet>);
- PassRefPtr<StyleRulePage> copy() const { return adoptRef(new StyleRulePage(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRulePage> copy() const { return adoptRefWillBeNoop(new StyleRulePage(*this)); }
+
+ void traceAfterDispatch(Visitor* visitor) { StyleRuleBase::traceAfterDispatch(visitor); }
private:
StyleRulePage();
StyleRulePage(const StyleRulePage&);
- RefPtr<StylePropertySet> m_properties;
+ RefPtr<StylePropertySet> m_properties; // Cannot be null.
CSSSelectorList m_selectorList;
};
class StyleRuleGroup : public StyleRuleBase {
public:
- const Vector<RefPtr<StyleRuleBase> >& childRules() const { return m_childRules; }
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& childRules() const { return m_childRules; }
- void wrapperInsertRule(unsigned, PassRefPtr<StyleRuleBase>);
+ void wrapperInsertRule(unsigned, PassRefPtrWillBeRawPtr<StyleRuleBase>);
void wrapperRemoveRule(unsigned);
+ void traceAfterDispatch(Visitor*);
+
protected:
- StyleRuleGroup(Type, Vector<RefPtr<StyleRuleBase> >& adoptRule);
+ StyleRuleGroup(Type, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRule);
StyleRuleGroup(const StyleRuleGroup&);
private:
- Vector<RefPtr<StyleRuleBase> > m_childRules;
+ WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> > m_childRules;
};
class StyleRuleMedia : public StyleRuleGroup {
public:
- static PassRefPtr<StyleRuleMedia> create(PassRefPtr<MediaQuerySet> media, Vector<RefPtr<StyleRuleBase> >& adoptRules)
+ static PassRefPtrWillBeRawPtr<StyleRuleMedia> create(PassRefPtrWillBeRawPtr<MediaQuerySet> media, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRules)
{
- return adoptRef(new StyleRuleMedia(media, adoptRules));
+ return adoptRefWillBeNoop(new StyleRuleMedia(media, adoptRules));
}
MediaQuerySet* mediaQueries() const { return m_mediaQueries.get(); }
- PassRefPtr<StyleRuleMedia> copy() const { return adoptRef(new StyleRuleMedia(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRuleMedia> copy() const { return adoptRefWillBeNoop(new StyleRuleMedia(*this)); }
+
+ void traceAfterDispatch(Visitor*);
private:
- StyleRuleMedia(PassRefPtr<MediaQuerySet>, Vector<RefPtr<StyleRuleBase> >& adoptRules);
+ StyleRuleMedia(PassRefPtrWillBeRawPtr<MediaQuerySet>, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRules);
StyleRuleMedia(const StyleRuleMedia&);
- RefPtr<MediaQuerySet> m_mediaQueries;
+ RefPtrWillBeMember<MediaQuerySet> m_mediaQueries;
};
class StyleRuleSupports : public StyleRuleGroup {
public:
- static PassRefPtr<StyleRuleSupports> create(const String& conditionText, bool conditionIsSupported, Vector<RefPtr<StyleRuleBase> >& adoptRules)
+ static PassRefPtrWillBeRawPtr<StyleRuleSupports> create(const String& conditionText, bool conditionIsSupported, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRules)
{
- return adoptRef(new StyleRuleSupports(conditionText, conditionIsSupported, adoptRules));
+ return adoptRefWillBeNoop(new StyleRuleSupports(conditionText, conditionIsSupported, adoptRules));
}
String conditionText() const { return m_conditionText; }
bool conditionIsSupported() const { return m_conditionIsSupported; }
- PassRefPtr<StyleRuleSupports> copy() const { return adoptRef(new StyleRuleSupports(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRuleSupports> copy() const { return adoptRefWillBeNoop(new StyleRuleSupports(*this)); }
+
+ void traceAfterDispatch(Visitor* visitor) { StyleRuleGroup::traceAfterDispatch(visitor); }
private:
- StyleRuleSupports(const String& conditionText, bool conditionIsSupported, Vector<RefPtr<StyleRuleBase> >& adoptRules);
+ StyleRuleSupports(const String& conditionText, bool conditionIsSupported, WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& adoptRules);
StyleRuleSupports(const StyleRuleSupports&);
String m_conditionText;
bool m_conditionIsSupported;
};
-class StyleRuleRegion : public StyleRuleGroup {
-public:
- static PassRefPtr<StyleRuleRegion> create(Vector<OwnPtr<CSSParserSelector> >* selectors, Vector<RefPtr<StyleRuleBase> >& adoptRules)
- {
- return adoptRef(new StyleRuleRegion(selectors, adoptRules));
- }
-
- const CSSSelectorList& selectorList() const { return m_selectorList; }
-
- PassRefPtr<StyleRuleRegion> copy() const { return adoptRef(new StyleRuleRegion(*this)); }
-
-private:
- StyleRuleRegion(Vector<OwnPtr<CSSParserSelector> >*, Vector<RefPtr<StyleRuleBase> >& adoptRules);
- StyleRuleRegion(const StyleRuleRegion&);
-
- CSSSelectorList m_selectorList;
-};
-
class StyleRuleViewport : public StyleRuleBase {
public:
- static PassRefPtr<StyleRuleViewport> create() { return adoptRef(new StyleRuleViewport); }
+ static PassRefPtrWillBeRawPtr<StyleRuleViewport> create() { return adoptRefWillBeNoop(new StyleRuleViewport); }
~StyleRuleViewport();
- const StylePropertySet* properties() const { return m_properties.get(); }
- MutableStylePropertySet* mutableProperties();
+ const StylePropertySet& properties() const { return *m_properties; }
+ MutableStylePropertySet& mutableProperties();
void setProperties(PassRefPtr<StylePropertySet>);
- PassRefPtr<StyleRuleViewport> copy() const { return adoptRef(new StyleRuleViewport(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRuleViewport> copy() const { return adoptRefWillBeNoop(new StyleRuleViewport(*this)); }
+
+ void traceAfterDispatch(Visitor* visitor) { StyleRuleBase::traceAfterDispatch(visitor); }
private:
StyleRuleViewport();
StyleRuleViewport(const StyleRuleViewport&);
- RefPtr<StylePropertySet> m_properties;
+ RefPtr<StylePropertySet> m_properties; // Cannot be null
};
class StyleRuleFilter : public StyleRuleBase {
public:
- static PassRefPtr<StyleRuleFilter> create(const String& filterName) { return adoptRef(new StyleRuleFilter(filterName)); }
+ static PassRefPtrWillBeRawPtr<StyleRuleFilter> create(const String& filterName) { return adoptRefWillBeNoop(new StyleRuleFilter(filterName)); }
~StyleRuleFilter();
const String& filterName() const { return m_filterName; }
- const StylePropertySet* properties() const { return m_properties.get(); }
- MutableStylePropertySet* mutableProperties();
+ const StylePropertySet& properties() const { return *m_properties; }
+ MutableStylePropertySet& mutableProperties();
void setProperties(PassRefPtr<StylePropertySet>);
- PassRefPtr<StyleRuleFilter> copy() const { return adoptRef(new StyleRuleFilter(*this)); }
+ PassRefPtrWillBeRawPtr<StyleRuleFilter> copy() const { return adoptRefWillBeNoop(new StyleRuleFilter(*this)); }
+
+ void traceAfterDispatch(Visitor* visitor) { StyleRuleBase::traceAfterDispatch(visitor); }
private:
StyleRuleFilter(const String&);
@@ -285,7 +288,6 @@ DEFINE_STYLE_RULE_TYPE_CASTS(FontFace);
DEFINE_STYLE_RULE_TYPE_CASTS(Page);
DEFINE_STYLE_RULE_TYPE_CASTS(Media);
DEFINE_STYLE_RULE_TYPE_CASTS(Supports);
-DEFINE_STYLE_RULE_TYPE_CASTS(Region);
DEFINE_STYLE_RULE_TYPE_CASTS(Viewport);
DEFINE_STYLE_RULE_TYPE_CASTS(Filter);
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.cpp b/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.cpp
index aff60cb9ecd..13fd117ca58 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.cpp
@@ -22,7 +22,7 @@
#include "config.h"
#include "core/css/StyleRuleImport.h"
-#include "FetchInitiatorTypeNames.h"
+#include "core/FetchInitiatorTypeNames.h"
#include "core/css/StyleSheetContents.h"
#include "core/dom/Document.h"
#include "core/fetch/CSSStyleSheetResource.h"
@@ -31,14 +31,14 @@
namespace WebCore {
-PassRefPtr<StyleRuleImport> StyleRuleImport::create(const String& href, PassRefPtr<MediaQuerySet> media)
+PassRefPtrWillBeRawPtr<StyleRuleImport> StyleRuleImport::create(const String& href, PassRefPtrWillBeRawPtr<MediaQuerySet> media)
{
- return adoptRef(new StyleRuleImport(href, media));
+ return adoptRefWillBeNoop(new StyleRuleImport(href, media));
}
-StyleRuleImport::StyleRuleImport(const String& href, PassRefPtr<MediaQuerySet> media)
+StyleRuleImport::StyleRuleImport(const String& href, PassRefPtrWillBeRawPtr<MediaQuerySet> media)
: StyleRuleBase(Import)
- , m_parentStyleSheet(0)
+ , m_parentStyleSheet(nullptr)
, m_styleSheetClient(this)
, m_strHref(href)
, m_mediaQueries(media)
@@ -51,25 +51,38 @@ StyleRuleImport::StyleRuleImport(const String& href, PassRefPtr<MediaQuerySet> m
StyleRuleImport::~StyleRuleImport()
{
+#if !ENABLE(OILPAN)
if (m_styleSheet)
m_styleSheet->clearOwnerRule();
+#endif
if (m_resource)
m_resource->removeClient(&m_styleSheetClient);
}
+void StyleRuleImport::traceAfterDispatch(Visitor* visitor)
+{
+ visitor->trace(m_parentStyleSheet);
+ visitor->trace(m_mediaQueries);
+ visitor->trace(m_styleSheet);
+ StyleRuleBase::traceAfterDispatch(visitor);
+}
+
void StyleRuleImport::setCSSStyleSheet(const String& href, const KURL& baseURL, const String& charset, const CSSStyleSheetResource* cachedStyleSheet)
{
if (m_styleSheet)
m_styleSheet->clearOwnerRule();
- CSSParserContext context = m_parentStyleSheet ? m_parentStyleSheet->parserContext() : HTMLStandardMode;
+ CSSParserContext context = m_parentStyleSheet ? m_parentStyleSheet->parserContext() : strictCSSParserContext();
context.setCharset(charset);
- if (!baseURL.isNull())
+ Document* document = m_parentStyleSheet ? m_parentStyleSheet->singleOwnerDocument() : 0;
+ if (!baseURL.isNull()) {
context.setBaseURL(baseURL);
+ if (document)
+ context.setReferrer(Referrer(baseURL.strippedForUseAsReferrer(), document->referrerPolicy()));
+ }
m_styleSheet = StyleSheetContents::create(this, href, context);
- Document* document = m_parentStyleSheet ? m_parentStyleSheet->singleOwnerDocument() : 0;
m_styleSheet->parseAuthorStyleSheet(cachedStyleSheet, document ? document->securityOrigin() : 0);
m_loading = false;
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.h b/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.h
index 8af664e2438..e67f7120a0c 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleRuleImport.h
@@ -25,6 +25,7 @@
#include "core/css/StyleRule.h"
#include "core/fetch/ResourcePtr.h"
#include "core/fetch/StyleSheetResourceClient.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -33,15 +34,15 @@ class MediaQuerySet;
class StyleSheetContents;
class StyleRuleImport : public StyleRuleBase {
- WTF_MAKE_FAST_ALLOCATED;
+ WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
- static PassRefPtr<StyleRuleImport> create(const String& href, PassRefPtr<MediaQuerySet>);
+ static PassRefPtrWillBeRawPtr<StyleRuleImport> create(const String& href, PassRefPtrWillBeRawPtr<MediaQuerySet>);
~StyleRuleImport();
StyleSheetContents* parentStyleSheet() const { return m_parentStyleSheet; }
void setParentStyleSheet(StyleSheetContents* sheet) { ASSERT(sheet); m_parentStyleSheet = sheet; }
- void clearParentStyleSheet() { m_parentStyleSheet = 0; }
+ void clearParentStyleSheet() { m_parentStyleSheet = nullptr; }
String href() const { return m_strHref; }
StyleSheetContents* styleSheet() const { return m_styleSheet.get(); }
@@ -51,14 +52,17 @@ public:
void requestStyleSheet();
+ void traceAfterDispatch(Visitor*);
+
private:
+ // FIXME: inherit from StyleSheetResourceClient directly to eliminate raw back pointer, as there are no space savings in this.
// NOTE: We put the StyleSheetResourceClient in a member instead of inheriting from it
// to avoid adding a vptr to StyleRuleImport.
- class ImportedStyleSheetClient : public StyleSheetResourceClient {
+ class ImportedStyleSheetClient FINAL : public StyleSheetResourceClient {
public:
ImportedStyleSheetClient(StyleRuleImport* ownerRule) : m_ownerRule(ownerRule) { }
virtual ~ImportedStyleSheetClient() { }
- virtual void setCSSStyleSheet(const String& href, const KURL& baseURL, const String& charset, const CSSStyleSheetResource* sheet)
+ virtual void setCSSStyleSheet(const String& href, const KURL& baseURL, const String& charset, const CSSStyleSheetResource* sheet) OVERRIDE
{
m_ownerRule->setCSSStyleSheet(href, baseURL, charset, sheet);
}
@@ -69,14 +73,14 @@ private:
void setCSSStyleSheet(const String& href, const KURL& baseURL, const String& charset, const CSSStyleSheetResource*);
friend class ImportedStyleSheetClient;
- StyleRuleImport(const String& href, PassRefPtr<MediaQuerySet>);
+ StyleRuleImport(const String& href, PassRefPtrWillBeRawPtr<MediaQuerySet>);
- StyleSheetContents* m_parentStyleSheet;
+ RawPtrWillBeMember<StyleSheetContents> m_parentStyleSheet;
ImportedStyleSheetClient m_styleSheetClient;
String m_strHref;
- RefPtr<MediaQuerySet> m_mediaQueries;
- RefPtr<StyleSheetContents> m_styleSheet;
+ RefPtrWillBeMember<MediaQuerySet> m_mediaQueries;
+ RefPtrWillBeMember<StyleSheetContents> m_styleSheet;
ResourcePtr<CSSStyleSheetResource> m_resource;
bool m_loading;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheet.h b/chromium/third_party/WebKit/Source/core/css/StyleSheet.h
index 2207b5a006c..136fa1d4ba9 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheet.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheet.h
@@ -22,6 +22,7 @@
#define StyleSheet_h
#include "core/css/CSSParserMode.h"
+#include "platform/heap/Handle.h"
#include "wtf/Forward.h"
#include "wtf/RefCounted.h"
@@ -33,7 +34,7 @@ class MediaList;
class Node;
class StyleSheet;
-class StyleSheet : public RefCounted<StyleSheet> {
+class StyleSheet : public RefCountedWillBeGarbageCollectedFinalized<StyleSheet> {
public:
virtual ~StyleSheet();
@@ -51,6 +52,8 @@ public:
virtual KURL baseURL() const = 0;
virtual bool isLoading() const = 0;
virtual bool isCSSStyleSheet() const { return false; }
+
+ virtual void trace(Visitor*) { }
};
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheet.idl b/chromium/third_party/WebKit/Source/core/css/StyleSheet.idl
index e3e13b37b1d..ed83f144757 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheet.idl
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheet.idl
@@ -21,7 +21,8 @@
// Introduced in DOM Level 2:
[
Custom=Wrap,
- GenerateVisitDOMWrapper=ownerNode,
+ SetWrapperReferenceFrom=ownerNode,
+ WillBeGarbageCollected
] interface StyleSheet {
[TreatReturnedNullStringAs=Null] readonly attribute DOMString type;
attribute boolean disabled;
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.cpp b/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.cpp
index fa7b022da58..2b3da24942a 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.cpp
@@ -21,16 +21,17 @@
#include "config.h"
#include "core/css/StyleSheetContents.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSStyleSheet.h"
#include "core/css/MediaList.h"
#include "core/css/StylePropertySet.h"
#include "core/css/StyleRule.h"
#include "core/css/StyleRuleImport.h"
-#include "core/css/resolver/StyleResolver.h"
+#include "core/dom/Document.h"
#include "core/dom/Node.h"
#include "core/dom/StyleEngine.h"
#include "core/fetch/CSSStyleSheetResource.h"
+#include "core/frame/UseCounter.h"
#include "platform/TraceEvent.h"
#include "platform/weborigin/SecurityOrigin.h"
#include "wtf/Deque.h"
@@ -44,7 +45,7 @@ unsigned StyleSheetContents::estimatedSizeInBytes() const
// The assumption is that nearly all of of them are atomic and would exist anyway.
unsigned size = sizeof(*this);
- // FIXME: This ignores the children of media and region rules.
+ // FIXME: This ignores the children of media rules.
// Most rules are StyleRules.
size += ruleCount() * StyleRule::averageSizeInBytes();
@@ -58,32 +59,33 @@ unsigned StyleSheetContents::estimatedSizeInBytes() const
StyleSheetContents::StyleSheetContents(StyleRuleImport* ownerRule, const String& originalURL, const CSSParserContext& context)
: m_ownerRule(ownerRule)
, m_originalURL(originalURL)
- , m_loadCompleted(false)
, m_hasSyntacticallyValidCSSHeader(true)
, m_didLoadErrorOccur(false)
, m_usesRemUnits(false)
, m_isMutable(false)
, m_isInMemoryCache(false)
, m_hasFontFaceRule(false)
+ , m_hasMediaQueries(false)
+ , m_hasSingleOwnerDocument(true)
, m_parserContext(context)
{
}
StyleSheetContents::StyleSheetContents(const StyleSheetContents& o)
- : RefCounted<StyleSheetContents>()
- , m_ownerRule(0)
+ : m_ownerRule(nullptr)
, m_originalURL(o.m_originalURL)
, m_encodingFromCharsetRule(o.m_encodingFromCharsetRule)
, m_importRules(o.m_importRules.size())
, m_childRules(o.m_childRules.size())
, m_namespaces(o.m_namespaces)
- , m_loadCompleted(true)
, m_hasSyntacticallyValidCSSHeader(o.m_hasSyntacticallyValidCSSHeader)
, m_didLoadErrorOccur(false)
, m_usesRemUnits(o.m_usesRemUnits)
, m_isMutable(false)
, m_isInMemoryCache(false)
, m_hasFontFaceRule(o.m_hasFontFaceRule)
+ , m_hasMediaQueries(o.m_hasMediaQueries)
+ , m_hasSingleOwnerDocument(true)
, m_parserContext(o.m_parserContext)
{
ASSERT(o.isCacheable());
@@ -97,11 +99,25 @@ StyleSheetContents::StyleSheetContents(const StyleSheetContents& o)
StyleSheetContents::~StyleSheetContents()
{
+#if !ENABLE(OILPAN)
clearRules();
+#endif
+}
+
+void StyleSheetContents::setHasSyntacticallyValidCSSHeader(bool isValidCss)
+{
+ if (!isValidCss) {
+ if (Document* document = clientSingleOwnerDocument())
+ removeSheetFromCache(document);
+ }
+ m_hasSyntacticallyValidCSSHeader = isValidCss;
}
bool StyleSheetContents::isCacheable() const
{
+ // This would require dealing with multiple clients for load callbacks.
+ if (!loadCompleted())
+ return false;
// FIXME: StyleSheets with media queries can't be cached because their RuleSet
// is processed differently based off the media queries, which might resolve
// differently depending on the context of the parent CSSStyleSheet (e.g.
@@ -115,9 +131,6 @@ bool StyleSheetContents::isCacheable() const
// FIXME: Support cached stylesheets in import rules.
if (m_ownerRule)
return false;
- // This would require dealing with multiple clients for load callbacks.
- if (!m_loadCompleted)
- return false;
if (m_didLoadErrorOccur)
return false;
// It is not the original sheet anymore.
@@ -130,7 +143,7 @@ bool StyleSheetContents::isCacheable() const
return true;
}
-void StyleSheetContents::parserAppendRule(PassRefPtr<StyleRuleBase> rule)
+void StyleSheetContents::parserAppendRule(PassRefPtrWillBeRawPtr<StyleRuleBase> rule)
{
ASSERT(!rule->isCharsetRule());
if (rule->isImportRule()) {
@@ -210,7 +223,7 @@ void StyleSheetContents::parserSetEncodingFromCharsetRule(const String& encoding
m_encodingFromCharsetRule = encoding;
}
-bool StyleSheetContents::wrapperInsertRule(PassRefPtr<StyleRuleBase> rule, unsigned index)
+bool StyleSheetContents::wrapperInsertRule(PassRefPtrWillBeRawPtr<StyleRuleBase> rule, unsigned index)
{
ASSERT(m_isMutable);
ASSERT_WITH_SECURITY_IMPLICATION(index <= ruleCount());
@@ -251,6 +264,8 @@ bool StyleSheetContents::wrapperInsertRule(PassRefPtr<StyleRuleBase> rule, unsig
childVectorIndex -= m_importRules.size();
+ if (rule->isFontFaceRule())
+ setHasFontFaceRule(true);
m_childRules.insert(childVectorIndex, rule);
return true;
}
@@ -270,11 +285,15 @@ void StyleSheetContents::wrapperDeleteRule(unsigned index)
}
if (childVectorIndex < m_importRules.size()) {
m_importRules[childVectorIndex]->clearParentStyleSheet();
+ if (m_importRules[childVectorIndex]->isFontFaceRule())
+ notifyRemoveFontFaceRule(toStyleRuleFontFace(m_importRules[childVectorIndex].get()));
m_importRules.remove(childVectorIndex);
return;
}
childVectorIndex -= m_importRules.size();
+ if (m_childRules[childVectorIndex]->isFontFaceRule())
+ notifyRemoveFontFaceRule(toStyleRuleFontFace(m_childRules[childVectorIndex].get()));
m_childRules.remove(childVectorIndex);
}
@@ -285,7 +304,7 @@ void StyleSheetContents::parserAddNamespace(const AtomicString& prefix, const At
PrefixNamespaceURIMap::AddResult result = m_namespaces.add(prefix, uri);
if (result.isNewEntry)
return;
- result.iterator->value = uri;
+ result.storedValue->value = uri;
}
const AtomicString& StyleSheetContents::determineNamespace(const AtomicString& prefix)
@@ -307,7 +326,8 @@ void StyleSheetContents::parseAuthorStyleSheet(const CSSStyleSheetResource* cach
bool hasValidMIMEType = false;
String sheetText = cachedStyleSheet->sheetText(enforceMIMEType, &hasValidMIMEType);
- CSSParser p(parserContext(), UseCounter::getFrom(this));
+ CSSParserContext context(parserContext(), UseCounter::getFrom(this));
+ BisonCSSParser p(context);
p.parseSheet(this, sheetText, TextPosition::minimumPosition(), 0, true);
// If we're loading a stylesheet cross-origin, and the MIME type is not standard, require the CSS
@@ -329,7 +349,8 @@ bool StyleSheetContents::parseString(const String& sheetText)
bool StyleSheetContents::parseStringAtPosition(const String& sheetText, const TextPosition& startPosition, bool createdByParser)
{
- CSSParser p(parserContext(), UseCounter::getFrom(this));
+ CSSParserContext context(parserContext(), UseCounter::getFrom(this));
+ BisonCSSParser p(context);
p.parseSheet(this, sheetText, startPosition, 0, createdByParser);
return true;
@@ -344,6 +365,16 @@ bool StyleSheetContents::isLoading() const
return false;
}
+bool StyleSheetContents::loadCompleted() const
+{
+ StyleSheetContents* parentSheet = parentStyleSheet();
+ if (parentSheet)
+ return parentSheet->loadCompleted();
+
+ StyleSheetContents* root = rootStyleSheet();
+ return root->m_loadingClients.isEmpty();
+}
+
void StyleSheetContents::checkLoaded()
{
if (isLoading())
@@ -352,22 +383,39 @@ void StyleSheetContents::checkLoaded()
// Avoid |this| being deleted by scripts that run via
// ScriptableDocumentParser::executeScriptsWaitingForResources().
// See https://bugs.webkit.org/show_bug.cgi?id=95106
- RefPtr<StyleSheetContents> protect(this);
+ RefPtrWillBeRawPtr<StyleSheetContents> protect(this);
StyleSheetContents* parentSheet = parentStyleSheet();
if (parentSheet) {
parentSheet->checkLoaded();
- m_loadCompleted = true;
return;
}
- RefPtr<Node> ownerNode = singleOwnerNode();
- if (!ownerNode) {
- m_loadCompleted = true;
+
+ StyleSheetContents* root = rootStyleSheet();
+ if (root->m_loadingClients.isEmpty())
return;
+
+ // Avoid |CSSSStyleSheet| and |ownerNode| being deleted by scripts that run via
+ // ScriptableDocumentParser::executeScriptsWaitingForResources(). Also protect
+ // the |CSSStyleSheet| from being deleted during iteration via the |sheetLoaded|
+ // method.
+ //
+ // When a sheet is loaded it is moved from the set of loading clients
+ // to the set of completed clients. We therefore need the copy in order to
+ // not modify the set while iterating it.
+ WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> > loadingClients;
+ copyToVector(m_loadingClients, loadingClients);
+
+ for (unsigned i = 0; i < loadingClients.size(); ++i) {
+ if (loadingClients[i]->loadCompleted())
+ continue;
+
+ // sheetLoaded might be invoked after its owner node is removed from document.
+ if (RefPtrWillBeRawPtr<Node> ownerNode = loadingClients[i]->ownerNode()) {
+ if (loadingClients[i]->sheetLoaded())
+ ownerNode->notifyLoadedSheetAndAllCriticalSubresources(m_didLoadErrorOccur);
+ }
}
- m_loadCompleted = ownerNode->sheetLoaded();
- if (m_loadCompleted)
- ownerNode->notifyLoadedSheetAndAllCriticalSubresources(m_didLoadErrorOccur);
}
void StyleSheetContents::notifyLoadedSheet(const CSSStyleSheetResource* sheet)
@@ -382,8 +430,18 @@ void StyleSheetContents::notifyLoadedSheet(const CSSStyleSheetResource* sheet)
void StyleSheetContents::startLoadingDynamicSheet()
{
- if (Node* owner = singleOwnerNode())
- owner->startLoadingDynamicSheet();
+ StyleSheetContents* root = rootStyleSheet();
+ for (ClientsIterator it = root->m_loadingClients.begin(); it != root->m_loadingClients.end(); ++it)
+ (*it)->startLoadingDynamicSheet();
+ // Copy the completed clients to a vector for iteration.
+ // startLoadingDynamicSheet will move the style sheet from the
+ // completed state to the loading state which modifies the set of
+ // completed clients. We therefore need the copy in order to not
+ // modify the set of completed clients while iterating it.
+ WillBeHeapVector<RawPtrWillBeMember<CSSStyleSheet> > completedClients;
+ copyToVector(root->m_completedClients, completedClients);
+ for (unsigned i = 0; i < completedClients.size(); ++i)
+ completedClients[i]->startLoadingDynamicSheet();
}
StyleSheetContents* StyleSheetContents::rootStyleSheet() const
@@ -396,78 +454,48 @@ StyleSheetContents* StyleSheetContents::rootStyleSheet() const
bool StyleSheetContents::hasSingleOwnerNode() const
{
- StyleSheetContents* root = rootStyleSheet();
- if (root->m_clients.isEmpty())
- return false;
- return root->m_clients.size() == 1;
+ return rootStyleSheet()->hasOneClient();
}
Node* StyleSheetContents::singleOwnerNode() const
{
StyleSheetContents* root = rootStyleSheet();
- if (root->m_clients.isEmpty())
+ if (!root->hasOneClient())
return 0;
- ASSERT(root->m_clients.size() == 1);
- return root->m_clients[0]->ownerNode();
+ if (root->m_loadingClients.size())
+ return (*root->m_loadingClients.begin())->ownerNode();
+ return (*root->m_completedClients.begin())->ownerNode();
}
Document* StyleSheetContents::singleOwnerDocument() const
{
- Node* ownerNode = singleOwnerNode();
- return ownerNode ? &ownerNode->document() : 0;
+ StyleSheetContents* root = rootStyleSheet();
+ return root->clientSingleOwnerDocument();
}
KURL StyleSheetContents::completeURL(const String& url) const
{
- return CSSParser::completeURL(m_parserContext, url);
+ // FIXME: This is only OK when we have a singleOwnerNode, right?
+ return m_parserContext.completeURL(url);
}
-void StyleSheetContents::addSubresourceStyleURLs(ListHashSet<KURL>& urls)
-{
- Deque<StyleSheetContents*> styleSheetQueue;
- styleSheetQueue.append(this);
-
- while (!styleSheetQueue.isEmpty()) {
- StyleSheetContents* styleSheet = styleSheetQueue.takeFirst();
-
- for (unsigned i = 0; i < styleSheet->m_importRules.size(); ++i) {
- StyleRuleImport* importRule = styleSheet->m_importRules[i].get();
- if (importRule->styleSheet()) {
- styleSheetQueue.append(importRule->styleSheet());
- addSubresourceURL(urls, importRule->styleSheet()->baseURL());
- }
- }
- for (unsigned i = 0; i < styleSheet->m_childRules.size(); ++i) {
- StyleRuleBase* rule = styleSheet->m_childRules[i].get();
- if (rule->isStyleRule())
- toStyleRule(rule)->properties()->addSubresourceStyleURLs(urls, this);
- else if (rule->isFontFaceRule())
- toStyleRuleFontFace(rule)->properties()->addSubresourceStyleURLs(urls, this);
- }
- }
-}
-
-static bool childRulesHaveFailedOrCanceledSubresources(const Vector<RefPtr<StyleRuleBase> >& rules)
+static bool childRulesHaveFailedOrCanceledSubresources(const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& rules)
{
for (unsigned i = 0; i < rules.size(); ++i) {
const StyleRuleBase* rule = rules[i].get();
switch (rule->type()) {
case StyleRuleBase::Style:
- if (toStyleRule(rule)->properties()->hasFailedOrCanceledSubresources())
+ if (toStyleRule(rule)->properties().hasFailedOrCanceledSubresources())
return true;
break;
case StyleRuleBase::FontFace:
- if (toStyleRuleFontFace(rule)->properties()->hasFailedOrCanceledSubresources())
+ if (toStyleRuleFontFace(rule)->properties().hasFailedOrCanceledSubresources())
return true;
break;
case StyleRuleBase::Media:
if (childRulesHaveFailedOrCanceledSubresources(toStyleRuleMedia(rule)->childRules()))
return true;
break;
- case StyleRuleBase::Region:
- if (childRulesHaveFailedOrCanceledSubresources(toStyleRuleRegion(rule)->childRules()))
- return true;
- break;
case StyleRuleBase::Import:
ASSERT_NOT_REACHED();
case StyleRuleBase::Page:
@@ -490,6 +518,16 @@ bool StyleSheetContents::hasFailedOrCanceledSubresources() const
return childRulesHaveFailedOrCanceledSubresources(m_childRules);
}
+Document* StyleSheetContents::clientSingleOwnerDocument() const
+{
+ if (!m_hasSingleOwnerDocument || clientSize() <= 0)
+ return 0;
+
+ if (m_loadingClients.size())
+ return (*m_loadingClients.begin())->ownerDocument();
+ return (*m_completedClients.begin())->ownerDocument();
+}
+
StyleSheetContents* StyleSheetContents::parentStyleSheet() const
{
return m_ownerRule ? m_ownerRule->parentStyleSheet() : 0;
@@ -497,15 +535,55 @@ StyleSheetContents* StyleSheetContents::parentStyleSheet() const
void StyleSheetContents::registerClient(CSSStyleSheet* sheet)
{
- ASSERT(!m_clients.contains(sheet));
- m_clients.append(sheet);
+ ASSERT(!m_loadingClients.contains(sheet) && !m_completedClients.contains(sheet));
+
+ // InspectorCSSAgent::buildObjectForRule creates CSSStyleSheet without any owner node.
+ if (!sheet->ownerDocument())
+ return;
+
+ if (Document* document = clientSingleOwnerDocument()) {
+ if (sheet->ownerDocument() != document)
+ m_hasSingleOwnerDocument = false;
+ }
+ m_loadingClients.add(sheet);
}
void StyleSheetContents::unregisterClient(CSSStyleSheet* sheet)
{
- size_t position = m_clients.find(sheet);
- ASSERT(position != kNotFound);
- m_clients.remove(position);
+ m_loadingClients.remove(sheet);
+ m_completedClients.remove(sheet);
+
+ if (!sheet->ownerDocument() || !m_loadingClients.isEmpty() || !m_completedClients.isEmpty())
+ return;
+
+ if (m_hasSingleOwnerDocument)
+ removeSheetFromCache(sheet->ownerDocument());
+ m_hasSingleOwnerDocument = true;
+}
+
+void StyleSheetContents::clientLoadCompleted(CSSStyleSheet* sheet)
+{
+ ASSERT(m_loadingClients.contains(sheet) || !sheet->ownerDocument());
+ m_loadingClients.remove(sheet);
+ // In m_ownerNode->sheetLoaded, the CSSStyleSheet might be detached.
+ // (i.e. clearOwnerNode was invoked.)
+ // In this case, we don't need to add the stylesheet to completed clients.
+ if (!sheet->ownerDocument())
+ return;
+ m_completedClients.add(sheet);
+}
+
+void StyleSheetContents::clientLoadStarted(CSSStyleSheet* sheet)
+{
+ ASSERT(m_completedClients.contains(sheet));
+ m_completedClients.remove(sheet);
+ m_loadingClients.add(sheet);
+}
+
+void StyleSheetContents::removeSheetFromCache(Document* document)
+{
+ ASSERT(document);
+ document->styleEngine()->removeSheet(this);
}
void StyleSheetContents::addedToMemoryCache()
@@ -537,6 +615,14 @@ RuleSet& StyleSheetContents::ensureRuleSet(const MediaQueryEvaluator& medium, Ad
return *m_ruleSet.get();
}
+static void clearResolvers(WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> >& clients)
+{
+ for (WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> >::iterator it = clients.begin(); it != clients.end(); ++it) {
+ if (Document* document = (*it)->ownerDocument())
+ document->styleEngine()->clearResolver();
+ }
+}
+
void StyleSheetContents::clearRuleSet()
{
if (StyleSheetContents* parentSheet = parentStyleSheet())
@@ -550,12 +636,61 @@ void StyleSheetContents::clearRuleSet()
// Clearing the ruleSet means we need to recreate the styleResolver data structures.
// See the StyleResolver calls in ScopedStyleResolver::addRulesFromSheet.
- for (size_t i = 0; i < m_clients.size(); ++i) {
- if (Document* document = m_clients[i]->ownerDocument())
- document->styleEngine()->clearResolver();
- }
+ clearResolvers(m_loadingClients);
+ clearResolvers(m_completedClients);
m_ruleSet.clear();
}
+static void removeFontFaceRules(WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> >& clients, const StyleRuleFontFace* fontFaceRule)
+{
+ for (WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> >::iterator it = clients.begin(); it != clients.end(); ++it) {
+ if (Node* ownerNode = (*it)->ownerNode())
+ ownerNode->document().styleEngine()->removeFontFaceRules(WillBeHeapVector<RawPtrWillBeMember<const StyleRuleFontFace> >(1, fontFaceRule));
+ }
+}
+
+void StyleSheetContents::notifyRemoveFontFaceRule(const StyleRuleFontFace* fontFaceRule)
+{
+ StyleSheetContents* root = rootStyleSheet();
+ removeFontFaceRules(root->m_loadingClients, fontFaceRule);
+ removeFontFaceRules(root->m_completedClients, fontFaceRule);
+}
+
+static void findFontFaceRulesFromRules(const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& rules, WillBeHeapVector<RawPtrWillBeMember<const StyleRuleFontFace> >& fontFaceRules)
+{
+ for (unsigned i = 0; i < rules.size(); ++i) {
+ StyleRuleBase* rule = rules[i].get();
+
+ if (rule->isFontFaceRule()) {
+ fontFaceRules.append(toStyleRuleFontFace(rule));
+ } else if (rule->isMediaRule()) {
+ StyleRuleMedia* mediaRule = toStyleRuleMedia(rule);
+ // We cannot know whether the media rule matches or not, but
+ // for safety, remove @font-face in the media rule (if exists).
+ findFontFaceRulesFromRules(mediaRule->childRules(), fontFaceRules);
+ }
+ }
+}
+
+void StyleSheetContents::findFontFaceRules(WillBeHeapVector<RawPtrWillBeMember<const StyleRuleFontFace> >& fontFaceRules)
+{
+ for (unsigned i = 0; i < m_importRules.size(); ++i) {
+ if (!m_importRules[i]->styleSheet())
+ continue;
+ m_importRules[i]->styleSheet()->findFontFaceRules(fontFaceRules);
+ }
+
+ findFontFaceRulesFromRules(childRules(), fontFaceRules);
+}
+
+void StyleSheetContents::trace(Visitor* visitor)
+{
+ visitor->trace(m_ownerRule);
+ visitor->trace(m_importRules);
+ visitor->trace(m_childRules);
+ visitor->trace(m_loadingClients);
+ visitor->trace(m_completedClients);
+ visitor->trace(m_ruleSet);
+}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.h b/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.h
index 7d59d80ef93..7dca729d02b 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheetContents.h
@@ -23,6 +23,7 @@
#include "core/css/CSSParserMode.h"
#include "core/css/RuleSet.h"
+#include "platform/heap/Handle.h"
#include "platform/weborigin/KURL.h"
#include "wtf/HashMap.h"
#include "wtf/ListHashSet.h"
@@ -41,21 +42,22 @@ class Document;
class Node;
class SecurityOrigin;
class StyleRuleBase;
+class StyleRuleFontFace;
class StyleRuleImport;
-class StyleSheetContents : public RefCounted<StyleSheetContents> {
+class StyleSheetContents : public RefCountedWillBeGarbageCollectedFinalized<StyleSheetContents> {
public:
- static PassRefPtr<StyleSheetContents> create(const CSSParserContext& context = CSSParserContext(HTMLStandardMode))
+ static PassRefPtrWillBeRawPtr<StyleSheetContents> create(const CSSParserContext& context)
{
- return adoptRef(new StyleSheetContents(0, String(), context));
+ return adoptRefWillBeNoop(new StyleSheetContents(0, String(), context));
}
- static PassRefPtr<StyleSheetContents> create(const String& originalURL, const CSSParserContext& context)
+ static PassRefPtrWillBeRawPtr<StyleSheetContents> create(const String& originalURL, const CSSParserContext& context)
{
- return adoptRef(new StyleSheetContents(0, originalURL, context));
+ return adoptRefWillBeNoop(new StyleSheetContents(0, originalURL, context));
}
- static PassRefPtr<StyleSheetContents> create(StyleRuleImport* ownerRule, const String& originalURL, const CSSParserContext& context)
+ static PassRefPtrWillBeRawPtr<StyleSheetContents> create(StyleRuleImport* ownerRule, const String& originalURL, const CSSParserContext& context)
{
- return adoptRef(new StyleSheetContents(ownerRule, originalURL, context));
+ return adoptRefWillBeNoop(new StyleSheetContents(ownerRule, originalURL, context));
}
~StyleSheetContents();
@@ -82,20 +84,20 @@ public:
const String& charset() const { return m_parserContext.charset(); }
- bool loadCompleted() const { return m_loadCompleted; }
+ bool loadCompleted() const;
bool hasFailedOrCanceledSubresources() const;
KURL completeURL(const String& url) const;
- void addSubresourceStyleURLs(ListHashSet<KURL>&);
- void setHasSyntacticallyValidCSSHeader(bool b) { m_hasSyntacticallyValidCSSHeader = b; }
+ void setHasSyntacticallyValidCSSHeader(bool isValidCss);
bool hasSyntacticallyValidCSSHeader() const { return m_hasSyntacticallyValidCSSHeader; }
void setHasFontFaceRule(bool b) { m_hasFontFaceRule = b; }
bool hasFontFaceRule() const { return m_hasFontFaceRule; }
+ void findFontFaceRules(WillBeHeapVector<RawPtrWillBeMember<const StyleRuleFontFace> >& fontFaceRules);
void parserAddNamespace(const AtomicString& prefix, const AtomicString& uri);
- void parserAppendRule(PassRefPtr<StyleRuleBase>);
+ void parserAppendRule(PassRefPtrWillBeRawPtr<StyleRuleBase>);
void parserSetEncodingFromCharsetRule(const String& encoding);
void parserSetUsesRemUnits(bool b) { m_usesRemUnits = b; }
@@ -104,14 +106,14 @@ public:
bool hasCharsetRule() const { return !m_encodingFromCharsetRule.isNull(); }
String encodingFromCharsetRule() const { return m_encodingFromCharsetRule; }
// Rules other than @charset and @import.
- const Vector<RefPtr<StyleRuleBase> >& childRules() const { return m_childRules; }
- const Vector<RefPtr<StyleRuleImport> >& importRules() const { return m_importRules; }
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& childRules() const { return m_childRules; }
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleImport> >& importRules() const { return m_importRules; }
void notifyLoadedSheet(const CSSStyleSheetResource*);
StyleSheetContents* parentStyleSheet() const;
StyleRuleImport* ownerRule() const { return m_ownerRule; }
- void clearOwnerRule() { m_ownerRule = 0; }
+ void clearOwnerRule() { m_ownerRule = nullptr; }
// Note that href is the URL that started the redirect chain that led to
// this style sheet. This property probably isn't useful for much except
@@ -126,47 +128,60 @@ public:
unsigned estimatedSizeInBytes() const;
- bool wrapperInsertRule(PassRefPtr<StyleRuleBase>, unsigned index);
+ bool wrapperInsertRule(PassRefPtrWillBeRawPtr<StyleRuleBase>, unsigned index);
void wrapperDeleteRule(unsigned index);
- PassRefPtr<StyleSheetContents> copy() const { return adoptRef(new StyleSheetContents(*this)); }
+ PassRefPtrWillBeRawPtr<StyleSheetContents> copy() const
+ {
+ return adoptRefWillBeNoop(new StyleSheetContents(*this));
+ }
void registerClient(CSSStyleSheet*);
void unregisterClient(CSSStyleSheet*);
- bool hasOneClient() { return m_clients.size() == 1; }
+ size_t clientSize() const { return m_loadingClients.size() + m_completedClients.size(); }
+ bool hasOneClient() { return clientSize() == 1; }
+ void clientLoadCompleted(CSSStyleSheet*);
+ void clientLoadStarted(CSSStyleSheet*);
bool isMutable() const { return m_isMutable; }
void setMutable() { m_isMutable = true; }
+ void removeSheetFromCache(Document*);
+
bool isInMemoryCache() const { return m_isInMemoryCache; }
void addedToMemoryCache();
void removedFromMemoryCache();
void setHasMediaQueries();
- bool hasMediaQueries() { return m_hasMediaQueries; }
+ bool hasMediaQueries() const { return m_hasMediaQueries; }
+
+ bool didLoadErrorOccur() const { return m_didLoadErrorOccur; }
void shrinkToFit();
RuleSet& ruleSet() { ASSERT(m_ruleSet); return *m_ruleSet.get(); }
RuleSet& ensureRuleSet(const MediaQueryEvaluator&, AddRuleFlags);
void clearRuleSet();
+ void trace(Visitor*);
+
private:
StyleSheetContents(StyleRuleImport* ownerRule, const String& originalURL, const CSSParserContext&);
StyleSheetContents(const StyleSheetContents&);
+ void notifyRemoveFontFaceRule(const StyleRuleFontFace*);
+ Document* clientSingleOwnerDocument() const;
void clearCharsetRule();
- StyleRuleImport* m_ownerRule;
+ RawPtrWillBeMember<StyleRuleImport> m_ownerRule;
String m_originalURL;
String m_encodingFromCharsetRule;
- Vector<RefPtr<StyleRuleImport> > m_importRules;
- Vector<RefPtr<StyleRuleBase> > m_childRules;
+ WillBeHeapVector<RefPtrWillBeMember<StyleRuleImport> > m_importRules;
+ WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> > m_childRules;
typedef HashMap<AtomicString, AtomicString> PrefixNamespaceURIMap;
PrefixNamespaceURIMap m_namespaces;
- bool m_loadCompleted : 1;
bool m_hasSyntacticallyValidCSSHeader : 1;
bool m_didLoadErrorOccur : 1;
bool m_usesRemUnits : 1;
@@ -174,11 +189,15 @@ private:
bool m_isInMemoryCache : 1;
bool m_hasFontFaceRule : 1;
bool m_hasMediaQueries : 1;
+ bool m_hasSingleOwnerDocument : 1;
CSSParserContext m_parserContext;
- Vector<CSSStyleSheet*> m_clients;
- OwnPtr<RuleSet> m_ruleSet;
+ WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> > m_loadingClients;
+ WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> > m_completedClients;
+ typedef WillBeHeapHashSet<RawPtrWillBeWeakMember<CSSStyleSheet> >::iterator ClientsIterator;
+
+ OwnPtrWillBeMember<RuleSet> m_ruleSet;
};
} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheetList.cpp b/chromium/third_party/WebKit/Source/core/css/StyleSheetList.cpp
index 10f5905ba4e..80714e52a8c 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheetList.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheetList.cpp
@@ -21,7 +21,7 @@
#include "config.h"
#include "core/css/StyleSheetList.h"
-#include "HTMLNames.h"
+#include "core/HTMLNames.h"
#include "core/dom/Document.h"
#include "core/dom/StyleEngine.h"
#include "core/html/HTMLStyleElement.h"
@@ -40,18 +40,22 @@ StyleSheetList::~StyleSheetList()
{
}
-inline const Vector<RefPtr<StyleSheet> >& StyleSheetList::styleSheets()
+inline const WillBeHeapVector<RefPtrWillBeMember<StyleSheet> >& StyleSheetList::styleSheets()
{
+#if !ENABLE(OILPAN)
if (!m_treeScope)
return m_detachedStyleSheets;
+#endif
return document()->styleEngine()->styleSheetsForStyleSheetList(*m_treeScope);
}
+#if !ENABLE(OILPAN)
void StyleSheetList::detachFromDocument()
{
m_detachedStyleSheets = document()->styleEngine()->styleSheetsForStyleSheetList(*m_treeScope);
- m_treeScope = 0;
+ m_treeScope = nullptr;
}
+#endif
unsigned StyleSheetList::length()
{
@@ -60,14 +64,16 @@ unsigned StyleSheetList::length()
StyleSheet* StyleSheetList::item(unsigned index)
{
- const Vector<RefPtr<StyleSheet> >& sheets = styleSheets();
+ const WillBeHeapVector<RefPtrWillBeMember<StyleSheet> >& sheets = styleSheets();
return index < sheets.size() ? sheets[index].get() : 0;
}
HTMLStyleElement* StyleSheetList::getNamedItem(const AtomicString& name) const
{
+#if !ENABLE(OILPAN)
if (!m_treeScope)
return 0;
+#endif
// IE also supports retrieving a stylesheet by name, using the name/id of the <style> tag
// (this is consistent with all the other collections)
@@ -76,9 +82,7 @@ HTMLStyleElement* StyleSheetList::getNamedItem(const AtomicString& name) const
// But unicity of stylesheet ids is good practice anyway ;)
// FIXME: We should figure out if we should change this or fix the spec.
Element* element = m_treeScope->getElementById(name);
- if (element && element->hasTagName(styleTag))
- return toHTMLStyleElement(element);
- return 0;
+ return isHTMLStyleElement(element) ? toHTMLStyleElement(element) : 0;
}
CSSStyleSheet* StyleSheetList::anonymousNamedGetter(const AtomicString& name)
@@ -89,4 +93,9 @@ CSSStyleSheet* StyleSheetList::anonymousNamedGetter(const AtomicString& name)
return item->sheet();
}
+void StyleSheetList::trace(Visitor* visitor)
+{
+ visitor->trace(m_treeScope);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheetList.h b/chromium/third_party/WebKit/Source/core/css/StyleSheetList.h
index c9c15404729..f842183b75d 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheetList.h
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheetList.h
@@ -33,9 +33,9 @@ namespace WebCore {
class HTMLStyleElement;
class StyleSheet;
-class StyleSheetList : public RefCounted<StyleSheetList> {
+class StyleSheetList : public RefCountedWillBeGarbageCollectedFinalized<StyleSheetList> {
public:
- static PassRefPtr<StyleSheetList> create(TreeScope* treeScope) { return adoptRef(new StyleSheetList(treeScope)); }
+ static PassRefPtrWillBeRawPtr<StyleSheetList> create(TreeScope* treeScope) { return adoptRefWillBeNoop(new StyleSheetList(treeScope)); }
~StyleSheetList();
unsigned length();
@@ -43,17 +43,24 @@ public:
HTMLStyleElement* getNamedItem(const AtomicString&) const;
- Document* document() { return m_treeScope->documentScope(); }
+ Document* document() { return m_treeScope ? &m_treeScope->document() : 0; }
+#if !ENABLE(OILPAN)
void detachFromDocument();
+#endif
+
CSSStyleSheet* anonymousNamedGetter(const AtomicString&);
+ void trace(Visitor*);
+
private:
StyleSheetList(TreeScope*);
- const Vector<RefPtr<StyleSheet> >& styleSheets();
+ const WillBeHeapVector<RefPtrWillBeMember<StyleSheet> >& styleSheets();
- TreeScope* m_treeScope;
+ RawPtrWillBeMember<TreeScope> m_treeScope;
+#if !ENABLE(OILPAN)
Vector<RefPtr<StyleSheet> > m_detachedStyleSheets;
+#endif
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleSheetList.idl b/chromium/third_party/WebKit/Source/core/css/StyleSheetList.idl
index 7341728216d..3da2d91e544 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleSheetList.idl
+++ b/chromium/third_party/WebKit/Source/core/css/StyleSheetList.idl
@@ -20,10 +20,10 @@
// Introduced in DOM Level 2:
[
- GenerateVisitDOMWrapper=document,
+ SetWrapperReferenceFrom=document,
+ WillBeGarbageCollected
] interface StyleSheetList {
- readonly attribute unsigned long length;
- getter StyleSheet item(unsigned long index);
- [ImplementedAs=anonymousNamedGetter, NotEnumerable] getter CSSStyleSheet (DOMString name);
+ readonly attribute unsigned long length;
+ getter StyleSheet item(unsigned long index);
+ [NotEnumerable] getter CSSStyleSheet (DOMString name);
};
-
diff --git a/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.cpp b/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.cpp
index 30a5604c412..4d3b123d3bc 100644
--- a/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.cpp
@@ -29,20 +29,68 @@
#include "config.h"
#include "core/css/TreeBoundaryCrossingRules.h"
+#include "core/css/ElementRuleCollector.h"
#include "core/css/RuleFeature.h"
#include "core/dom/StyleEngine.h"
+#include "core/dom/shadow/ShadowRoot.h"
namespace WebCore {
-void TreeBoundaryCrossingRules::addRule(StyleRule* rule, size_t selectorIndex, ContainerNode* scopingNode, AddRuleFlags addRuleFlags)
+static void addRules(RuleSet* ruleSet, const WillBeHeapVector<MinimalRuleData>& rules)
{
- if (m_treeBoundaryCrossingRuleSetMap.contains(scopingNode)) {
- m_treeBoundaryCrossingRuleSetMap.get(scopingNode)->addRule(rule, selectorIndex, addRuleFlags);
- } else {
- OwnPtr<RuleSet> ruleSetForScope = RuleSet::create();
- ruleSetForScope->addRule(rule, selectorIndex, addRuleFlags);
- m_treeBoundaryCrossingRuleSetMap.add(scopingNode, ruleSetForScope.release());
- m_scopingNodes.add(scopingNode);
+ for (unsigned i = 0; i < rules.size(); ++i) {
+ const MinimalRuleData& info = rules[i];
+ ruleSet->addRule(info.m_rule, info.m_selectorIndex, info.m_flags);
+ }
+}
+
+void TreeBoundaryCrossingRules::addTreeBoundaryCrossingRules(const RuleSet& authorRules, ContainerNode& scopingNode, CSSStyleSheet* parentStyleSheet)
+{
+ if (authorRules.treeBoundaryCrossingRules().isEmpty() && (scopingNode.isDocumentNode() || authorRules.shadowDistributedRules().isEmpty()))
+ return;
+ OwnPtrWillBeRawPtr<RuleSet> ruleSetForScope = RuleSet::create();
+ addRules(ruleSetForScope.get(), authorRules.treeBoundaryCrossingRules());
+ if (!scopingNode.isDocumentNode())
+ addRules(ruleSetForScope.get(), authorRules.shadowDistributedRules());
+
+ if (!m_treeBoundaryCrossingRuleSetMap.contains(&scopingNode)) {
+ m_treeBoundaryCrossingRuleSetMap.add(&scopingNode, adoptPtrWillBeNoop(new CSSStyleSheetRuleSubSet()));
+ m_scopingNodes.add(&scopingNode);
+ }
+ CSSStyleSheetRuleSubSet* ruleSubSet = m_treeBoundaryCrossingRuleSetMap.get(&scopingNode);
+ ruleSubSet->append(std::make_pair(parentStyleSheet, ruleSetForScope.release()));
+}
+
+void TreeBoundaryCrossingRules::collectTreeBoundaryCrossingRules(Element* element, ElementRuleCollector& collector, bool includeEmptyRules)
+{
+ if (m_treeBoundaryCrossingRuleSetMap.isEmpty())
+ return;
+
+ RuleRange ruleRange = collector.matchedResult().ranges.authorRuleRange();
+
+ // When comparing rules declared in outer treescopes, outer's rules win.
+ CascadeOrder outerCascadeOrder = size() + size();
+ // When comparing rules declared in inner treescopes, inner's rules win.
+ CascadeOrder innerCascadeOrder = size();
+
+ for (DocumentOrderedList::iterator it = m_scopingNodes.begin(); it != m_scopingNodes.end(); ++it) {
+ const ContainerNode* scopingNode = toContainerNode(*it);
+ CSSStyleSheetRuleSubSet* ruleSubSet = m_treeBoundaryCrossingRuleSetMap.get(scopingNode);
+ unsigned boundaryBehavior = SelectorChecker::ScopeContainsLastMatchedElement;
+ bool isInnerTreeScope = element->treeScope().isInclusiveAncestorOf(scopingNode->treeScope());
+
+ // If a given scoping node is a shadow root, we should use ScopeIsShadowRoot.
+ if (scopingNode && scopingNode->isShadowRoot())
+ boundaryBehavior |= SelectorChecker::ScopeIsShadowRoot;
+
+ CascadeOrder cascadeOrder = isInnerTreeScope ? innerCascadeOrder : outerCascadeOrder;
+ for (CSSStyleSheetRuleSubSet::iterator it = ruleSubSet->begin(); it != ruleSubSet->end(); ++it) {
+ CSSStyleSheet* parentStyleSheet = it->first;
+ RuleSet* ruleSet = it->second.get();
+ collector.collectMatchingRules(MatchRequest(ruleSet, includeEmptyRules, scopingNode, parentStyleSheet), ruleRange, static_cast<SelectorChecker::BehaviorAtBoundary>(boundaryBehavior), ignoreCascadeScope, cascadeOrder);
+ }
+ ++innerCascadeOrder;
+ --outerCascadeOrder;
}
}
@@ -52,12 +100,16 @@ void TreeBoundaryCrossingRules::reset(const ContainerNode* scopingNode)
m_scopingNodes.remove(scopingNode);
}
+void TreeBoundaryCrossingRules::collectFeaturesFromRuleSubSet(CSSStyleSheetRuleSubSet* ruleSubSet, RuleFeatureSet& features)
+{
+ for (CSSStyleSheetRuleSubSet::iterator it = ruleSubSet->begin(); it != ruleSubSet->end(); ++it)
+ features.add(it->second->features());
+}
+
void TreeBoundaryCrossingRules::collectFeaturesTo(RuleFeatureSet& features)
{
- for (TreeBoundaryCrossingRuleSetMap::iterator::Values it = m_treeBoundaryCrossingRuleSetMap.values().begin(); it != m_treeBoundaryCrossingRuleSetMap.values().end(); ++it) {
- RuleSet* ruleSet = it->get();
- features.add(ruleSet->features());
- }
+ for (TreeBoundaryCrossingRuleSetMap::iterator::Values it = m_treeBoundaryCrossingRuleSetMap.values().begin(); it != m_treeBoundaryCrossingRuleSetMap.values().end(); ++it)
+ collectFeaturesFromRuleSubSet(it->get(), features);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.h b/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.h
index bba30ed9dcf..64c2970e4c3 100644
--- a/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.h
+++ b/chromium/third_party/WebKit/Source/core/css/TreeBoundaryCrossingRules.h
@@ -32,24 +32,29 @@
namespace WebCore {
+class CSSStyleSheet;
class ContainerNode;
+class ElementRuleCollector;
class RuleFeatureSet;
class TreeBoundaryCrossingRules {
+ DISALLOW_ALLOCATION();
public:
- void addRule(StyleRule*, size_t selectorIndex, ContainerNode* scopingNode, AddRuleFlags);
- void clear() { m_treeBoundaryCrossingRuleSetMap.clear(); }
+ void addTreeBoundaryCrossingRules(const RuleSet&, ContainerNode& scope, CSSStyleSheet*);
+
void reset(const ContainerNode* scopingNode);
- bool isEmpty() const { return m_treeBoundaryCrossingRuleSetMap.isEmpty(); }
void collectFeaturesTo(RuleFeatureSet&);
+ void collectTreeBoundaryCrossingRules(Element*, ElementRuleCollector&, bool includeEmptyRules);
- DocumentOrderedList::iterator begin() { return m_scopingNodes.begin(); }
- DocumentOrderedList::iterator end() { return m_scopingNodes.end(); }
- RuleSet* ruleSetScopedBy(const ContainerNode* scopingNode) { return m_treeBoundaryCrossingRuleSetMap.get(scopingNode); }
+ void trace(Visitor* visitor) { visitor->trace(m_treeBoundaryCrossingRuleSetMap); }
private:
+ size_t size() const { return m_scopingNodes.size(); }
+ typedef WillBeHeapVector<std::pair<CSSStyleSheet*, OwnPtrWillBeMember<RuleSet> > > CSSStyleSheetRuleSubSet;
+ void collectFeaturesFromRuleSubSet(CSSStyleSheetRuleSubSet*, RuleFeatureSet&);
+
DocumentOrderedList m_scopingNodes;
- typedef HashMap<const ContainerNode*, OwnPtr<RuleSet> > TreeBoundaryCrossingRuleSetMap;
+ typedef WillBeHeapHashMap<const ContainerNode*, OwnPtrWillBeMember<CSSStyleSheetRuleSubSet> > TreeBoundaryCrossingRuleSetMap;
TreeBoundaryCrossingRuleSetMap m_treeBoundaryCrossingRuleSetMap;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/WebKitCSSFilterValue.idl b/chromium/third_party/WebKit/Source/core/css/WebKitCSSFilterValue.idl
index db2fb1d931d..8c346d2d612 100644
--- a/chromium/third_party/WebKit/Source/core/css/WebKitCSSFilterValue.idl
+++ b/chromium/third_party/WebKit/Source/core/css/WebKitCSSFilterValue.idl
@@ -25,7 +25,7 @@
[
DoNotCheckConstants,
- ImplementedAs=CSSFilterValue
+ ImplementedAs=CSSFilterValue,
] interface WebKitCSSFilterValue : CSSValueList {
// OperationTypes
@@ -41,8 +41,7 @@
const unsigned short CSS_FILTER_CONTRAST = 9;
const unsigned short CSS_FILTER_BLUR = 10;
const unsigned short CSS_FILTER_DROP_SHADOW = 11;
- const unsigned short CSS_FILTER_CUSTOM = 12;
readonly attribute unsigned short operationType;
- [ImplementedAs=item] getter CSSValue(unsigned long index);
+ [ImplementedAs=item] getter CSSValue (unsigned long index);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/WebKitCSSMatrix.idl b/chromium/third_party/WebKit/Source/core/css/WebKitCSSMatrix.idl
index 0016fcfdc80..08ee79783c5 100644
--- a/chromium/third_party/WebKit/Source/core/css/WebKitCSSMatrix.idl
+++ b/chromium/third_party/WebKit/Source/core/css/WebKitCSSMatrix.idl
@@ -25,9 +25,10 @@
// Introduced in DOM Level ?:
[
- Constructor([Default=NullString] optional DOMString cssValue),
+ Constructor(optional DOMString cssValue = null),
ImplementedAs=CSSMatrix,
- RaisesException=Constructor
+ RaisesException=Constructor,
+ WillBeGarbageCollected
] interface WebKitCSSMatrix {
// These attributes are simple aliases for certain elements of the 4x4 matrix
diff --git a/chromium/third_party/WebKit/Source/core/css/WebKitCSSMixFunctionValue.idl b/chromium/third_party/WebKit/Source/core/css/WebKitCSSMixFunctionValue.idl
deleted file mode 100644
index 57f3125d6df..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/WebKitCSSMixFunctionValue.idl
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (C) 2012 Adobe Systems Incorporated. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-[
- ImplementedAs=CSSMixFunctionValue
-] interface WebKitCSSMixFunctionValue : CSSValueList {
-};
-
diff --git a/chromium/third_party/WebKit/Source/core/css/WebKitCSSRegionRule.idl b/chromium/third_party/WebKit/Source/core/css/WebKitCSSRegionRule.idl
deleted file mode 100644
index 68113448048..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/WebKitCSSRegionRule.idl
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright (C) 2011 Adobe Systems Incorporated. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above
- * copyright notice, this list of conditions and the following
- * disclaimer.
- * 2. Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials
- * provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
- * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
- * OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
- * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
- * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-[
- RuntimeEnabled=CSSRegions,
- ImplementedAs=CSSRegionRule
-] interface WebKitCSSRegionRule : CSSRule {
- readonly attribute CSSRuleList cssRules;
-};
-
diff --git a/chromium/third_party/WebKit/Source/core/css/WebKitCSSTransformValue.idl b/chromium/third_party/WebKit/Source/core/css/WebKitCSSTransformValue.idl
index 836bcc6dc2d..a17e482d4c6 100644
--- a/chromium/third_party/WebKit/Source/core/css/WebKitCSSTransformValue.idl
+++ b/chromium/third_party/WebKit/Source/core/css/WebKitCSSTransformValue.idl
@@ -28,7 +28,7 @@
[
DoNotCheckConstants,
- ImplementedAs=CSSTransformValue
+ ImplementedAs=CSSTransformValue,
] interface WebKitCSSTransformValue : CSSValueList {
// OperationTypes
@@ -56,6 +56,6 @@
const unsigned short CSS_MATRIX3D = 21;
readonly attribute unsigned short operationType;
- [ImplementedAs=item] getter CSSValue(unsigned long index);
+ [ImplementedAs=item] getter CSSValue (unsigned long index);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/fullscreen.css b/chromium/third_party/WebKit/Source/core/css/fullscreen.css
index 7ecffc6ffa2..337265b9e42 100644
--- a/chromium/third_party/WebKit/Source/core/css/fullscreen.css
+++ b/chromium/third_party/WebKit/Source/core/css/fullscreen.css
@@ -31,6 +31,7 @@ video:-webkit-full-screen, audio:-webkit-full-screen {
width: 100% !important;
flex: 1 !important;
display: block !important;
+ -webkit-transform: none !important;
}
img:-webkit-full-screen {
diff --git a/chromium/third_party/WebKit/Source/core/css/html.css b/chromium/third_party/WebKit/Source/core/css/html.css
index fdacec72bdf..52aa586e5c8 100644
--- a/chromium/third_party/WebKit/Source/core/css/html.css
+++ b/chromium/third_party/WebKit/Source/core/css/html.css
@@ -59,10 +59,6 @@ body {
margin: 8px
}
-body:-webkit-seamless-document {
- margin: 0px
-}
-
body:-webkit-full-page-media {
background-color: rgb(0, 0, 0)
}
@@ -394,11 +390,11 @@ button {
}
/* Form controls don't go vertical. */
-input, textarea, keygen, select, button, isindex, meter, progress {
+input, textarea, keygen, select, button, meter, progress {
-webkit-writing-mode: horizontal-tb !important;
}
-input, textarea, keygen, select, button, isindex {
+input, textarea, keygen, select, button {
margin: 0__qem;
font: -webkit-small-control;
color: initial;
@@ -416,7 +412,7 @@ input[type="hidden"] {
display: none
}
-input, input[type="password"], input[type="search"], isindex {
+input, input[type="password"], input[type="search"] {
-webkit-appearance: textfield;
padding: 1px;
background-color: white;
@@ -577,8 +573,8 @@ input[type="datetime-local"]::-webkit-inner-spin-button,
input[type="month"]::-webkit-inner-spin-button,
input[type="time"]::-webkit-inner-spin-button,
input[type="week"]::-webkit-inner-spin-button {
- display: inline-block;
- position: static;
+ /* FIXME: Remove height. */
+ height: 1.5em;
-webkit-margin-start: 2px;
}
@@ -589,7 +585,9 @@ input[type="month"],
input[type="time"],
input[type="week"] {
align-items: center;
- -webkit-appearance: menulist-button;
+ -webkit-appearance: menulist;
+ background-color: ButtonFace;
+ border: 1px solid #a9a9a9;
display: -webkit-inline-flex;
overflow: hidden;
width: 10em;
@@ -603,15 +601,10 @@ input::-webkit-date-and-time-value {
input::-webkit-inner-spin-button {
-webkit-appearance: inner-spin-button;
- display: block;
- position: relative;
+ display: inline-block;
cursor: default;
- /* This height property is ignored for input type "number" and others which
- * use RenderTextControlSingleLine as renderer which sets height of spin
- * button in layout(). */
- height: 1.5em;
- vertical-align: top;
flex: none;
+ align-self: stretch;
-webkit-user-select: none;
-webkit-user-modify: read-only !important;
opacity: 0;
@@ -623,18 +616,6 @@ input:enabled:read-write:-webkit-any(:focus,:hover)::-webkit-inner-spin-button {
pointer-events: auto;
}
-#if defined(ENABLE_INPUT_SPEECH) && ENABLE_INPUT_SPEECH
-input::-webkit-input-speech-button {
- -webkit-appearance: -webkit-input-speech-button;
- display: block;
- vertical-align: top;
- flex: none;
- -webkit-user-modify: read-only !important;
- -webkit-align-self: flex-start;
- margin: auto 0;
-}
-#endif
-
keygen, select {
border-radius: 5px;
}
@@ -664,7 +645,7 @@ textarea {
pointer-events: none !important;
}
-input::-webkit-input-placeholder, isindex::-webkit-input-placeholder {
+input::-webkit-input-placeholder {
white-space: pre;
word-wrap: normal;
overflow: hidden;
@@ -688,7 +669,7 @@ input[type="file"] {
text-align: start !important;
}
-input:-webkit-autofill, textarea:-webkit-autofill {
+input:-webkit-autofill, textarea:-webkit-autofill, select:-webkit-autofill {
background-color: #FAFFBD !important;
background-image:none !important;
color: #000000 !important;
@@ -773,6 +754,10 @@ input[type="button"]:active:disabled, input[type="submit"]:active:disabled, inpu
border-style: outset
}
+datalist {
+ display: none
+}
+
area, param {
display: none
}
@@ -791,6 +776,10 @@ input[type="color"] {
-webkit-appearance: square-button;
width: 44px;
height: 23px;
+ background-color: ButtonFace;
+ /* Same as native_theme_base. */
+ border: 1px #a9a9a9 solid;
+ padding: 1px 2px;
}
input[type="color"]::-webkit-color-swatch-wrapper {
@@ -809,6 +798,21 @@ input[type="color"]::-webkit-color-swatch {
-webkit-user-modify: read-only !important;
}
+input[type="color"][list] {
+ -webkit-appearance: menulist;
+ width: 88px;
+ height: 23px
+}
+
+input[type="color"][list]::-webkit-color-swatch-wrapper {
+ padding-left: 8px;
+ padding-right: 24px;
+}
+
+input[type="color"][list]::-webkit-color-swatch {
+ border-color: #000000;
+}
+
input::-webkit-calendar-picker-indicator {
display: inline-block;
width: 0.66em;
@@ -912,7 +916,7 @@ meter::-webkit-meter-inner-element {
}
meter::-webkit-meter-bar {
- background: -webkit-gradient(linear, left top, left bottom, from(#ddd), to(#ddd), color-stop(0.20, #eee), color-stop(0.45, #ccc), color-stop(0.55, #ccc));
+ background: linear-gradient(to bottom, #ddd, #eee 20%, #ccc 45%, #ccc 55%, #ddd);
height: 100%;
width: 100%;
-webkit-user-modify: read-only !important;
@@ -920,21 +924,21 @@ meter::-webkit-meter-bar {
}
meter::-webkit-meter-optimum-value {
- background: -webkit-gradient(linear, left top, left bottom, from(#ad7), to(#ad7), color-stop(0.20, #cea), color-stop(0.45, #7a3), color-stop(0.55, #7a3));
+ background: linear-gradient(to bottom, #ad7, #cea 20%, #7a3 45%, #7a3 55%, #ad7);
height: 100%;
-webkit-user-modify: read-only !important;
box-sizing: border-box;
}
meter::-webkit-meter-suboptimum-value {
- background: -webkit-gradient(linear, left top, left bottom, from(#fe7), to(#fe7), color-stop(0.20, #ffc), color-stop(0.45, #db3), color-stop(0.55, #db3));
+ background: linear-gradient(to bottom, #fe7, #ffc 20%, #db3 45%, #db3 55%, #fe7);
height: 100%;
-webkit-user-modify: read-only !important;
box-sizing: border-box;
}
meter::-webkit-meter-even-less-good-value {
- background: -webkit-gradient(linear, left top, left bottom, from(#f77), to(#f77), color-stop(0.20, #fcc), color-stop(0.45, #d44), color-stop(0.55, #d44));
+ background: linear-gradient(to bottom, #f77, #fcc 20%, #d44 45%, #d44 55%, #f77);
height: 100%;
-webkit-user-modify: read-only !important;
box-sizing: border-box;
@@ -1046,7 +1050,7 @@ applet:focus, embed:focus, iframe:focus, object:focus {
outline: none
}
-input:focus, textarea:focus, isindex:focus, keygen:focus, select:focus {
+input:focus, textarea:focus, keygen:focus, select:focus {
outline-offset: -2px
}
@@ -1108,14 +1112,10 @@ frameset {
border-color: inherit
}
-iframe:not([seamless]) {
+iframe {
border: 2px inset
}
-iframe[seamless] {
- display: block
-}
-
details {
display: block
}
@@ -1128,7 +1128,7 @@ summary::-webkit-details-marker {
display: inline-block;
width: 0.66em;
height: 0.66em;
- margin-right: 0.4em;
+ -webkit-margin-end: 0.4em;
}
template {
diff --git a/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.cpp b/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.cpp
new file mode 100644
index 00000000000..6f1be3b13bf
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.cpp
@@ -0,0 +1,196 @@
+/*
+ * Copyright (C) 2014 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "core/css/invalidation/DescendantInvalidationSet.h"
+
+#include "core/css/resolver/StyleResolver.h"
+#include "core/dom/Element.h"
+
+namespace WebCore {
+
+DescendantInvalidationSet::DescendantInvalidationSet()
+ : m_allDescendantsMightBeInvalid(false)
+ , m_customPseudoInvalid(false)
+ , m_treeBoundaryCrossing(false)
+{
+}
+
+bool DescendantInvalidationSet::invalidatesElement(Element& element) const
+{
+ if (m_allDescendantsMightBeInvalid)
+ return true;
+
+ if (m_tagNames && m_tagNames->contains(element.tagQName().localName()))
+ return true;
+
+ if (element.hasID() && m_ids && m_ids->contains(element.idForStyleResolution()))
+ return true;
+
+ if (element.hasClass() && m_classes) {
+ const SpaceSplitString& classNames = element.classNames();
+ for (WillBeHeapHashSet<AtomicString>::const_iterator it = m_classes->begin(); it != m_classes->end(); ++it) {
+ if (classNames.contains(*it))
+ return true;
+ }
+ }
+
+ if (element.hasAttributes() && m_attributes) {
+ for (WillBeHeapHashSet<AtomicString>::const_iterator it = m_attributes->begin(); it != m_attributes->end(); ++it) {
+ if (element.hasAttribute(*it))
+ return true;
+ }
+ }
+
+ return false;
+}
+
+void DescendantInvalidationSet::combine(const DescendantInvalidationSet& other)
+{
+ // No longer bother combining data structures, since the whole subtree is deemed invalid.
+ if (wholeSubtreeInvalid())
+ return;
+
+ if (other.wholeSubtreeInvalid()) {
+ setWholeSubtreeInvalid();
+ return;
+ }
+
+ if (other.customPseudoInvalid())
+ setCustomPseudoInvalid();
+
+ if (other.treeBoundaryCrossing())
+ setTreeBoundaryCrossing();
+
+ if (other.m_classes) {
+ WillBeHeapHashSet<AtomicString>::const_iterator end = other.m_classes->end();
+ for (WillBeHeapHashSet<AtomicString>::const_iterator it = other.m_classes->begin(); it != end; ++it)
+ addClass(*it);
+ }
+
+ if (other.m_ids) {
+ WillBeHeapHashSet<AtomicString>::const_iterator end = other.m_ids->end();
+ for (WillBeHeapHashSet<AtomicString>::const_iterator it = other.m_ids->begin(); it != end; ++it)
+ addId(*it);
+ }
+
+ if (other.m_tagNames) {
+ WillBeHeapHashSet<AtomicString>::const_iterator end = other.m_tagNames->end();
+ for (WillBeHeapHashSet<AtomicString>::const_iterator it = other.m_tagNames->begin(); it != end; ++it)
+ addTagName(*it);
+ }
+
+ if (other.m_attributes) {
+ WillBeHeapHashSet<AtomicString>::const_iterator end = other.m_attributes->end();
+ for (WillBeHeapHashSet<AtomicString>::const_iterator it = other.m_attributes->begin(); it != end; ++it)
+ addAttribute(*it);
+ }
+}
+
+WillBeHeapHashSet<AtomicString>& DescendantInvalidationSet::ensureClassSet()
+{
+ if (!m_classes)
+ m_classes = adoptPtrWillBeNoop(new WillBeHeapHashSet<AtomicString>);
+ return *m_classes;
+}
+
+WillBeHeapHashSet<AtomicString>& DescendantInvalidationSet::ensureIdSet()
+{
+ if (!m_ids)
+ m_ids = adoptPtrWillBeNoop(new WillBeHeapHashSet<AtomicString>);
+ return *m_ids;
+}
+
+WillBeHeapHashSet<AtomicString>& DescendantInvalidationSet::ensureTagNameSet()
+{
+ if (!m_tagNames)
+ m_tagNames = adoptPtrWillBeNoop(new WillBeHeapHashSet<AtomicString>);
+ return *m_tagNames;
+}
+
+WillBeHeapHashSet<AtomicString>& DescendantInvalidationSet::ensureAttributeSet()
+{
+ if (!m_attributes)
+ m_attributes = adoptPtrWillBeNoop(new WillBeHeapHashSet<AtomicString>);
+ return *m_attributes;
+}
+
+void DescendantInvalidationSet::addClass(const AtomicString& className)
+{
+ if (wholeSubtreeInvalid())
+ return;
+ ensureClassSet().add(className);
+}
+
+void DescendantInvalidationSet::addId(const AtomicString& id)
+{
+ if (wholeSubtreeInvalid())
+ return;
+ ensureIdSet().add(id);
+}
+
+void DescendantInvalidationSet::addTagName(const AtomicString& tagName)
+{
+ if (wholeSubtreeInvalid())
+ return;
+ ensureTagNameSet().add(tagName);
+}
+
+void DescendantInvalidationSet::addAttribute(const AtomicString& attribute)
+{
+ if (wholeSubtreeInvalid())
+ return;
+ ensureAttributeSet().add(attribute);
+}
+
+void DescendantInvalidationSet::setWholeSubtreeInvalid()
+{
+ if (m_allDescendantsMightBeInvalid)
+ return;
+
+ m_allDescendantsMightBeInvalid = true;
+ m_treeBoundaryCrossing = false;
+ m_classes = nullptr;
+ m_ids = nullptr;
+ m_tagNames = nullptr;
+ m_attributes = nullptr;
+}
+
+void DescendantInvalidationSet::trace(Visitor* visitor)
+{
+#if ENABLE(OILPAN)
+ visitor->trace(m_classes);
+ visitor->trace(m_ids);
+ visitor->trace(m_tagNames);
+ visitor->trace(m_attributes);
+#endif
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.h b/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.h
new file mode 100644
index 00000000000..b86c93b03c6
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSet.h
@@ -0,0 +1,103 @@
+/*
+ * Copyright (C) 2014 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef DescendantInvalidationSet_h
+#define DescendantInvalidationSet_h
+
+#include "platform/heap/Handle.h"
+#include "wtf/Forward.h"
+#include "wtf/HashSet.h"
+#include "wtf/RefCounted.h"
+#include "wtf/RefPtr.h"
+#include "wtf/text/AtomicStringHash.h"
+#include "wtf/text/StringHash.h"
+
+namespace WebCore {
+
+class Element;
+
+// Tracks data to determine which elements of a DOM subtree need to have style
+// recalculated.
+class DescendantInvalidationSet FINAL : public RefCountedWillBeGarbageCollected<DescendantInvalidationSet> {
+public:
+ static PassRefPtrWillBeRawPtr<DescendantInvalidationSet> create()
+ {
+ return adoptRefWillBeNoop(new DescendantInvalidationSet);
+ }
+
+ bool invalidatesElement(Element&) const;
+
+ void combine(const DescendantInvalidationSet& other);
+
+ void addClass(const AtomicString& className);
+ void addId(const AtomicString& id);
+ void addTagName(const AtomicString& tagName);
+ void addAttribute(const AtomicString& attributeLocalName);
+
+ void setWholeSubtreeInvalid();
+ bool wholeSubtreeInvalid() const { return m_allDescendantsMightBeInvalid; }
+
+ void setTreeBoundaryCrossing() { m_treeBoundaryCrossing = true; }
+ bool treeBoundaryCrossing() const { return m_treeBoundaryCrossing; }
+
+ void setCustomPseudoInvalid() { m_customPseudoInvalid = true; }
+ bool customPseudoInvalid() const { return m_customPseudoInvalid; }
+
+ bool isEmpty() const { return !m_classes && !m_ids && !m_tagNames && !m_attributes; }
+
+ void trace(Visitor*);
+
+private:
+ DescendantInvalidationSet();
+
+ WillBeHeapHashSet<AtomicString>& ensureClassSet();
+ WillBeHeapHashSet<AtomicString>& ensureIdSet();
+ WillBeHeapHashSet<AtomicString>& ensureTagNameSet();
+ WillBeHeapHashSet<AtomicString>& ensureAttributeSet();
+
+ // FIXME: optimize this if it becomes a memory issue.
+ OwnPtrWillBeMember<WillBeHeapHashSet<AtomicString> > m_classes;
+ OwnPtrWillBeMember<WillBeHeapHashSet<AtomicString> > m_ids;
+ OwnPtrWillBeMember<WillBeHeapHashSet<AtomicString> > m_tagNames;
+ OwnPtrWillBeMember<WillBeHeapHashSet<AtomicString> > m_attributes;
+
+ // If true, all descendants might be invalidated, so a full subtree recalc is required.
+ unsigned m_allDescendantsMightBeInvalid : 1;
+
+ // If true, all descendants which are custom pseudo elements must be invalidated.
+ unsigned m_customPseudoInvalid : 1;
+
+ // If true, the invalidation must traverse into ShadowRoots with this set.
+ unsigned m_treeBoundaryCrossing : 1;
+};
+
+} // namespace WebCore
+
+#endif // DescendantInvalidationSet_h
diff --git a/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSetTest.cpp b/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSetTest.cpp
new file mode 100644
index 00000000000..3732ebf405e
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/DescendantInvalidationSetTest.cpp
@@ -0,0 +1,64 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/invalidation/DescendantInvalidationSet.h"
+
+#include <gtest/gtest.h>
+
+using namespace WebCore;
+
+namespace {
+
+// Once we setWholeSubtreeInvalid, we should not keep the HashSets.
+TEST(DescendantInvalidationSetTest, SubtreeInvalid_AddBefore)
+{
+ RefPtrWillBeRawPtr<DescendantInvalidationSet> set = DescendantInvalidationSet::create();
+ set->addClass("a");
+ set->setWholeSubtreeInvalid();
+
+ ASSERT_TRUE(set->isEmpty());
+}
+
+// Don't (re)create HashSets if we've already setWholeSubtreeInvalid.
+TEST(DescendantInvalidationSetTest, SubtreeInvalid_AddAfter)
+{
+ RefPtrWillBeRawPtr<DescendantInvalidationSet> set = DescendantInvalidationSet::create();
+ set->setWholeSubtreeInvalid();
+ set->addTagName("a");
+
+ ASSERT_TRUE(set->isEmpty());
+}
+
+// No need to keep the HashSets when combining with a wholeSubtreeInvalid set.
+TEST(DescendantInvalidationSetTest, SubtreeInvalid_Combine_1)
+{
+ RefPtrWillBeRawPtr<DescendantInvalidationSet> set1 = DescendantInvalidationSet::create();
+ RefPtrWillBeRawPtr<DescendantInvalidationSet> set2 = DescendantInvalidationSet::create();
+
+ set1->addId("a");
+ set2->setWholeSubtreeInvalid();
+
+ set1->combine(*set2);
+
+ ASSERT_TRUE(set1->wholeSubtreeInvalid());
+ ASSERT_TRUE(set1->isEmpty());
+}
+
+// No need to add HashSets from combining set when we already have wholeSubtreeInvalid.
+TEST(DescendantInvalidationSetTest, SubtreeInvalid_Combine_2)
+{
+ RefPtrWillBeRawPtr<DescendantInvalidationSet> set1 = DescendantInvalidationSet::create();
+ RefPtrWillBeRawPtr<DescendantInvalidationSet> set2 = DescendantInvalidationSet::create();
+
+ set1->setWholeSubtreeInvalid();
+ set2->addAttribute("a");
+
+ set1->combine(*set2);
+
+ ASSERT_TRUE(set1->wholeSubtreeInvalid());
+ ASSERT_TRUE(set1->isEmpty());
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.cpp b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.cpp
new file mode 100644
index 00000000000..3874c2b93e6
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.cpp
@@ -0,0 +1,167 @@
+
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+
+#include "core/css/invalidation/StyleInvalidator.h"
+
+#include "core/css/invalidation/DescendantInvalidationSet.h"
+#include "core/dom/Document.h"
+#include "core/dom/Element.h"
+#include "core/dom/ElementTraversal.h"
+#include "core/dom/shadow/ElementShadow.h"
+#include "core/dom/shadow/ShadowRoot.h"
+#include "core/rendering/RenderObject.h"
+
+namespace WebCore {
+
+void StyleInvalidator::invalidate(Document& document)
+{
+ if (Element* documentElement = document.documentElement())
+ invalidate(*documentElement);
+ document.clearChildNeedsStyleInvalidation();
+ document.clearNeedsStyleInvalidation();
+ clearPendingInvalidations();
+}
+
+void StyleInvalidator::scheduleInvalidation(PassRefPtrWillBeRawPtr<DescendantInvalidationSet> invalidationSet, Element& element)
+{
+ ASSERT(element.inActiveDocument());
+ ASSERT(element.styleChangeType() < SubtreeStyleChange);
+ InvalidationList& list = ensurePendingInvalidationList(element);
+ // If we're already going to invalidate the whole subtree we don't need to store any new sets.
+ if (!list.isEmpty() && list.last()->wholeSubtreeInvalid())
+ return;
+ // If this set would invalidate the whole subtree we can discard all existing sets.
+ if (invalidationSet->wholeSubtreeInvalid())
+ list.clear();
+ list.append(invalidationSet);
+ element.setNeedsStyleInvalidation();
+}
+
+StyleInvalidator::InvalidationList& StyleInvalidator::ensurePendingInvalidationList(Element& element)
+{
+ PendingInvalidationMap::AddResult addResult = m_pendingInvalidationMap.add(&element, nullptr);
+ if (addResult.isNewEntry)
+ addResult.storedValue->value = adoptPtrWillBeNoop(new InvalidationList);
+ return *addResult.storedValue->value;
+}
+
+void StyleInvalidator::clearInvalidation(Node& node)
+{
+ if (node.isElementNode() && node.needsStyleInvalidation())
+ m_pendingInvalidationMap.remove(toElement(&node));
+}
+
+void StyleInvalidator::clearPendingInvalidations()
+{
+ m_pendingInvalidationMap.clear();
+}
+
+StyleInvalidator::StyleInvalidator()
+{
+}
+
+StyleInvalidator::~StyleInvalidator()
+{
+}
+
+void StyleInvalidator::RecursionData::pushInvalidationSet(const DescendantInvalidationSet& invalidationSet)
+{
+ ASSERT(!m_wholeSubtreeInvalid);
+ if (invalidationSet.treeBoundaryCrossing())
+ m_treeBoundaryCrossing = true;
+ if (invalidationSet.wholeSubtreeInvalid()) {
+ m_wholeSubtreeInvalid = true;
+ return;
+ }
+ m_invalidationSets.append(&invalidationSet);
+ m_invalidateCustomPseudo = invalidationSet.customPseudoInvalid();
+}
+
+bool StyleInvalidator::RecursionData::matchesCurrentInvalidationSets(Element& element)
+{
+ ASSERT(!m_wholeSubtreeInvalid);
+
+ if (m_invalidateCustomPseudo && element.shadowPseudoId() != nullAtom)
+ return true;
+
+ for (InvalidationSets::iterator it = m_invalidationSets.begin(); it != m_invalidationSets.end(); ++it) {
+ if ((*it)->invalidatesElement(element))
+ return true;
+ }
+
+ return false;
+}
+
+bool StyleInvalidator::checkInvalidationSetsAgainstElement(Element& element)
+{
+ if (element.styleChangeType() >= SubtreeStyleChange || m_recursionData.wholeSubtreeInvalid()) {
+ m_recursionData.setWholeSubtreeInvalid();
+ return false;
+ }
+ if (element.needsStyleInvalidation()) {
+ if (InvalidationList* invalidationList = m_pendingInvalidationMap.get(&element)) {
+ for (InvalidationList::const_iterator it = invalidationList->begin(); it != invalidationList->end(); ++it)
+ m_recursionData.pushInvalidationSet(**it);
+ // FIXME: It's really only necessary to clone the render style for this element, not full style recalc.
+ return true;
+ }
+ }
+ return m_recursionData.matchesCurrentInvalidationSets(element);
+}
+
+bool StyleInvalidator::invalidateChildren(Element& element)
+{
+ bool someChildrenNeedStyleRecalc = false;
+ for (ShadowRoot* root = element.youngestShadowRoot(); root; root = root->olderShadowRoot()) {
+ if (!m_recursionData.treeBoundaryCrossing() && !root->childNeedsStyleInvalidation() && !root->needsStyleInvalidation())
+ continue;
+ for (Element* child = ElementTraversal::firstChild(*root); child; child = ElementTraversal::nextSibling(*child)) {
+ bool childRecalced = invalidate(*child);
+ someChildrenNeedStyleRecalc = someChildrenNeedStyleRecalc || childRecalced;
+ }
+ root->clearChildNeedsStyleInvalidation();
+ root->clearNeedsStyleInvalidation();
+ }
+ for (Element* child = ElementTraversal::firstChild(element); child; child = ElementTraversal::nextSibling(*child)) {
+ bool childRecalced = invalidate(*child);
+ someChildrenNeedStyleRecalc = someChildrenNeedStyleRecalc || childRecalced;
+ }
+ return someChildrenNeedStyleRecalc;
+}
+
+bool StyleInvalidator::invalidate(Element& element)
+{
+ RecursionCheckpoint checkpoint(&m_recursionData);
+
+ bool thisElementNeedsStyleRecalc = checkInvalidationSetsAgainstElement(element);
+
+ bool someChildrenNeedStyleRecalc = false;
+ if (m_recursionData.hasInvalidationSets() || element.childNeedsStyleInvalidation())
+ someChildrenNeedStyleRecalc = invalidateChildren(element);
+
+ if (thisElementNeedsStyleRecalc) {
+ element.setNeedsStyleRecalc(m_recursionData.wholeSubtreeInvalid() ? SubtreeStyleChange : LocalStyleChange);
+ } else if (m_recursionData.hasInvalidationSets() && someChildrenNeedStyleRecalc) {
+ // Clone the RenderStyle in order to preserve correct style sharing, if possible. Otherwise recalc style.
+ if (RenderObject* renderer = element.renderer())
+ renderer->setStyleInternal(RenderStyle::clone(renderer->style()));
+ else
+ element.setNeedsStyleRecalc(LocalStyleChange);
+ }
+
+ element.clearChildNeedsStyleInvalidation();
+ element.clearNeedsStyleInvalidation();
+
+ return thisElementNeedsStyleRecalc;
+}
+
+void StyleInvalidator::trace(Visitor* visitor)
+{
+ visitor->trace(m_pendingInvalidationMap);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.h b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.h
new file mode 100644
index 00000000000..275c6c8c8e6
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleInvalidator.h
@@ -0,0 +1,96 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef StyleInvalidator_h
+#define StyleInvalidator_h
+
+#include "platform/heap/Handle.h"
+
+namespace WebCore {
+
+class DescendantInvalidationSet;
+class Document;
+class Element;
+
+class StyleInvalidator {
+ DISALLOW_ALLOCATION();
+public:
+ StyleInvalidator();
+ ~StyleInvalidator();
+ void invalidate(Document&);
+ void scheduleInvalidation(PassRefPtrWillBeRawPtr<DescendantInvalidationSet>, Element&);
+
+ // Clears all style invalidation state for the passed node.
+ void clearInvalidation(Node&);
+
+ void clearPendingInvalidations();
+
+ void trace(Visitor*);
+
+private:
+ bool invalidate(Element&);
+ bool invalidateChildren(Element&);
+
+ bool checkInvalidationSetsAgainstElement(Element&);
+
+ struct RecursionData {
+ RecursionData()
+ : m_invalidateCustomPseudo(false)
+ , m_wholeSubtreeInvalid(false)
+ , m_treeBoundaryCrossing(false)
+ { }
+
+ void pushInvalidationSet(const DescendantInvalidationSet&);
+ bool matchesCurrentInvalidationSets(Element&);
+ bool hasInvalidationSets() const { return !wholeSubtreeInvalid() && m_invalidationSets.size(); }
+
+ bool wholeSubtreeInvalid() const { return m_wholeSubtreeInvalid; }
+ void setWholeSubtreeInvalid() { m_wholeSubtreeInvalid = true; }
+
+ bool treeBoundaryCrossing() const { return m_treeBoundaryCrossing; }
+
+ typedef Vector<const DescendantInvalidationSet*, 16> InvalidationSets;
+ InvalidationSets m_invalidationSets;
+ bool m_invalidateCustomPseudo;
+ bool m_wholeSubtreeInvalid;
+ bool m_treeBoundaryCrossing;
+ };
+
+ class RecursionCheckpoint {
+ public:
+ RecursionCheckpoint(RecursionData* data)
+ : m_prevInvalidationSetsSize(data->m_invalidationSets.size())
+ , m_prevInvalidateCustomPseudo(data->m_invalidateCustomPseudo)
+ , m_prevWholeSubtreeInvalid(data->m_wholeSubtreeInvalid)
+ , m_treeBoundaryCrossing(data->m_treeBoundaryCrossing)
+ , m_data(data)
+ { }
+ ~RecursionCheckpoint()
+ {
+ m_data->m_invalidationSets.remove(m_prevInvalidationSetsSize, m_data->m_invalidationSets.size() - m_prevInvalidationSetsSize);
+ m_data->m_invalidateCustomPseudo = m_prevInvalidateCustomPseudo;
+ m_data->m_wholeSubtreeInvalid = m_prevWholeSubtreeInvalid;
+ m_data->m_treeBoundaryCrossing = m_treeBoundaryCrossing;
+ }
+
+ private:
+ int m_prevInvalidationSetsSize;
+ bool m_prevInvalidateCustomPseudo;
+ bool m_prevWholeSubtreeInvalid;
+ bool m_treeBoundaryCrossing;
+ RecursionData* m_data;
+ };
+
+ typedef WillBeHeapVector<RefPtrWillBeMember<DescendantInvalidationSet> > InvalidationList;
+ typedef WillBeHeapHashMap<RawPtrWillBeMember<Element>, OwnPtrWillBeMember<InvalidationList> > PendingInvalidationMap;
+
+ InvalidationList& ensurePendingInvalidationList(Element&);
+
+ PendingInvalidationMap m_pendingInvalidationMap;
+ RecursionData m_recursionData;
+};
+
+} // namespace WebCore
+
+#endif // StyleInvalidator_h
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleInvalidationAnalysis.cpp b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleSheetInvalidationAnalysis.cpp
index 440e17fe346..bb9854b4762 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleInvalidationAnalysis.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleSheetInvalidationAnalysis.cpp
@@ -24,7 +24,7 @@
*/
#include "config.h"
-#include "core/css/StyleInvalidationAnalysis.h"
+#include "core/css/invalidation/StyleSheetInvalidationAnalysis.h"
#include "core/css/CSSSelectorList.h"
#include "core/css/StyleRuleImport.h"
@@ -37,7 +37,7 @@
namespace WebCore {
-StyleInvalidationAnalysis::StyleInvalidationAnalysis(const Vector<StyleSheetContents*>& sheets)
+StyleSheetInvalidationAnalysis::StyleSheetInvalidationAnalysis(const WillBeHeapVector<RawPtrWillBeMember<StyleSheetContents> >& sheets)
: m_dirtiesAllStyle(false)
{
for (unsigned i = 0; i < sheets.size() && !m_dirtiesAllStyle; ++i)
@@ -46,23 +46,27 @@ StyleInvalidationAnalysis::StyleInvalidationAnalysis(const Vector<StyleSheetCont
static bool determineSelectorScopes(const CSSSelectorList& selectorList, HashSet<StringImpl*>& idScopes, HashSet<StringImpl*>& classScopes)
{
- for (const CSSSelector* selector = selectorList.first(); selector; selector = CSSSelectorList::next(selector)) {
+ for (const CSSSelector* selector = selectorList.first(); selector; selector = CSSSelectorList::next(*selector)) {
const CSSSelector* scopeSelector = 0;
// This picks the widest scope, not the narrowest, to minimize the number of found scopes.
for (const CSSSelector* current = selector; current; current = current->tagHistory()) {
// Prefer ids over classes.
- if (current->m_match == CSSSelector::Id)
+ if (current->match() == CSSSelector::Id)
scopeSelector = current;
- else if (current->m_match == CSSSelector::Class && (!scopeSelector || scopeSelector->m_match != CSSSelector::Id))
+ else if (current->match() == CSSSelector::Class && (!scopeSelector || scopeSelector->match() != CSSSelector::Id))
scopeSelector = current;
CSSSelector::Relation relation = current->relation();
+ // FIXME: it would be better to use setNeedsStyleRecalc for all shadow hosts matching
+ // scopeSelector. Currently requests full style recalc.
+ if (relation == CSSSelector::ShadowDeep || relation == CSSSelector::ShadowPseudo)
+ return false;
if (relation != CSSSelector::Descendant && relation != CSSSelector::Child && relation != CSSSelector::SubSelector)
break;
}
if (!scopeSelector)
return false;
- ASSERT(scopeSelector->m_match == CSSSelector::Class || scopeSelector->m_match == CSSSelector::Id);
- if (scopeSelector->m_match == CSSSelector::Id)
+ ASSERT(scopeSelector->match() == CSSSelector::Class || scopeSelector->match() == CSSSelector::Id);
+ if (scopeSelector->match() == CSSSelector::Id)
idScopes.add(scopeSelector->value().impl());
else
classScopes.add(scopeSelector->value().impl());
@@ -72,7 +76,7 @@ static bool determineSelectorScopes(const CSSSelectorList& selectorList, HashSet
static bool hasDistributedRule(StyleSheetContents* styleSheetContents)
{
- const Vector<RefPtr<StyleRuleBase> >& rules = styleSheetContents->childRules();
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& rules = styleSheetContents->childRules();
for (unsigned i = 0; i < rules.size(); i++) {
const StyleRuleBase* rule = rules[i].get();
if (!rule->isStyleRule())
@@ -88,24 +92,19 @@ static bool hasDistributedRule(StyleSheetContents* styleSheetContents)
return false;
}
-static Node* determineScopingNodeForStyleScoped(HTMLStyleElement* ownerElement, StyleSheetContents* styleSheetContents)
+static Node* determineScopingNodeForStyleInShadow(HTMLStyleElement* ownerElement, StyleSheetContents* styleSheetContents)
{
- ASSERT(ownerElement && ownerElement->isRegisteredAsScoped());
-
- if (ownerElement->isInShadowTree()) {
- if (hasDistributedRule(styleSheetContents)) {
- ContainerNode* scope = ownerElement;
- do {
- scope = scope->containingShadowRoot()->shadowHost();
- } while (scope->isInShadowTree());
-
- return scope;
- }
- if (ownerElement->isRegisteredAsScoped())
- return ownerElement->containingShadowRoot()->shadowHost();
+ ASSERT(ownerElement && ownerElement->isInShadowTree());
+
+ if (hasDistributedRule(styleSheetContents)) {
+ ContainerNode* scope = ownerElement;
+ do {
+ scope = scope->containingShadowRoot()->shadowHost();
+ } while (scope->isInShadowTree());
+ return scope;
}
- return ownerElement->isRegisteredInShadowRoot() ? ownerElement->containingShadowRoot()->shadowHost() : ownerElement->parentNode();
+ return ownerElement->containingShadowRoot()->shadowHost();
}
static bool ruleAdditionMightRequireDocumentStyleRecalc(StyleRuleBase* rule)
@@ -123,7 +122,6 @@ static bool ruleAdditionMightRequireDocumentStyleRecalc(StyleRuleBase* rule)
case StyleRule::Supports: // If we evaluated the supports-clause we could avoid recalc.
case StyleRule::Viewport: // If the viewport doesn't match, we could avoid recalcing.
// FIXME: Unclear if any of the rest need to cause style recalc:
- case StyleRule::Region:
case StyleRule::Filter:
return true;
@@ -138,13 +136,13 @@ static bool ruleAdditionMightRequireDocumentStyleRecalc(StyleRuleBase* rule)
return true;
}
-void StyleInvalidationAnalysis::analyzeStyleSheet(StyleSheetContents* styleSheetContents)
+void StyleSheetInvalidationAnalysis::analyzeStyleSheet(StyleSheetContents* styleSheetContents)
{
ASSERT(!styleSheetContents->isLoading());
// See if all rules on the sheet are scoped to some specific ids or classes.
// Then test if we actually have any of those in the tree at the moment.
- const Vector<RefPtr<StyleRuleImport> >& importRules = styleSheetContents->importRules();
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleImport> >& importRules = styleSheetContents->importRules();
for (unsigned i = 0; i < importRules.size(); ++i) {
if (!importRules[i]->styleSheet())
continue;
@@ -154,13 +152,13 @@ void StyleInvalidationAnalysis::analyzeStyleSheet(StyleSheetContents* styleSheet
}
if (styleSheetContents->hasSingleOwnerNode()) {
Node* ownerNode = styleSheetContents->singleOwnerNode();
- if (ownerNode && ownerNode->hasTagName(HTMLNames::styleTag) && toHTMLStyleElement(ownerNode)->isRegisteredAsScoped()) {
- m_scopingNodes.append(determineScopingNodeForStyleScoped(toHTMLStyleElement(ownerNode), styleSheetContents));
+ if (isHTMLStyleElement(ownerNode) && toHTMLStyleElement(*ownerNode).isInShadowTree()) {
+ m_scopingNodes.append(determineScopingNodeForStyleInShadow(toHTMLStyleElement(ownerNode), styleSheetContents));
return;
}
}
- const Vector<RefPtr<StyleRuleBase> >& rules = styleSheetContents->childRules();
+ const WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> >& rules = styleSheetContents->childRules();
for (unsigned i = 0; i < rules.size(); i++) {
StyleRuleBase* rule = rules[i].get();
if (!rule->isStyleRule()) {
@@ -192,13 +190,13 @@ static bool elementMatchesSelectorScopes(const Element* element, const HashSet<S
return false;
}
-void StyleInvalidationAnalysis::invalidateStyle(Document& document)
+void StyleSheetInvalidationAnalysis::invalidateStyle(Document& document)
{
ASSERT(!m_dirtiesAllStyle);
if (!m_scopingNodes.isEmpty()) {
for (unsigned i = 0; i < m_scopingNodes.size(); ++i)
- m_scopingNodes.at(i)->setNeedsStyleRecalc();
+ m_scopingNodes.at(i)->setNeedsStyleRecalc(SubtreeStyleChange);
}
if (m_idScopes.isEmpty() && m_classScopes.isEmpty())
@@ -206,7 +204,7 @@ void StyleInvalidationAnalysis::invalidateStyle(Document& document)
Element* element = ElementTraversal::firstWithin(document);
while (element) {
if (elementMatchesSelectorScopes(element, m_idScopes, m_classScopes)) {
- element->setNeedsStyleRecalc();
+ element->setNeedsStyleRecalc(SubtreeStyleChange);
// The whole subtree is now invalidated, we can skip to the next sibling.
element = ElementTraversal::nextSkippingChildren(*element);
continue;
diff --git a/chromium/third_party/WebKit/Source/core/css/StyleInvalidationAnalysis.h b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleSheetInvalidationAnalysis.h
index 79cf3d87bda..9b74a3eef53 100644
--- a/chromium/third_party/WebKit/Source/core/css/StyleInvalidationAnalysis.h
+++ b/chromium/third_party/WebKit/Source/core/css/invalidation/StyleSheetInvalidationAnalysis.h
@@ -23,9 +23,10 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef StyleInvalidationAnalysis_h
-#define StyleInvalidationAnalysis_h
+#ifndef StyleSheetInvalidationAnalysis_h
+#define StyleSheetInvalidationAnalysis_h
+#include "platform/heap/Handle.h"
#include "wtf/HashSet.h"
#include "wtf/Vector.h"
#include "wtf/text/StringImpl.h"
@@ -36,9 +37,9 @@ class Document;
class Node;
class StyleSheetContents;
-class StyleInvalidationAnalysis {
+class StyleSheetInvalidationAnalysis {
public:
- StyleInvalidationAnalysis(const Vector<StyleSheetContents*>&);
+ StyleSheetInvalidationAnalysis(const WillBeHeapVector<RawPtrWillBeMember<StyleSheetContents> >&);
bool dirtiesAllStyle() const { return m_dirtiesAllStyle; }
void invalidateStyle(Document&);
diff --git a/chromium/third_party/WebKit/Source/core/css/make-css-file-arrays.pl b/chromium/third_party/WebKit/Source/core/css/make-css-file-arrays.pl
index 66eb7dfb0e4..d111cb30576 100755
--- a/chromium/third_party/WebKit/Source/core/css/make-css-file-arrays.pl
+++ b/chromium/third_party/WebKit/Source/core/css/make-css-file-arrays.pl
@@ -34,8 +34,10 @@ shift;
my $out = $ARGV[0];
shift;
-open HEADER, ">", $header or die;
-open OUT, ">", $out or die;
+$header =~ s|\\|/|g;
+$out =~ s|\\|/|g;
+open HEADER, ">", $header or die "$!\n";
+open OUT, ">", $out or die "$!\n";
print HEADER "namespace WebCore {\n";
print OUT "namespace WebCore {\n";
diff --git a/chromium/third_party/WebKit/Source/core/css/mathml.css b/chromium/third_party/WebKit/Source/core/css/mathml.css
new file mode 100644
index 00000000000..cef10e3f7b0
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/mathml.css
@@ -0,0 +1,49 @@
+/*
+ * The default style sheet used to render MathML.
+ *
+ * Copyright (C) 2014 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@namespace "http://www.w3.org/1998/Math/MathML";
+
+/* By default, we only display the MathML formulas without any formatting other than the one specified by the display attribute. */
+math {
+ display: inline;
+}
+
+math[display="block"] {
+ display: block;
+ text-align: center;
+}
+
+/* We hide the PresentationExpression constructions that are children of a <semantics> element.
+ http://www.w3.org/TR/MathML/appendixa.html#parsing_PresentationExpression */
+semantics > mi, semantics > mn, semantics > mo, semantics > mtext, semantics > mspace, semantics > ms, semantics > maligngroup, semantics > malignmark, semantics > mrow, semantics > mfrac, semantics > msqrt, semantics > mroot, semantics > mstyle, semantics > merror, semantics > mpadded, semantics > mphantom, semantics > mfenced, semantics > menclose, semantics > msub, semantics > msup, semantics > msubsup, semantics > munder, semantics > mover, semantics > munderover, semantics > mmultiscripts, semantics > mtable, semantics > mstack, semantics > mlongdiv, semantics > maction {
+ display: none;
+}
+
+/* However, we display all the annotations. */
+annotation, annotation-xml {
+ display: inline-block;
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/mediaControls.css b/chromium/third_party/WebKit/Source/core/css/mediaControls.css
index a2efc1d2bc1..d3b5536e4a4 100644
--- a/chromium/third_party/WebKit/Source/core/css/mediaControls.css
+++ b/chromium/third_party/WebKit/Source/core/css/mediaControls.css
@@ -115,10 +115,40 @@ audio::-webkit-media-controls-mute-button, video::-webkit-media-controls-mute-bu
color: inherit;
}
-audio::-webkit-media-controls-overlay-play-button, video::-webkit-media-controls-overlay-play-button {
+audio::-webkit-media-controls-overlay-enclosure {
display: none;
}
+video::-webkit-media-controls-overlay-enclosure {
+ display: flex;
+ position: relative;
+ flex-direction: column;
+ justify-content: flex-end;
+ align-items: center;
+ flex: 1 1;
+ width: 100%;
+ max-width: 800px;
+ text-indent: 0;
+ box-sizing: border-box;
+ overflow: hidden;
+}
+
+video::-webkit-media-controls-overlay-play-button {
+ -webkit-appearance: media-overlay-play-button;
+ display: flex;
+ position: absolute;
+ top: 50%;
+ left: 50%;
+ margin-left: -40px;
+ margin-top: -40px;
+ border: none;
+ box-sizing: border-box;
+ background-color: transparent;
+ width: 80px;
+ height: 80px;
+ padding: 0;
+}
+
audio::-webkit-media-controls-play-button, video::-webkit-media-controls-play-button {
-webkit-appearance: media-play-button;
display: flex;
@@ -231,26 +261,6 @@ input[type="range"]::-webkit-media-slider-thumb {
margin-right: -7px;
}
-audio::-webkit-media-controls-seek-back-button, video::-webkit-media-controls-seek-back-button {
- -webkit-appearance: media-seek-back-button;
- display: flex;
- width: 16px;
- height: 16px;
- background-color: initial;
- border: initial;
- color: inherit;
-}
-
-audio::-webkit-media-controls-seek-forward-button, video::-webkit-media-controls-seek-forward-button {
- -webkit-appearance: media-seek-forward-button;
- display: flex;
- width: 16px;
- height: 16px;
- background-color: initial;
- border: initial;
- color: inherit;
-}
-
audio::-webkit-media-controls-fullscreen-button, video::-webkit-media-controls-fullscreen-button {
-webkit-appearance: media-enter-fullscreen-button;
display: flex;
@@ -267,20 +277,6 @@ audio::-webkit-media-controls-fullscreen-button, video::-webkit-media-controls-f
color: inherit;
}
-audio::-webkit-media-controls-rewind-button, video::-webkit-media-controls-rewind-button {
- display: none;
- background-color: initial;
- border: initial;
- color: inherit;
-}
-
-audio::-webkit-media-controls-return-to-realtime-button, video::-webkit-media-controls-return-to-realtime-button {
- display: none;
- background-color: initial;
- border: initial;
- color: inherit;
-}
-
audio::-webkit-media-controls-toggle-closed-captions-button {
display: none;
}
@@ -301,14 +297,6 @@ video::-webkit-media-controls-toggle-closed-captions-button {
color: inherit;
}
-audio::-webkit-media-controls-volume-slider-mute-button, video::-webkit-media-controls-volume-slider-mute-button {
- -webkit-appearance: media-volume-slider-mute-button;
- display: none;
- background-color: initial;
- border: initial;
- color: inherit;
-}
-
audio::-webkit-media-controls-fullscreen-volume-slider, video::-webkit-media-controls-fullscreen-volume-slider {
display: none;
}
diff --git a/chromium/third_party/WebKit/Source/core/css/mediaControlsAndroid.css b/chromium/third_party/WebKit/Source/core/css/mediaControlsAndroid.css
index 35a0bb4435e..107d18106b7 100644
--- a/chromium/third_party/WebKit/Source/core/css/mediaControlsAndroid.css
+++ b/chromium/third_party/WebKit/Source/core/css/mediaControlsAndroid.css
@@ -38,24 +38,6 @@ video::-webkit-media-controls-enclosure {
height: 40px;
}
-audio::-webkit-media-controls-overlay-enclosure {
- display: none;
-}
-
-video::-webkit-media-controls-overlay-enclosure {
- display: flex;
- position: relative;
- flex-direction: column;
- justify-content: flex-end;
- align-items: center;
- flex: 1 1;
- width: 100%;
- max-width: 800px;
- text-indent: 0;
- box-sizing: border-box;
- overflow: hidden;
-}
-
audio::-webkit-media-controls-panel, video::-webkit-media-controls-panel {
height: 35px;
}
@@ -64,22 +46,6 @@ audio::-webkit-media-controls-mute-button, video::-webkit-media-controls-mute-bu
display: none;
}
-video::-webkit-media-controls-overlay-play-button {
- -webkit-appearance: media-overlay-play-button;
- display: flex;
- position: absolute;
- top: 50%;
- left: 50%;
- margin-left: -40px;
- margin-top: -40px;
- border: none;
- box-sizing: border-box;
- background-color: transparent;
- width: 80px;
- height: 80px;
- padding: 0;
-}
-
audio::-webkit-media-controls-play-button, video::-webkit-media-controls-play-button {
width: 35px;
height: 35px;
diff --git a/chromium/third_party/WebKit/Source/core/css/navigationTransitions.css b/chromium/third_party/WebKit/Source/core/css/navigationTransitions.css
new file mode 100644
index 00000000000..4ae2f81d390
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/navigationTransitions.css
@@ -0,0 +1,13 @@
+/*
+ * Copyright 2014 The Chromium Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+body {
+ animation-duration: 300ms;
+ transition-duration: 300ms;
+
+ /* Prevent user interaction. */
+ pointer-events: none !important;
+} \ No newline at end of file
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser-in.cpp b/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser-in.cpp
new file mode 100644
index 00000000000..4b366c75d11
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser-in.cpp
@@ -0,0 +1,2119 @@
+/*
+ * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
+ * Copyright (C) 2005 Allan Sandfeld Jensen (kde@carewolf.com)
+ * Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved.
+ * Copyright (C) 2007 Nicholas Shanks <webkit@nickshanks.com>
+ * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
+ * Copyright (C) 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
+ * Copyright (C) 2012 Adobe Systems Incorporated. All rights reserved.
+ * Copyright (C) 2012 Intel Corporation. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include "config.h"
+#include "core/css/parser/BisonCSSParser.h"
+
+#include "core/CSSValueKeywords.h"
+#include "core/StylePropertyShorthand.h"
+#include "core/css/CSSArrayFunctionValue.h"
+#include "core/css/CSSAspectRatioValue.h"
+#include "core/css/CSSBasicShapes.h"
+#include "core/css/CSSBorderImage.h"
+#include "core/css/CSSCanvasValue.h"
+#include "core/css/CSSCrossfadeValue.h"
+#include "core/css/CSSCursorImageValue.h"
+#include "core/css/CSSFontFaceSrcValue.h"
+#include "core/css/CSSFontFeatureValue.h"
+#include "core/css/CSSFunctionValue.h"
+#include "core/css/CSSGradientValue.h"
+#include "core/css/CSSGridLineNamesValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
+#include "core/css/CSSImageSetValue.h"
+#include "core/css/CSSImageValue.h"
+#include "core/css/CSSInheritedValue.h"
+#include "core/css/CSSInitialValue.h"
+#include "core/css/CSSKeyframeRule.h"
+#include "core/css/CSSKeyframesRule.h"
+#include "core/css/CSSLineBoxContainValue.h"
+#include "core/css/CSSPrimitiveValue.h"
+#include "core/css/CSSPropertySourceData.h"
+#include "core/css/CSSReflectValue.h"
+#include "core/css/CSSSelector.h"
+#include "core/css/CSSShadowValue.h"
+#include "core/css/CSSStyleSheet.h"
+#include "core/css/CSSTimingFunctionValue.h"
+#include "core/css/CSSTransformValue.h"
+#include "core/css/CSSUnicodeRangeValue.h"
+#include "core/css/CSSValueList.h"
+#include "core/css/CSSValuePool.h"
+#include "core/css/Counter.h"
+#include "core/css/HashTools.h"
+#include "core/css/MediaList.h"
+#include "core/css/MediaQueryExp.h"
+#include "core/css/Pair.h"
+#include "core/css/Rect.h"
+#include "core/css/StylePropertySet.h"
+#include "core/css/StyleRule.h"
+#include "core/css/StyleRuleImport.h"
+#include "core/css/StyleSheetContents.h"
+#include "core/css/parser/CSSParserIdioms.h"
+#include "core/dom/Document.h"
+#include "core/frame/FrameConsole.h"
+#include "core/frame/FrameHost.h"
+#include "core/frame/Settings.h"
+#include "core/html/parser/HTMLParserIdioms.h"
+#include "core/inspector/InspectorInstrumentation.h"
+#include "core/rendering/RenderTheme.h"
+#include "platform/FloatConversion.h"
+#include "platform/RuntimeEnabledFeatures.h"
+#include "wtf/BitArray.h"
+#include "wtf/HexNumber.h"
+#include "wtf/text/StringBuffer.h"
+#include "wtf/text/StringBuilder.h"
+#include "wtf/text/StringImpl.h"
+#include "wtf/text/TextEncoding.h"
+#include <limits.h>
+
+#define YYDEBUG 0
+
+#if YYDEBUG > 0
+extern int cssyydebug;
+#endif
+
+int cssyyparse(WebCore::BisonCSSParser*);
+
+using namespace WTF;
+
+namespace WebCore {
+
+static const unsigned INVALID_NUM_PARSED_PROPERTIES = UINT_MAX;
+
+BisonCSSParser::BisonCSSParser(const CSSParserContext& context)
+ : m_context(context)
+ , m_important(false)
+ , m_id(CSSPropertyInvalid)
+ , m_styleSheet(nullptr)
+ , m_supportsCondition(false)
+ , m_selectorListForParseSelector(0)
+ , m_numParsedPropertiesBeforeMarginBox(INVALID_NUM_PARSED_PROPERTIES)
+ , m_hadSyntacticallyValidCSSRule(false)
+ , m_logErrors(false)
+ , m_ignoreErrors(false)
+ , m_defaultNamespace(starAtom)
+ , m_observer(0)
+ , m_source(0)
+ , m_ruleHeaderType(CSSRuleSourceData::UNKNOWN_RULE)
+ , m_allowImportRules(true)
+ , m_allowNamespaceDeclarations(true)
+ , m_inViewport(false)
+ , m_tokenizer(*this)
+{
+#if YYDEBUG > 0
+ cssyydebug = 1;
+#endif
+}
+
+BisonCSSParser::~BisonCSSParser()
+{
+ clearProperties();
+
+ deleteAllValues(m_floatingSelectors);
+ deleteAllValues(m_floatingSelectorVectors);
+ deleteAllValues(m_floatingValueLists);
+ deleteAllValues(m_floatingFunctions);
+}
+
+void BisonCSSParser::setupParser(const char* prefix, unsigned prefixLength, const String& string, const char* suffix, unsigned suffixLength)
+{
+ m_tokenizer.setupTokenizer(prefix, prefixLength, string, suffix, suffixLength);
+ m_ruleHasHeader = true;
+}
+
+void BisonCSSParser::parseSheet(StyleSheetContents* sheet, const String& string, const TextPosition& startPosition, CSSParserObserver* observer, bool logErrors)
+{
+ setStyleSheet(sheet);
+ m_defaultNamespace = starAtom; // Reset the default namespace.
+ TemporaryChange<CSSParserObserver*> scopedObsever(m_observer, observer);
+ m_logErrors = logErrors && sheet->singleOwnerDocument() && !sheet->baseURL().isEmpty() && sheet->singleOwnerDocument()->frameHost();
+ m_ignoreErrors = false;
+ m_tokenizer.m_lineNumber = 0;
+ m_startPosition = startPosition;
+ m_source = &string;
+ m_tokenizer.m_internal = false;
+ setupParser("", string, "");
+ cssyyparse(this);
+ sheet->shrinkToFit();
+ m_source = 0;
+ m_rule = nullptr;
+ m_lineEndings.clear();
+ m_ignoreErrors = false;
+ m_logErrors = false;
+ m_tokenizer.m_internal = true;
+}
+
+PassRefPtrWillBeRawPtr<StyleRuleBase> BisonCSSParser::parseRule(StyleSheetContents* sheet, const String& string)
+{
+ setStyleSheet(sheet);
+ m_allowNamespaceDeclarations = false;
+ setupParser("@-internal-rule ", string, "");
+ cssyyparse(this);
+ return m_rule.release();
+}
+
+PassRefPtrWillBeRawPtr<StyleKeyframe> BisonCSSParser::parseKeyframeRule(StyleSheetContents* sheet, const String& string)
+{
+ setStyleSheet(sheet);
+ setupParser("@-internal-keyframe-rule ", string, "");
+ cssyyparse(this);
+ return m_keyframe.release();
+}
+
+PassOwnPtr<Vector<double> > BisonCSSParser::parseKeyframeKeyList(const String& string)
+{
+ setupParser("@-internal-keyframe-key-list ", string, "");
+ cssyyparse(this);
+ ASSERT(m_valueList);
+ return StyleKeyframe::createKeyList(m_valueList.get());
+}
+
+bool BisonCSSParser::parseSupportsCondition(const String& string)
+{
+ m_supportsCondition = false;
+ setupParser("@-internal-supports-condition ", string, "");
+ cssyyparse(this);
+ return m_supportsCondition;
+}
+
+static inline bool isColorPropertyID(CSSPropertyID propertyId)
+{
+ switch (propertyId) {
+ case CSSPropertyColor:
+ case CSSPropertyBackgroundColor:
+ case CSSPropertyBorderBottomColor:
+ case CSSPropertyBorderLeftColor:
+ case CSSPropertyBorderRightColor:
+ case CSSPropertyBorderTopColor:
+ case CSSPropertyOutlineColor:
+ case CSSPropertyTextLineThroughColor:
+ case CSSPropertyTextOverlineColor:
+ case CSSPropertyTextUnderlineColor:
+ case CSSPropertyWebkitBorderAfterColor:
+ case CSSPropertyWebkitBorderBeforeColor:
+ case CSSPropertyWebkitBorderEndColor:
+ case CSSPropertyWebkitBorderStartColor:
+ case CSSPropertyWebkitColumnRuleColor:
+ case CSSPropertyWebkitTextEmphasisColor:
+ case CSSPropertyWebkitTextFillColor:
+ case CSSPropertyWebkitTextStrokeColor:
+ return true;
+ case CSSPropertyTextDecorationColor:
+ return RuntimeEnabledFeatures::css3TextDecorationsEnabled();
+ default:
+ return false;
+ }
+}
+
+static bool parseColorValue(MutableStylePropertySet* declaration, CSSPropertyID propertyId, const String& string, bool important, CSSParserMode cssParserMode)
+{
+ ASSERT(!string.isEmpty());
+ bool quirksMode = isQuirksModeBehavior(cssParserMode);
+ if (!isColorPropertyID(propertyId))
+ return false;
+ CSSParserString cssString;
+ cssString.init(string);
+ CSSValueID valueID = cssValueKeywordID(cssString);
+ bool validPrimitive = false;
+ if (valueID == CSSValueWebkitText) {
+ validPrimitive = true;
+ } else if (valueID == CSSValueCurrentcolor) {
+ validPrimitive = true;
+ } else if ((valueID >= CSSValueAqua && valueID <= CSSValueWindowtext) || valueID == CSSValueMenu
+ || (quirksMode && valueID >= CSSValueWebkitFocusRingColor && valueID < CSSValueWebkitText)) {
+ validPrimitive = true;
+ }
+
+ if (validPrimitive) {
+ RefPtrWillBeRawPtr<CSSValue> value = cssValuePool().createIdentifierValue(valueID);
+ declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
+ return true;
+ }
+ RGBA32 color;
+ if (!CSSPropertyParser::fastParseColor(color, string, !quirksMode && string[0] != '#'))
+ return false;
+ RefPtrWillBeRawPtr<CSSValue> value = cssValuePool().createColorValue(color);
+ declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
+ return true;
+}
+
+static inline bool isSimpleLengthPropertyID(CSSPropertyID propertyId, bool& acceptsNegativeNumbers)
+{
+ switch (propertyId) {
+ case CSSPropertyFontSize:
+ case CSSPropertyHeight:
+ case CSSPropertyWidth:
+ case CSSPropertyMinHeight:
+ case CSSPropertyMinWidth:
+ case CSSPropertyPaddingBottom:
+ case CSSPropertyPaddingLeft:
+ case CSSPropertyPaddingRight:
+ case CSSPropertyPaddingTop:
+ case CSSPropertyWebkitLogicalWidth:
+ case CSSPropertyWebkitLogicalHeight:
+ case CSSPropertyWebkitMinLogicalWidth:
+ case CSSPropertyWebkitMinLogicalHeight:
+ case CSSPropertyWebkitPaddingAfter:
+ case CSSPropertyWebkitPaddingBefore:
+ case CSSPropertyWebkitPaddingEnd:
+ case CSSPropertyWebkitPaddingStart:
+ acceptsNegativeNumbers = false;
+ return true;
+ case CSSPropertyShapeMargin:
+ acceptsNegativeNumbers = false;
+ return RuntimeEnabledFeatures::cssShapesEnabled();
+ case CSSPropertyBottom:
+ case CSSPropertyLeft:
+ case CSSPropertyMarginBottom:
+ case CSSPropertyMarginLeft:
+ case CSSPropertyMarginRight:
+ case CSSPropertyMarginTop:
+ case CSSPropertyRight:
+ case CSSPropertyTop:
+ case CSSPropertyWebkitMarginAfter:
+ case CSSPropertyWebkitMarginBefore:
+ case CSSPropertyWebkitMarginEnd:
+ case CSSPropertyWebkitMarginStart:
+ acceptsNegativeNumbers = true;
+ return true;
+ default:
+ return false;
+ }
+}
+
+template <typename CharacterType>
+static inline bool parseSimpleLength(const CharacterType* characters, unsigned length, CSSPrimitiveValue::UnitType& unit, double& number)
+{
+ if (length > 2 && (characters[length - 2] | 0x20) == 'p' && (characters[length - 1] | 0x20) == 'x') {
+ length -= 2;
+ unit = CSSPrimitiveValue::CSS_PX;
+ } else if (length > 1 && characters[length - 1] == '%') {
+ length -= 1;
+ unit = CSSPrimitiveValue::CSS_PERCENTAGE;
+ }
+
+ // We rely on charactersToDouble for validation as well. The function
+ // will set "ok" to "false" if the entire passed-in character range does
+ // not represent a double.
+ bool ok;
+ number = charactersToDouble(characters, length, &ok);
+ return ok;
+}
+
+static bool parseSimpleLengthValue(MutableStylePropertySet* declaration, CSSPropertyID propertyId, const String& string, bool important, CSSParserMode cssParserMode)
+{
+ ASSERT(!string.isEmpty());
+ bool acceptsNegativeNumbers = false;
+
+ // In @viewport, width and height are shorthands, not simple length values.
+ if (isCSSViewportParsingEnabledForMode(cssParserMode) || !isSimpleLengthPropertyID(propertyId, acceptsNegativeNumbers))
+ return false;
+
+ unsigned length = string.length();
+ double number;
+ CSSPrimitiveValue::UnitType unit = CSSPrimitiveValue::CSS_NUMBER;
+
+ if (string.is8Bit()) {
+ if (!parseSimpleLength(string.characters8(), length, unit, number))
+ return false;
+ } else {
+ if (!parseSimpleLength(string.characters16(), length, unit, number))
+ return false;
+ }
+
+ if (unit == CSSPrimitiveValue::CSS_NUMBER) {
+ bool quirksMode = isQuirksModeBehavior(cssParserMode);
+ if (number && !quirksMode)
+ return false;
+ unit = CSSPrimitiveValue::CSS_PX;
+ }
+ if (number < 0 && !acceptsNegativeNumbers)
+ return false;
+
+ RefPtrWillBeRawPtr<CSSValue> value = cssValuePool().createValue(number, unit);
+ declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
+ return true;
+}
+
+bool isValidKeywordPropertyAndValue(CSSPropertyID propertyId, CSSValueID valueID, const CSSParserContext& parserContext)
+{
+ if (valueID == CSSValueInvalid)
+ return false;
+
+ switch (propertyId) {
+ case CSSPropertyBackgroundRepeatX: // repeat | no-repeat
+ case CSSPropertyBackgroundRepeatY: // repeat | no-repeat
+ return valueID == CSSValueRepeat || valueID == CSSValueNoRepeat;
+ case CSSPropertyBorderCollapse: // collapse | separate
+ return valueID == CSSValueCollapse || valueID == CSSValueSeparate;
+ case CSSPropertyBorderTopStyle: // <border-style>
+ case CSSPropertyBorderRightStyle: // Defined as: none | hidden | dotted | dashed |
+ case CSSPropertyBorderBottomStyle: // solid | double | groove | ridge | inset | outset
+ case CSSPropertyBorderLeftStyle:
+ case CSSPropertyWebkitBorderAfterStyle:
+ case CSSPropertyWebkitBorderBeforeStyle:
+ case CSSPropertyWebkitBorderEndStyle:
+ case CSSPropertyWebkitBorderStartStyle:
+ case CSSPropertyWebkitColumnRuleStyle:
+ return valueID >= CSSValueNone && valueID <= CSSValueDouble;
+ case CSSPropertyBoxSizing:
+ return valueID == CSSValueBorderBox || valueID == CSSValueContentBox;
+ case CSSPropertyCaptionSide: // top | bottom | left | right
+ return valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueTop || valueID == CSSValueBottom;
+ case CSSPropertyClear: // none | left | right | both
+ return valueID == CSSValueNone || valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueBoth;
+ case CSSPropertyDirection: // ltr | rtl
+ return valueID == CSSValueLtr || valueID == CSSValueRtl;
+ case CSSPropertyDisplay:
+ // inline | block | list-item | inline-block | table |
+ // inline-table | table-row-group | table-header-group | table-footer-group | table-row |
+ // table-column-group | table-column | table-cell | table-caption | -webkit-box | -webkit-inline-box | none
+ // flex | inline-flex | -webkit-flex | -webkit-inline-flex | grid | inline-grid | lazy-block
+ return (valueID >= CSSValueInline && valueID <= CSSValueInlineFlex) || valueID == CSSValueWebkitFlex || valueID == CSSValueWebkitInlineFlex || valueID == CSSValueNone
+ || (RuntimeEnabledFeatures::cssGridLayoutEnabled() && (valueID == CSSValueGrid || valueID == CSSValueInlineGrid));
+ case CSSPropertyEmptyCells: // show | hide
+ return valueID == CSSValueShow || valueID == CSSValueHide;
+ case CSSPropertyFloat: // left | right | none | center (for buggy CSS, maps to none)
+ return valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueNone || valueID == CSSValueCenter;
+ case CSSPropertyFontStyle: // normal | italic | oblique
+ return valueID == CSSValueNormal || valueID == CSSValueItalic || valueID == CSSValueOblique;
+ case CSSPropertyImageRendering: // auto | optimizeContrast
+ return valueID == CSSValueAuto || valueID == CSSValueWebkitOptimizeContrast;
+ case CSSPropertyIsolation: // auto | isolate
+ return RuntimeEnabledFeatures::cssCompositingEnabled()
+ && (valueID == CSSValueAuto || valueID == CSSValueIsolate);
+ case CSSPropertyListStylePosition: // inside | outside
+ return valueID == CSSValueInside || valueID == CSSValueOutside;
+ case CSSPropertyListStyleType:
+ // See section CSS_PROP_LIST_STYLE_TYPE of file CSSValueKeywords.in
+ // for the list of supported list-style-types.
+ return (valueID >= CSSValueDisc && valueID <= CSSValueKatakanaIroha) || valueID == CSSValueNone;
+ case CSSPropertyObjectFit:
+ return RuntimeEnabledFeatures::objectFitPositionEnabled()
+ && (valueID == CSSValueFill || valueID == CSSValueContain || valueID == CSSValueCover || valueID == CSSValueNone || valueID == CSSValueScaleDown);
+ case CSSPropertyOutlineStyle: // (<border-style> except hidden) | auto
+ return valueID == CSSValueAuto || valueID == CSSValueNone || (valueID >= CSSValueInset && valueID <= CSSValueDouble);
+ case CSSPropertyOverflowWrap: // normal | break-word
+ case CSSPropertyWordWrap:
+ return valueID == CSSValueNormal || valueID == CSSValueBreakWord;
+ case CSSPropertyOverflowX: // visible | hidden | scroll | auto | overlay
+ return valueID == CSSValueVisible || valueID == CSSValueHidden || valueID == CSSValueScroll || valueID == CSSValueAuto || valueID == CSSValueOverlay;
+ case CSSPropertyOverflowY: // visible | hidden | scroll | auto | overlay | -webkit-paged-x | -webkit-paged-y
+ return valueID == CSSValueVisible || valueID == CSSValueHidden || valueID == CSSValueScroll || valueID == CSSValueAuto || valueID == CSSValueOverlay || valueID == CSSValueWebkitPagedX || valueID == CSSValueWebkitPagedY;
+ case CSSPropertyPageBreakAfter: // auto | always | avoid | left | right
+ case CSSPropertyPageBreakBefore:
+ case CSSPropertyWebkitColumnBreakAfter:
+ case CSSPropertyWebkitColumnBreakBefore:
+ return valueID == CSSValueAuto || valueID == CSSValueAlways || valueID == CSSValueAvoid || valueID == CSSValueLeft || valueID == CSSValueRight;
+ case CSSPropertyPageBreakInside: // avoid | auto
+ case CSSPropertyWebkitColumnBreakInside:
+ return valueID == CSSValueAuto || valueID == CSSValueAvoid;
+ case CSSPropertyPointerEvents:
+ // none | visiblePainted | visibleFill | visibleStroke | visible |
+ // painted | fill | stroke | auto | all | bounding-box
+ return valueID == CSSValueVisible || valueID == CSSValueNone || valueID == CSSValueAll || valueID == CSSValueAuto || (valueID >= CSSValueVisiblepainted && valueID <= CSSValueBoundingBox);
+ case CSSPropertyPosition: // static | relative | absolute | fixed | sticky
+ return valueID == CSSValueStatic || valueID == CSSValueRelative || valueID == CSSValueAbsolute || valueID == CSSValueFixed
+ || (RuntimeEnabledFeatures::cssStickyPositionEnabled() && valueID == CSSValueSticky);
+ case CSSPropertyResize: // none | both | horizontal | vertical | auto
+ return valueID == CSSValueNone || valueID == CSSValueBoth || valueID == CSSValueHorizontal || valueID == CSSValueVertical || valueID == CSSValueAuto;
+ case CSSPropertyScrollBehavior: // instant | smooth
+ return RuntimeEnabledFeatures::cssomSmoothScrollEnabled()
+ && (valueID == CSSValueInstant || valueID == CSSValueSmooth);
+ case CSSPropertySpeak: // none | normal | spell-out | digits | literal-punctuation | no-punctuation
+ return valueID == CSSValueNone || valueID == CSSValueNormal || valueID == CSSValueSpellOut || valueID == CSSValueDigits || valueID == CSSValueLiteralPunctuation || valueID == CSSValueNoPunctuation;
+ case CSSPropertyTableLayout: // auto | fixed
+ return valueID == CSSValueAuto || valueID == CSSValueFixed;
+ case CSSPropertyTextAlignLast:
+ // auto | start | end | left | right | center | justify
+ return RuntimeEnabledFeatures::css3TextEnabled()
+ && ((valueID >= CSSValueLeft && valueID <= CSSValueJustify) || valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueAuto);
+ case CSSPropertyTextJustify:
+ // auto | none | inter-word | distribute
+ return RuntimeEnabledFeatures::css3TextEnabled()
+ && (valueID == CSSValueInterWord || valueID == CSSValueDistribute || valueID == CSSValueAuto || valueID == CSSValueNone);
+ case CSSPropertyTextLineThroughMode:
+ case CSSPropertyTextOverlineMode:
+ case CSSPropertyTextUnderlineMode:
+ return valueID == CSSValueContinuous || valueID == CSSValueSkipWhiteSpace;
+ case CSSPropertyTextLineThroughStyle:
+ case CSSPropertyTextOverlineStyle:
+ case CSSPropertyTextUnderlineStyle:
+ return valueID == CSSValueNone || valueID == CSSValueSolid || valueID == CSSValueDouble || valueID == CSSValueDashed || valueID == CSSValueDotDash || valueID == CSSValueDotDotDash || valueID == CSSValueWave;
+ case CSSPropertyTextOverflow: // clip | ellipsis
+ return valueID == CSSValueClip || valueID == CSSValueEllipsis;
+ case CSSPropertyTextRendering: // auto | optimizeSpeed | optimizeLegibility | geometricPrecision
+ return valueID == CSSValueAuto || valueID == CSSValueOptimizespeed || valueID == CSSValueOptimizelegibility || valueID == CSSValueGeometricprecision;
+ case CSSPropertyTextTransform: // capitalize | uppercase | lowercase | none
+ return (valueID >= CSSValueCapitalize && valueID <= CSSValueLowercase) || valueID == CSSValueNone;
+ case CSSPropertyTouchActionDelay: // none | script
+ return RuntimeEnabledFeatures::cssTouchActionDelayEnabled()
+ && (valueID == CSSValueScript || valueID == CSSValueNone);
+ case CSSPropertyVisibility: // visible | hidden | collapse
+ return valueID == CSSValueVisible || valueID == CSSValueHidden || valueID == CSSValueCollapse;
+ case CSSPropertyWebkitAppearance:
+ return (valueID >= CSSValueCheckbox && valueID <= CSSValueTextarea) || valueID == CSSValueNone;
+ case CSSPropertyBackfaceVisibility:
+ case CSSPropertyWebkitBackfaceVisibility:
+ return valueID == CSSValueVisible || valueID == CSSValueHidden;
+ case CSSPropertyMixBlendMode:
+ return RuntimeEnabledFeatures::cssCompositingEnabled()
+ && (valueID == CSSValueNormal || valueID == CSSValueMultiply || valueID == CSSValueScreen || valueID == CSSValueOverlay
+ || valueID == CSSValueDarken || valueID == CSSValueLighten || valueID == CSSValueColorDodge || valueID == CSSValueColorBurn
+ || valueID == CSSValueHardLight || valueID == CSSValueSoftLight || valueID == CSSValueDifference || valueID == CSSValueExclusion
+ || valueID == CSSValueHue || valueID == CSSValueSaturation || valueID == CSSValueColor || valueID == CSSValueLuminosity);
+ case CSSPropertyWebkitBorderFit:
+ return valueID == CSSValueBorder || valueID == CSSValueLines;
+ case CSSPropertyWebkitBoxAlign:
+ return valueID == CSSValueStretch || valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueCenter || valueID == CSSValueBaseline;
+ case CSSPropertyWebkitBoxDecorationBreak:
+ return valueID == CSSValueClone || valueID == CSSValueSlice;
+ case CSSPropertyWebkitBoxDirection:
+ return valueID == CSSValueNormal || valueID == CSSValueReverse;
+ case CSSPropertyWebkitBoxLines:
+ return valueID == CSSValueSingle || valueID == CSSValueMultiple;
+ case CSSPropertyWebkitBoxOrient:
+ return valueID == CSSValueHorizontal || valueID == CSSValueVertical || valueID == CSSValueInlineAxis || valueID == CSSValueBlockAxis;
+ case CSSPropertyWebkitBoxPack:
+ return valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueCenter || valueID == CSSValueJustify;
+ case CSSPropertyInternalCallback:
+ // This property is only injected programmatically, not parsed from stylesheets.
+ return false;
+ case CSSPropertyColumnFill:
+ return RuntimeEnabledFeatures::regionBasedColumnsEnabled()
+ && (valueID == CSSValueAuto || valueID == CSSValueBalance);
+ case CSSPropertyAlignContent:
+ // FIXME: Per CSS alignment, this property should accept an optional <overflow-position>. We should share this parsing code with 'justify-self'.
+ return valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueSpaceBetween || valueID == CSSValueSpaceAround || valueID == CSSValueStretch;
+ case CSSPropertyAlignItems:
+ // FIXME: Per CSS alignment, this property should accept the same arguments as 'justify-self' so we should share its parsing code.
+ return valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueBaseline || valueID == CSSValueStretch;
+ case CSSPropertyAlignSelf:
+ // FIXME: Per CSS alignment, this property should accept the same arguments as 'justify-self' so we should share its parsing code.
+ return valueID == CSSValueAuto || valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueBaseline || valueID == CSSValueStretch;
+ case CSSPropertyFlexDirection:
+ return valueID == CSSValueRow || valueID == CSSValueRowReverse || valueID == CSSValueColumn || valueID == CSSValueColumnReverse;
+ case CSSPropertyFlexWrap:
+ return valueID == CSSValueNowrap || valueID == CSSValueWrap || valueID == CSSValueWrapReverse;
+ case CSSPropertyJustifyContent:
+ // FIXME: Per CSS alignment, this property should accept an optional <overflow-position>. We should share this parsing code with 'justify-self'.
+ return valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueSpaceBetween || valueID == CSSValueSpaceAround;
+ case CSSPropertyFontKerning:
+ return valueID == CSSValueAuto || valueID == CSSValueNormal || valueID == CSSValueNone;
+ case CSSPropertyWebkitFontSmoothing:
+ return valueID == CSSValueAuto || valueID == CSSValueNone || valueID == CSSValueAntialiased || valueID == CSSValueSubpixelAntialiased;
+ case CSSPropertyGridAutoFlow:
+ return RuntimeEnabledFeatures::cssGridLayoutEnabled()
+ && (valueID == CSSValueNone || valueID == CSSValueRow || valueID == CSSValueColumn);
+ case CSSPropertyWebkitLineBreak: // auto | loose | normal | strict | after-white-space
+ return valueID == CSSValueAuto || valueID == CSSValueLoose || valueID == CSSValueNormal || valueID == CSSValueStrict || valueID == CSSValueAfterWhiteSpace;
+ case CSSPropertyWebkitMarginAfterCollapse:
+ case CSSPropertyWebkitMarginBeforeCollapse:
+ case CSSPropertyWebkitMarginBottomCollapse:
+ case CSSPropertyWebkitMarginTopCollapse:
+ return valueID == CSSValueCollapse || valueID == CSSValueSeparate || valueID == CSSValueDiscard;
+ case CSSPropertyInternalMarqueeDirection:
+ return valueID == CSSValueForwards || valueID == CSSValueBackwards || valueID == CSSValueAhead || valueID == CSSValueReverse || valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueDown
+ || valueID == CSSValueUp || valueID == CSSValueAuto;
+ case CSSPropertyInternalMarqueeStyle:
+ return valueID == CSSValueNone || valueID == CSSValueSlide || valueID == CSSValueScroll || valueID == CSSValueAlternate;
+ case CSSPropertyWebkitPrintColorAdjust:
+ return valueID == CSSValueExact || valueID == CSSValueEconomy;
+ case CSSPropertyWebkitRtlOrdering:
+ return valueID == CSSValueLogical || valueID == CSSValueVisual;
+ case CSSPropertyWebkitRubyPosition:
+ return valueID == CSSValueBefore || valueID == CSSValueAfter;
+ case CSSPropertyWebkitTextCombine:
+ return valueID == CSSValueNone || valueID == CSSValueHorizontal;
+ case CSSPropertyWebkitTextEmphasisPosition:
+ return valueID == CSSValueOver || valueID == CSSValueUnder;
+ case CSSPropertyWebkitTextSecurity: // disc | circle | square | none
+ return valueID == CSSValueDisc || valueID == CSSValueCircle || valueID == CSSValueSquare || valueID == CSSValueNone;
+ case CSSPropertyTransformStyle:
+ case CSSPropertyWebkitTransformStyle:
+ return valueID == CSSValueFlat || valueID == CSSValuePreserve3d;
+ case CSSPropertyWebkitUserDrag: // auto | none | element
+ return valueID == CSSValueAuto || valueID == CSSValueNone || valueID == CSSValueElement;
+ case CSSPropertyWebkitUserModify: // read-only | read-write
+ return valueID == CSSValueReadOnly || valueID == CSSValueReadWrite || valueID == CSSValueReadWritePlaintextOnly;
+ case CSSPropertyWebkitUserSelect: // auto | none | text | all
+ return valueID == CSSValueAuto || valueID == CSSValueNone || valueID == CSSValueText || valueID == CSSValueAll;
+ case CSSPropertyWebkitWrapFlow:
+ return RuntimeEnabledFeatures::cssExclusionsEnabled()
+ && (valueID == CSSValueAuto || valueID == CSSValueBoth || valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueMaximum || valueID == CSSValueClear);
+ case CSSPropertyWebkitWrapThrough:
+ return RuntimeEnabledFeatures::cssExclusionsEnabled()
+ && (valueID == CSSValueWrap || valueID == CSSValueNone);
+ case CSSPropertyWebkitWritingMode:
+ return valueID >= CSSValueHorizontalTb && valueID <= CSSValueHorizontalBt;
+ case CSSPropertyWhiteSpace: // normal | pre | nowrap
+ return valueID == CSSValueNormal || valueID == CSSValuePre || valueID == CSSValuePreWrap || valueID == CSSValuePreLine || valueID == CSSValueNowrap;
+ case CSSPropertyWordBreak: // normal | break-all | break-word (this is a custom extension)
+ return valueID == CSSValueNormal || valueID == CSSValueBreakAll || valueID == CSSValueBreakWord;
+ default:
+ ASSERT_NOT_REACHED();
+ return false;
+ }
+ return false;
+}
+
+bool isKeywordPropertyID(CSSPropertyID propertyId)
+{
+ switch (propertyId) {
+ case CSSPropertyMixBlendMode:
+ case CSSPropertyIsolation:
+ case CSSPropertyBackgroundRepeatX:
+ case CSSPropertyBackgroundRepeatY:
+ case CSSPropertyBorderBottomStyle:
+ case CSSPropertyBorderCollapse:
+ case CSSPropertyBorderLeftStyle:
+ case CSSPropertyBorderRightStyle:
+ case CSSPropertyBorderTopStyle:
+ case CSSPropertyBoxSizing:
+ case CSSPropertyCaptionSide:
+ case CSSPropertyClear:
+ case CSSPropertyDirection:
+ case CSSPropertyDisplay:
+ case CSSPropertyEmptyCells:
+ case CSSPropertyFloat:
+ case CSSPropertyFontStyle:
+ case CSSPropertyImageRendering:
+ case CSSPropertyListStylePosition:
+ case CSSPropertyListStyleType:
+ case CSSPropertyObjectFit:
+ case CSSPropertyOutlineStyle:
+ case CSSPropertyOverflowWrap:
+ case CSSPropertyOverflowX:
+ case CSSPropertyOverflowY:
+ case CSSPropertyPageBreakAfter:
+ case CSSPropertyPageBreakBefore:
+ case CSSPropertyPageBreakInside:
+ case CSSPropertyPointerEvents:
+ case CSSPropertyPosition:
+ case CSSPropertyResize:
+ case CSSPropertyScrollBehavior:
+ case CSSPropertySpeak:
+ case CSSPropertyTableLayout:
+ case CSSPropertyTextAlignLast:
+ case CSSPropertyTextJustify:
+ case CSSPropertyTextLineThroughMode:
+ case CSSPropertyTextLineThroughStyle:
+ case CSSPropertyTextOverflow:
+ case CSSPropertyTextOverlineMode:
+ case CSSPropertyTextOverlineStyle:
+ case CSSPropertyTextRendering:
+ case CSSPropertyTextTransform:
+ case CSSPropertyTextUnderlineMode:
+ case CSSPropertyTextUnderlineStyle:
+ case CSSPropertyTouchActionDelay:
+ case CSSPropertyVisibility:
+ case CSSPropertyWebkitAppearance:
+ case CSSPropertyBackfaceVisibility:
+ case CSSPropertyWebkitBackfaceVisibility:
+ case CSSPropertyWebkitBorderAfterStyle:
+ case CSSPropertyWebkitBorderBeforeStyle:
+ case CSSPropertyWebkitBorderEndStyle:
+ case CSSPropertyWebkitBorderFit:
+ case CSSPropertyWebkitBorderStartStyle:
+ case CSSPropertyWebkitBoxAlign:
+ case CSSPropertyWebkitBoxDecorationBreak:
+ case CSSPropertyWebkitBoxDirection:
+ case CSSPropertyWebkitBoxLines:
+ case CSSPropertyWebkitBoxOrient:
+ case CSSPropertyWebkitBoxPack:
+ case CSSPropertyInternalCallback:
+ case CSSPropertyWebkitColumnBreakAfter:
+ case CSSPropertyWebkitColumnBreakBefore:
+ case CSSPropertyWebkitColumnBreakInside:
+ case CSSPropertyColumnFill:
+ case CSSPropertyWebkitColumnRuleStyle:
+ case CSSPropertyAlignContent:
+ case CSSPropertyFlexDirection:
+ case CSSPropertyFlexWrap:
+ case CSSPropertyJustifyContent:
+ case CSSPropertyFontKerning:
+ case CSSPropertyWebkitFontSmoothing:
+ case CSSPropertyGridAutoFlow:
+ case CSSPropertyWebkitLineBreak:
+ case CSSPropertyWebkitMarginAfterCollapse:
+ case CSSPropertyWebkitMarginBeforeCollapse:
+ case CSSPropertyWebkitMarginBottomCollapse:
+ case CSSPropertyWebkitMarginTopCollapse:
+ case CSSPropertyInternalMarqueeDirection:
+ case CSSPropertyInternalMarqueeStyle:
+ case CSSPropertyWebkitPrintColorAdjust:
+ case CSSPropertyWebkitRtlOrdering:
+ case CSSPropertyWebkitRubyPosition:
+ case CSSPropertyWebkitTextCombine:
+ case CSSPropertyWebkitTextEmphasisPosition:
+ case CSSPropertyWebkitTextSecurity:
+ case CSSPropertyTransformStyle:
+ case CSSPropertyWebkitTransformStyle:
+ case CSSPropertyWebkitUserDrag:
+ case CSSPropertyWebkitUserModify:
+ case CSSPropertyWebkitUserSelect:
+ case CSSPropertyWebkitWrapFlow:
+ case CSSPropertyWebkitWrapThrough:
+ case CSSPropertyWebkitWritingMode:
+ case CSSPropertyWhiteSpace:
+ case CSSPropertyWordBreak:
+ case CSSPropertyWordWrap:
+ return true;
+ case CSSPropertyAlignItems:
+ case CSSPropertyAlignSelf:
+ return !RuntimeEnabledFeatures::cssGridLayoutEnabled();
+ default:
+ return false;
+ }
+}
+
+static bool parseKeywordValue(MutableStylePropertySet* declaration, CSSPropertyID propertyId, const String& string, bool important, const CSSParserContext& parserContext)
+{
+ ASSERT(!string.isEmpty());
+
+ if (!isKeywordPropertyID(propertyId)) {
+ // All properties accept the values of "initial" and "inherit".
+ String lowerCaseString = string.lower();
+ if (lowerCaseString != "initial" && lowerCaseString != "inherit")
+ return false;
+
+ // Parse initial/inherit shorthands using the BisonCSSParser.
+ if (shorthandForProperty(propertyId).length())
+ return false;
+ }
+
+ CSSParserString cssString;
+ cssString.init(string);
+ CSSValueID valueID = cssValueKeywordID(cssString);
+
+ if (!valueID)
+ return false;
+
+ RefPtrWillBeRawPtr<CSSValue> value = nullptr;
+ if (valueID == CSSValueInherit)
+ value = cssValuePool().createInheritedValue();
+ else if (valueID == CSSValueInitial)
+ value = cssValuePool().createExplicitInitialValue();
+ else if (isValidKeywordPropertyAndValue(propertyId, valueID, parserContext))
+ value = cssValuePool().createIdentifierValue(valueID);
+ else
+ return false;
+
+ declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
+ return true;
+}
+
+template <typename CharType>
+static bool parseTransformTranslateArguments(CharType*& pos, CharType* end, unsigned expectedCount, CSSTransformValue* transformValue)
+{
+ while (expectedCount) {
+ size_t delimiter = WTF::find(pos, end - pos, expectedCount == 1 ? ')' : ',');
+ if (delimiter == kNotFound)
+ return false;
+ unsigned argumentLength = static_cast<unsigned>(delimiter);
+ CSSPrimitiveValue::UnitType unit = CSSPrimitiveValue::CSS_NUMBER;
+ double number;
+ if (!parseSimpleLength(pos, argumentLength, unit, number))
+ return false;
+ if (unit != CSSPrimitiveValue::CSS_PX && (number || unit != CSSPrimitiveValue::CSS_NUMBER))
+ return false;
+ transformValue->append(cssValuePool().createValue(number, CSSPrimitiveValue::CSS_PX));
+ pos += argumentLength + 1;
+ --expectedCount;
+ }
+ return true;
+}
+
+template <typename CharType>
+static bool parseTransformNumberArguments(CharType*& pos, CharType* end, unsigned expectedCount, CSSTransformValue* transformValue)
+{
+ while (expectedCount) {
+ size_t delimiter = WTF::find(pos, end - pos, expectedCount == 1 ? ')' : ',');
+ if (delimiter == kNotFound)
+ return false;
+ unsigned argumentLength = static_cast<unsigned>(delimiter);
+ bool ok;
+ double number = charactersToDouble(pos, argumentLength, &ok);
+ if (!ok)
+ return false;
+ transformValue->append(cssValuePool().createValue(number, CSSPrimitiveValue::CSS_NUMBER));
+ pos += argumentLength + 1;
+ --expectedCount;
+ }
+ return true;
+}
+
+template <typename CharType>
+static PassRefPtrWillBeRawPtr<CSSTransformValue> parseSimpleTransformValue(CharType*& pos, CharType* end)
+{
+ static const int shortestValidTransformStringLength = 12;
+
+ if (end - pos < shortestValidTransformStringLength)
+ return nullptr;
+
+ const bool isTranslate = toASCIILower(pos[0]) == 't'
+ && toASCIILower(pos[1]) == 'r'
+ && toASCIILower(pos[2]) == 'a'
+ && toASCIILower(pos[3]) == 'n'
+ && toASCIILower(pos[4]) == 's'
+ && toASCIILower(pos[5]) == 'l'
+ && toASCIILower(pos[6]) == 'a'
+ && toASCIILower(pos[7]) == 't'
+ && toASCIILower(pos[8]) == 'e';
+
+ if (isTranslate) {
+ CSSTransformValue::TransformOperationType transformType;
+ unsigned expectedArgumentCount = 1;
+ unsigned argumentStart = 11;
+ CharType c9 = toASCIILower(pos[9]);
+ if (c9 == 'x' && pos[10] == '(') {
+ transformType = CSSTransformValue::TranslateXTransformOperation;
+ } else if (c9 == 'y' && pos[10] == '(') {
+ transformType = CSSTransformValue::TranslateYTransformOperation;
+ } else if (c9 == 'z' && pos[10] == '(') {
+ transformType = CSSTransformValue::TranslateZTransformOperation;
+ } else if (c9 == '(') {
+ transformType = CSSTransformValue::TranslateTransformOperation;
+ expectedArgumentCount = 2;
+ argumentStart = 10;
+ } else if (c9 == '3' && toASCIILower(pos[10]) == 'd' && pos[11] == '(') {
+ transformType = CSSTransformValue::Translate3DTransformOperation;
+ expectedArgumentCount = 3;
+ argumentStart = 12;
+ } else {
+ return nullptr;
+ }
+ pos += argumentStart;
+ RefPtrWillBeRawPtr<CSSTransformValue> transformValue = CSSTransformValue::create(transformType);
+ if (!parseTransformTranslateArguments(pos, end, expectedArgumentCount, transformValue.get()))
+ return nullptr;
+ return transformValue.release();
+ }
+
+ const bool isMatrix3d = toASCIILower(pos[0]) == 'm'
+ && toASCIILower(pos[1]) == 'a'
+ && toASCIILower(pos[2]) == 't'
+ && toASCIILower(pos[3]) == 'r'
+ && toASCIILower(pos[4]) == 'i'
+ && toASCIILower(pos[5]) == 'x'
+ && pos[6] == '3'
+ && toASCIILower(pos[7]) == 'd'
+ && pos[8] == '(';
+
+ if (isMatrix3d) {
+ pos += 9;
+ RefPtrWillBeRawPtr<CSSTransformValue> transformValue = CSSTransformValue::create(CSSTransformValue::Matrix3DTransformOperation);
+ if (!parseTransformNumberArguments(pos, end, 16, transformValue.get()))
+ return nullptr;
+ return transformValue.release();
+ }
+
+ const bool isScale3d = toASCIILower(pos[0]) == 's'
+ && toASCIILower(pos[1]) == 'c'
+ && toASCIILower(pos[2]) == 'a'
+ && toASCIILower(pos[3]) == 'l'
+ && toASCIILower(pos[4]) == 'e'
+ && pos[5] == '3'
+ && toASCIILower(pos[6]) == 'd'
+ && pos[7] == '(';
+
+ if (isScale3d) {
+ pos += 8;
+ RefPtrWillBeRawPtr<CSSTransformValue> transformValue = CSSTransformValue::create(CSSTransformValue::Scale3DTransformOperation);
+ if (!parseTransformNumberArguments(pos, end, 3, transformValue.get()))
+ return nullptr;
+ return transformValue.release();
+ }
+
+ return nullptr;
+}
+
+template <typename CharType>
+static PassRefPtrWillBeRawPtr<CSSValueList> parseSimpleTransformList(CharType*& pos, CharType* end)
+{
+ RefPtrWillBeRawPtr<CSSValueList> transformList = nullptr;
+ while (pos < end) {
+ while (pos < end && isCSSSpace(*pos))
+ ++pos;
+ RefPtrWillBeRawPtr<CSSTransformValue> transformValue = parseSimpleTransformValue(pos, end);
+ if (!transformValue)
+ return nullptr;
+ if (!transformList)
+ transformList = CSSValueList::createSpaceSeparated();
+ transformList->append(transformValue.release());
+ if (pos < end) {
+ if (isCSSSpace(*pos))
+ return nullptr;
+ }
+ }
+ return transformList.release();
+}
+
+static bool parseSimpleTransform(MutableStylePropertySet* properties, CSSPropertyID propertyID, const String& string, bool important)
+{
+ if (propertyID != CSSPropertyTransform && propertyID != CSSPropertyWebkitTransform)
+ return false;
+ if (string.isEmpty())
+ return false;
+ RefPtrWillBeRawPtr<CSSValueList> transformList = nullptr;
+ if (string.is8Bit()) {
+ const LChar* pos = string.characters8();
+ const LChar* end = pos + string.length();
+ transformList = parseSimpleTransformList(pos, end);
+ if (!transformList)
+ return false;
+ } else {
+ const UChar* pos = string.characters16();
+ const UChar* end = pos + string.length();
+ transformList = parseSimpleTransformList(pos, end);
+ if (!transformList)
+ return false;
+ }
+ properties->addParsedProperty(CSSProperty(propertyID, transformList.release(), important));
+ return true;
+}
+
+PassRefPtrWillBeRawPtr<CSSValueList> BisonCSSParser::parseFontFaceValue(const AtomicString& string)
+{
+ if (string.isEmpty())
+ return nullptr;
+ RefPtrWillBeRawPtr<MutableStylePropertySet> dummyStyle = MutableStylePropertySet::create();
+ if (!parseValue(dummyStyle.get(), CSSPropertyFontFamily, string, false, HTMLQuirksMode, 0))
+ return nullptr;
+
+ RefPtrWillBeRawPtr<CSSValue> fontFamily = dummyStyle->getPropertyCSSValue(CSSPropertyFontFamily);
+ if (!fontFamily->isValueList())
+ return nullptr;
+
+ return toCSSValueList(dummyStyle->getPropertyCSSValue(CSSPropertyFontFamily).get());
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> BisonCSSParser::parseAnimationTimingFunctionValue(const String& string)
+{
+ if (string.isEmpty())
+ return nullptr;
+ RefPtrWillBeRawPtr<MutableStylePropertySet> style = MutableStylePropertySet::create();
+ if (!parseValue(style.get(), CSSPropertyTransitionTimingFunction, string, false, HTMLStandardMode, 0))
+ return nullptr;
+
+ RefPtrWillBeRawPtr<CSSValue> value = style->getPropertyCSSValue(CSSPropertyTransitionTimingFunction);
+ if (!value || value->isInitialValue() || value->isInheritedValue())
+ return nullptr;
+ CSSValueList* valueList = toCSSValueList(value.get());
+ if (valueList->length() > 1)
+ return nullptr;
+ return valueList->item(0);
+}
+
+bool BisonCSSParser::parseValue(MutableStylePropertySet* declaration, CSSPropertyID propertyID, const String& string, bool important, const Document& document)
+{
+ ASSERT(!string.isEmpty());
+
+ CSSParserContext context(document, UseCounter::getFrom(&document));
+
+ if (parseSimpleLengthValue(declaration, propertyID, string, important, context.mode()))
+ return true;
+ if (parseColorValue(declaration, propertyID, string, important, context.mode()))
+ return true;
+ if (parseKeywordValue(declaration, propertyID, string, important, context))
+ return true;
+
+ BisonCSSParser parser(context);
+ return parser.parseValue(declaration, propertyID, string, important, static_cast<StyleSheetContents*>(0));
+}
+
+bool BisonCSSParser::parseValue(MutableStylePropertySet* declaration, CSSPropertyID propertyID, const String& string, bool important, CSSParserMode cssParserMode, StyleSheetContents* contextStyleSheet)
+{
+ ASSERT(!string.isEmpty());
+ if (parseSimpleLengthValue(declaration, propertyID, string, important, cssParserMode))
+ return true;
+ if (parseColorValue(declaration, propertyID, string, important, cssParserMode))
+ return true;
+
+ CSSParserContext context(cssParserMode, 0);
+ if (contextStyleSheet) {
+ context = contextStyleSheet->parserContext();
+ context.setMode(cssParserMode);
+ }
+
+ if (parseKeywordValue(declaration, propertyID, string, important, context))
+ return true;
+ if (parseSimpleTransform(declaration, propertyID, string, important))
+ return true;
+
+ BisonCSSParser parser(context);
+ return parser.parseValue(declaration, propertyID, string, important, contextStyleSheet);
+}
+
+bool BisonCSSParser::parseValue(MutableStylePropertySet* declaration, CSSPropertyID propertyID, const String& string, bool important, StyleSheetContents* contextStyleSheet)
+{
+ // FIXME: Check RuntimeCSSEnabled::isPropertyEnabled or isValueEnabledForProperty.
+
+ if (m_context.useCounter())
+ m_context.useCounter()->count(m_context, propertyID);
+
+ setStyleSheet(contextStyleSheet);
+
+ setupParser("@-internal-value ", string, "");
+
+ m_id = propertyID;
+ m_important = important;
+
+ {
+ StyleDeclarationScope scope(this, declaration);
+ cssyyparse(this);
+ }
+
+ m_rule = nullptr;
+ m_id = CSSPropertyInvalid;
+
+ bool ok = false;
+ if (!m_parsedProperties.isEmpty()) {
+ ok = true;
+ declaration->addParsedProperties(m_parsedProperties);
+ clearProperties();
+ }
+
+ return ok;
+}
+
+// The color will only be changed when string contains a valid CSS color, so callers
+// can set it to a default color and ignore the boolean result.
+bool BisonCSSParser::parseColor(RGBA32& color, const String& string, bool strict)
+{
+ // First try creating a color specified by name, rgba(), rgb() or "#" syntax.
+ if (CSSPropertyParser::fastParseColor(color, string, strict))
+ return true;
+
+ BisonCSSParser parser(strictCSSParserContext());
+
+ // In case the fast-path parser didn't understand the color, try the full parser.
+ if (!parser.parseColor(string))
+ return false;
+
+ CSSValue* value = parser.m_parsedProperties.first().value();
+ if (!value->isPrimitiveValue())
+ return false;
+
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (!primitiveValue->isRGBColor())
+ return false;
+
+ color = primitiveValue->getRGBA32Value();
+ return true;
+}
+
+bool BisonCSSParser::parseColor(const String& string)
+{
+ setupParser("@-internal-decls color:", string, "");
+ cssyyparse(this);
+ m_rule = nullptr;
+
+ return !m_parsedProperties.isEmpty() && m_parsedProperties.first().id() == CSSPropertyColor;
+}
+
+bool BisonCSSParser::parseSystemColor(RGBA32& color, const String& string)
+{
+ CSSParserString cssColor;
+ cssColor.init(string);
+ CSSValueID id = cssValueKeywordID(cssColor);
+ if (!CSSPropertyParser::isSystemColor(id))
+ return false;
+
+ Color parsedColor = RenderTheme::theme().systemColor(id);
+ color = parsedColor.rgb();
+ return true;
+}
+
+void BisonCSSParser::parseSelector(const String& string, CSSSelectorList& selectorList)
+{
+ m_selectorListForParseSelector = &selectorList;
+
+ setupParser("@-internal-selector ", string, "");
+
+ cssyyparse(this);
+
+ m_selectorListForParseSelector = 0;
+}
+
+PassRefPtr<ImmutableStylePropertySet> BisonCSSParser::parseInlineStyleDeclaration(const String& string, Element* element)
+{
+ Document& document = element->document();
+ CSSParserContext context = CSSParserContext(document.elementSheet().contents()->parserContext(), UseCounter::getFrom(&document));
+ context.setMode((element->isHTMLElement() && !document.inQuirksMode()) ? HTMLStandardMode : HTMLQuirksMode);
+ return BisonCSSParser(context).parseDeclaration(string, document.elementSheet().contents());
+}
+
+PassRefPtr<ImmutableStylePropertySet> BisonCSSParser::parseDeclaration(const String& string, StyleSheetContents* contextStyleSheet)
+{
+ setStyleSheet(contextStyleSheet);
+
+ setupParser("@-internal-decls ", string, "");
+ cssyyparse(this);
+ m_rule = nullptr;
+
+ RefPtr<ImmutableStylePropertySet> style = createStylePropertySet();
+ clearProperties();
+ return style.release();
+}
+
+
+bool BisonCSSParser::parseDeclaration(MutableStylePropertySet* declaration, const String& string, CSSParserObserver* observer, StyleSheetContents* contextStyleSheet)
+{
+ setStyleSheet(contextStyleSheet);
+
+ TemporaryChange<CSSParserObserver*> scopedObsever(m_observer, observer);
+
+ setupParser("@-internal-decls ", string, "");
+ if (m_observer) {
+ m_observer->startRuleHeader(CSSRuleSourceData::STYLE_RULE, 0);
+ m_observer->endRuleHeader(1);
+ m_observer->startRuleBody(0);
+ }
+
+ {
+ StyleDeclarationScope scope(this, declaration);
+ cssyyparse(this);
+ }
+
+ m_rule = nullptr;
+
+ bool ok = false;
+ if (!m_parsedProperties.isEmpty()) {
+ ok = true;
+ declaration->addParsedProperties(m_parsedProperties);
+ clearProperties();
+ }
+
+ if (m_observer)
+ m_observer->endRuleBody(string.length(), false);
+
+ return ok;
+}
+
+PassRefPtrWillBeRawPtr<MediaQuerySet> BisonCSSParser::parseMediaQueryList(const String& string)
+{
+ ASSERT(!m_mediaList);
+
+ // can't use { because tokenizer state switches from mediaquery to initial state when it sees { token.
+ // instead insert one " " (which is caught by maybe_space in CSSGrammar.y)
+ setupParser("@-internal-medialist ", string, "");
+ cssyyparse(this);
+
+ ASSERT(m_mediaList);
+ return m_mediaList.release();
+}
+
+static inline void filterProperties(bool important, const WillBeHeapVector<CSSProperty, 256>& input, WillBeHeapVector<CSSProperty, 256>& output, size_t& unusedEntries, BitArray<numCSSProperties>& seenProperties)
+{
+ // Add properties in reverse order so that highest priority definitions are reached first. Duplicate definitions can then be ignored when found.
+ for (int i = input.size() - 1; i >= 0; --i) {
+ const CSSProperty& property = input[i];
+ if (property.isImportant() != important)
+ continue;
+ const unsigned propertyIDIndex = property.id() - firstCSSProperty;
+ if (seenProperties.get(propertyIDIndex))
+ continue;
+ seenProperties.set(propertyIDIndex);
+ output[--unusedEntries] = property;
+ }
+}
+
+PassRefPtr<ImmutableStylePropertySet> BisonCSSParser::createStylePropertySet()
+{
+ BitArray<numCSSProperties> seenProperties;
+ size_t unusedEntries = m_parsedProperties.size();
+ WillBeHeapVector<CSSProperty, 256> results(unusedEntries);
+
+ // Important properties have higher priority, so add them first. Duplicate definitions can then be ignored when found.
+ filterProperties(true, m_parsedProperties, results, unusedEntries, seenProperties);
+ filterProperties(false, m_parsedProperties, results, unusedEntries, seenProperties);
+ if (unusedEntries)
+ results.remove(0, unusedEntries);
+
+ CSSParserMode mode = inViewport() ? CSSViewportRuleMode : m_context.mode();
+
+ return ImmutableStylePropertySet::create(results.data(), results.size(), mode);
+}
+
+void BisonCSSParser::rollbackLastProperties(int num)
+{
+ ASSERT(num >= 0);
+ ASSERT(m_parsedProperties.size() >= static_cast<unsigned>(num));
+ m_parsedProperties.shrink(m_parsedProperties.size() - num);
+}
+
+void BisonCSSParser::clearProperties()
+{
+ m_parsedProperties.clear();
+ m_numParsedPropertiesBeforeMarginBox = INVALID_NUM_PARSED_PROPERTIES;
+}
+
+void BisonCSSParser::setCurrentProperty(CSSPropertyID propId)
+{
+ m_id = propId;
+}
+
+bool BisonCSSParser::parseValue(CSSPropertyID propId, bool important)
+{
+ CSSPropertyParser parser(m_valueList, m_context, m_inViewport, m_important, m_parsedProperties, m_ruleHeaderType);
+ return parser.parseValue(propId, important);
+}
+
+
+class TransformOperationInfo {
+public:
+ TransformOperationInfo(const CSSParserString& name)
+ : m_type(CSSTransformValue::UnknownTransformOperation)
+ , m_argCount(1)
+ , m_allowSingleArgument(false)
+ , m_unit(CSSPropertyParser::FUnknown)
+ {
+ const UChar* characters;
+ unsigned nameLength = name.length();
+
+ const unsigned longestNameLength = 12;
+ UChar characterBuffer[longestNameLength];
+ if (name.is8Bit()) {
+ unsigned length = std::min(longestNameLength, nameLength);
+ const LChar* characters8 = name.characters8();
+ for (unsigned i = 0; i < length; ++i)
+ characterBuffer[i] = characters8[i];
+ characters = characterBuffer;
+ } else
+ characters = name.characters16();
+
+ SWITCH(characters, nameLength) {
+ CASE("skew(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::SkewTransformOperation;
+ m_allowSingleArgument = true;
+ m_argCount = 3;
+ }
+ CASE("scale(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::ScaleTransformOperation;
+ m_allowSingleArgument = true;
+ m_argCount = 3;
+ }
+ CASE("skewx(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::SkewXTransformOperation;
+ }
+ CASE("skewy(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::SkewYTransformOperation;
+ }
+ CASE("matrix(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::MatrixTransformOperation;
+ m_argCount = 11;
+ }
+ CASE("rotate(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::RotateTransformOperation;
+ }
+ CASE("scalex(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::ScaleXTransformOperation;
+ }
+ CASE("scaley(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::ScaleYTransformOperation;
+ }
+ CASE("scalez(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::ScaleZTransformOperation;
+ }
+ CASE("scale3d(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::Scale3DTransformOperation;
+ m_argCount = 5;
+ }
+ CASE("rotatex(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::RotateXTransformOperation;
+ }
+ CASE("rotatey(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::RotateYTransformOperation;
+ }
+ CASE("rotatez(") {
+ m_unit = CSSPropertyParser::FAngle;
+ m_type = CSSTransformValue::RotateZTransformOperation;
+ }
+ CASE("matrix3d(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::Matrix3DTransformOperation;
+ m_argCount = 31;
+ }
+ CASE("rotate3d(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::Rotate3DTransformOperation;
+ m_argCount = 7;
+ }
+ CASE("translate(") {
+ m_unit = CSSPropertyParser::FLength | CSSPropertyParser::FPercent;
+ m_type = CSSTransformValue::TranslateTransformOperation;
+ m_allowSingleArgument = true;
+ m_argCount = 3;
+ }
+ CASE("translatex(") {
+ m_unit = CSSPropertyParser::FLength | CSSPropertyParser::FPercent;
+ m_type = CSSTransformValue::TranslateXTransformOperation;
+ }
+ CASE("translatey(") {
+ m_unit = CSSPropertyParser::FLength | CSSPropertyParser::FPercent;
+ m_type = CSSTransformValue::TranslateYTransformOperation;
+ }
+ CASE("translatez(") {
+ m_unit = CSSPropertyParser::FLength | CSSPropertyParser::FPercent;
+ m_type = CSSTransformValue::TranslateZTransformOperation;
+ }
+ CASE("perspective(") {
+ m_unit = CSSPropertyParser::FNumber;
+ m_type = CSSTransformValue::PerspectiveTransformOperation;
+ }
+ CASE("translate3d(") {
+ m_unit = CSSPropertyParser::FLength | CSSPropertyParser::FPercent;
+ m_type = CSSTransformValue::Translate3DTransformOperation;
+ m_argCount = 5;
+ }
+ }
+ }
+
+ CSSTransformValue::TransformOperationType type() const { return m_type; }
+ unsigned argCount() const { return m_argCount; }
+ CSSPropertyParser::Units unit() const { return m_unit; }
+
+ bool unknown() const { return m_type == CSSTransformValue::UnknownTransformOperation; }
+ bool hasCorrectArgCount(unsigned argCount) { return m_argCount == argCount || (m_allowSingleArgument && argCount == 1); }
+
+private:
+ CSSTransformValue::TransformOperationType m_type;
+ unsigned m_argCount;
+ bool m_allowSingleArgument;
+ CSSPropertyParser::Units m_unit;
+};
+
+PassRefPtrWillBeRawPtr<CSSValueList> CSSPropertyParser::parseTransform(CSSPropertyID propId)
+{
+ if (!m_valueList)
+ return nullptr;
+
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
+ RefPtrWillBeRawPtr<CSSValue> parsedTransformValue = parseTransformValue(propId, value);
+ if (!parsedTransformValue)
+ return nullptr;
+
+ list->append(parsedTransformValue.release());
+ }
+
+ return list.release();
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseTransformValue(CSSPropertyID propId, CSSParserValue *value)
+{
+ if (value->unit != CSSParserValue::Function || !value->function)
+ return nullptr;
+
+ // Every primitive requires at least one argument.
+ CSSParserValueList* args = value->function->args.get();
+ if (!args)
+ return nullptr;
+
+ // See if the specified primitive is one we understand.
+ TransformOperationInfo info(value->function->name);
+ if (info.unknown())
+ return nullptr;
+
+ if (!info.hasCorrectArgCount(args->size()))
+ return nullptr;
+
+ // The transform is a list of functional primitives that specify transform operations.
+ // We collect a list of CSSTransformValues, where each value specifies a single operation.
+
+ // Create the new CSSTransformValue for this operation and add it to our list.
+ RefPtrWillBeRawPtr<CSSTransformValue> transformValue = CSSTransformValue::create(info.type());
+
+ // Snag our values.
+ CSSParserValue* a = args->current();
+ unsigned argNumber = 0;
+ while (a) {
+ CSSPropertyParser::Units unit = info.unit();
+
+ if (info.type() == CSSTransformValue::Rotate3DTransformOperation && argNumber == 3) {
+ // 4th param of rotate3d() is an angle rather than a bare number, validate it as such
+ if (!validUnit(a, FAngle, HTMLStandardMode))
+ return nullptr;
+ } else if (info.type() == CSSTransformValue::Translate3DTransformOperation && argNumber == 2) {
+ // 3rd param of translate3d() cannot be a percentage
+ if (!validUnit(a, FLength, HTMLStandardMode))
+ return nullptr;
+ } else if (info.type() == CSSTransformValue::TranslateZTransformOperation && !argNumber) {
+ // 1st param of translateZ() cannot be a percentage
+ if (!validUnit(a, FLength, HTMLStandardMode))
+ return nullptr;
+ } else if (info.type() == CSSTransformValue::PerspectiveTransformOperation && !argNumber) {
+ // 1st param of perspective() must be a non-negative number (deprecated) or length.
+ if ((propId == CSSPropertyWebkitTransform && !validUnit(a, FNumber | FLength | FNonNeg, HTMLStandardMode))
+ || (propId == CSSPropertyTransform && !validUnit(a, FLength | FNonNeg, HTMLStandardMode)))
+ return nullptr;
+ } else if (!validUnit(a, unit, HTMLStandardMode)) {
+ return nullptr;
+ }
+
+ // Add the value to the current transform operation.
+ transformValue->append(createPrimitiveNumericValue(a));
+
+ a = args->next();
+ if (!a)
+ break;
+ if (a->unit != CSSParserValue::Operator || a->iValue != ',')
+ return nullptr;
+ a = args->next();
+
+ argNumber++;
+ }
+
+ return transformValue.release();
+}
+
+void BisonCSSParser::ensureLineEndings()
+{
+ if (!m_lineEndings)
+ m_lineEndings = lineEndings(*m_source);
+}
+
+CSSParserSelector* BisonCSSParser::createFloatingSelectorWithTagName(const QualifiedName& tagQName)
+{
+ CSSParserSelector* selector = new CSSParserSelector(tagQName);
+ m_floatingSelectors.append(selector);
+ return selector;
+}
+
+CSSParserSelector* BisonCSSParser::createFloatingSelector()
+{
+ CSSParserSelector* selector = new CSSParserSelector;
+ m_floatingSelectors.append(selector);
+ return selector;
+}
+
+PassOwnPtr<CSSParserSelector> BisonCSSParser::sinkFloatingSelector(CSSParserSelector* selector)
+{
+ if (selector) {
+ size_t index = m_floatingSelectors.reverseFind(selector);
+ ASSERT(index != kNotFound);
+ m_floatingSelectors.remove(index);
+ }
+ return adoptPtr(selector);
+}
+
+Vector<OwnPtr<CSSParserSelector> >* BisonCSSParser::createFloatingSelectorVector()
+{
+ Vector<OwnPtr<CSSParserSelector> >* selectorVector = new Vector<OwnPtr<CSSParserSelector> >;
+ m_floatingSelectorVectors.append(selectorVector);
+ return selectorVector;
+}
+
+PassOwnPtr<Vector<OwnPtr<CSSParserSelector> > > BisonCSSParser::sinkFloatingSelectorVector(Vector<OwnPtr<CSSParserSelector> >* selectorVector)
+{
+ if (selectorVector) {
+ size_t index = m_floatingSelectorVectors.reverseFind(selectorVector);
+ ASSERT(index != kNotFound);
+ m_floatingSelectorVectors.remove(index);
+ }
+ return adoptPtr(selectorVector);
+}
+
+CSSParserValueList* BisonCSSParser::createFloatingValueList()
+{
+ CSSParserValueList* list = new CSSParserValueList;
+ m_floatingValueLists.append(list);
+ return list;
+}
+
+PassOwnPtr<CSSParserValueList> BisonCSSParser::sinkFloatingValueList(CSSParserValueList* list)
+{
+ if (list) {
+ size_t index = m_floatingValueLists.reverseFind(list);
+ ASSERT(index != kNotFound);
+ m_floatingValueLists.remove(index);
+ }
+ return adoptPtr(list);
+}
+
+CSSParserFunction* BisonCSSParser::createFloatingFunction()
+{
+ CSSParserFunction* function = new CSSParserFunction;
+ m_floatingFunctions.append(function);
+ return function;
+}
+
+CSSParserFunction* BisonCSSParser::createFloatingFunction(const CSSParserString& name, PassOwnPtr<CSSParserValueList> args)
+{
+ CSSParserFunction* function = createFloatingFunction();
+ function->name = name;
+ function->args = args;
+ return function;
+}
+
+PassOwnPtr<CSSParserFunction> BisonCSSParser::sinkFloatingFunction(CSSParserFunction* function)
+{
+ if (function) {
+ size_t index = m_floatingFunctions.reverseFind(function);
+ ASSERT(index != kNotFound);
+ m_floatingFunctions.remove(index);
+ }
+ return adoptPtr(function);
+}
+
+CSSParserValue& BisonCSSParser::sinkFloatingValue(CSSParserValue& value)
+{
+ if (value.unit == CSSParserValue::Function) {
+ size_t index = m_floatingFunctions.reverseFind(value.function);
+ ASSERT(index != kNotFound);
+ m_floatingFunctions.remove(index);
+ }
+ return value;
+}
+
+MediaQueryExp* BisonCSSParser::createFloatingMediaQueryExp(const AtomicString& mediaFeature, CSSParserValueList* values)
+{
+ m_floatingMediaQueryExp = MediaQueryExp::createIfValid(mediaFeature, values);
+ return m_floatingMediaQueryExp.get();
+}
+
+PassOwnPtrWillBeRawPtr<MediaQueryExp> BisonCSSParser::sinkFloatingMediaQueryExp(MediaQueryExp* expression)
+{
+ ASSERT_UNUSED(expression, expression == m_floatingMediaQueryExp);
+ return m_floatingMediaQueryExp.release();
+}
+
+WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> >* BisonCSSParser::createFloatingMediaQueryExpList()
+{
+ m_floatingMediaQueryExpList = adoptPtrWillBeNoop(new WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> >);
+ return m_floatingMediaQueryExpList.get();
+}
+
+PassOwnPtrWillBeRawPtr<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > > BisonCSSParser::sinkFloatingMediaQueryExpList(WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> >* list)
+{
+ ASSERT_UNUSED(list, list == m_floatingMediaQueryExpList);
+ return m_floatingMediaQueryExpList.release();
+}
+
+MediaQuery* BisonCSSParser::createFloatingMediaQuery(MediaQuery::Restrictor restrictor, const AtomicString& mediaType, PassOwnPtrWillBeRawPtr<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > > expressions)
+{
+ m_floatingMediaQuery = adoptPtrWillBeNoop(new MediaQuery(restrictor, mediaType, expressions));
+ return m_floatingMediaQuery.get();
+}
+
+MediaQuery* BisonCSSParser::createFloatingMediaQuery(PassOwnPtrWillBeRawPtr<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > > expressions)
+{
+ return createFloatingMediaQuery(MediaQuery::None, AtomicString("all", AtomicString::ConstructFromLiteral), expressions);
+}
+
+MediaQuery* BisonCSSParser::createFloatingNotAllQuery()
+{
+ return createFloatingMediaQuery(MediaQuery::Not, AtomicString("all", AtomicString::ConstructFromLiteral), sinkFloatingMediaQueryExpList(createFloatingMediaQueryExpList()));
+}
+
+PassOwnPtrWillBeRawPtr<MediaQuery> BisonCSSParser::sinkFloatingMediaQuery(MediaQuery* query)
+{
+ ASSERT_UNUSED(query, query == m_floatingMediaQuery);
+ return m_floatingMediaQuery.release();
+}
+
+WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >* BisonCSSParser::createFloatingKeyframeVector()
+{
+ m_floatingKeyframeVector = adoptPtrWillBeNoop(new WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >());
+ return m_floatingKeyframeVector.get();
+}
+
+PassOwnPtrWillBeRawPtr<WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > > BisonCSSParser::sinkFloatingKeyframeVector(WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >* keyframeVector)
+{
+ ASSERT_UNUSED(keyframeVector, m_floatingKeyframeVector == keyframeVector);
+ return m_floatingKeyframeVector.release();
+}
+
+MediaQuerySet* BisonCSSParser::createMediaQuerySet()
+{
+ RefPtrWillBeRawPtr<MediaQuerySet> queries = MediaQuerySet::create();
+ MediaQuerySet* result = queries.get();
+ m_parsedMediaQuerySets.append(queries.release());
+ return result;
+}
+
+StyleRuleBase* BisonCSSParser::createImportRule(const CSSParserString& url, MediaQuerySet* media)
+{
+ if (!media || !m_allowImportRules)
+ return 0;
+ RefPtrWillBeRawPtr<StyleRuleImport> rule = StyleRuleImport::create(url, media);
+ StyleRuleImport* result = rule.get();
+ m_parsedRules.append(rule.release());
+ return result;
+}
+
+StyleRuleBase* BisonCSSParser::createMediaRule(MediaQuerySet* media, RuleList* rules)
+{
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+ RefPtrWillBeRawPtr<StyleRuleMedia> rule = nullptr;
+ if (rules) {
+ rule = StyleRuleMedia::create(media ? media : MediaQuerySet::create().get(), *rules);
+ } else {
+ RuleList emptyRules;
+ rule = StyleRuleMedia::create(media ? media : MediaQuerySet::create().get(), emptyRules);
+ }
+ StyleRuleMedia* result = rule.get();
+ m_parsedRules.append(rule.release());
+ return result;
+}
+
+StyleRuleBase* BisonCSSParser::createSupportsRule(bool conditionIsSupported, RuleList* rules)
+{
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+
+ RefPtrWillBeRawPtr<CSSRuleSourceData> data = popSupportsRuleData();
+ RefPtrWillBeRawPtr<StyleRuleSupports> rule = nullptr;
+ String conditionText;
+ unsigned conditionOffset = data->ruleHeaderRange.start + 9;
+ unsigned conditionLength = data->ruleHeaderRange.length() - 9;
+
+ if (m_tokenizer.is8BitSource())
+ conditionText = String(m_tokenizer.m_dataStart8.get() + conditionOffset, conditionLength).stripWhiteSpace();
+ else
+ conditionText = String(m_tokenizer.m_dataStart16.get() + conditionOffset, conditionLength).stripWhiteSpace();
+
+ if (rules) {
+ rule = StyleRuleSupports::create(conditionText, conditionIsSupported, *rules);
+ } else {
+ RuleList emptyRules;
+ rule = StyleRuleSupports::create(conditionText, conditionIsSupported, emptyRules);
+ }
+
+ StyleRuleSupports* result = rule.get();
+ m_parsedRules.append(rule.release());
+
+ return result;
+}
+
+void BisonCSSParser::markSupportsRuleHeaderStart()
+{
+ if (!m_supportsRuleDataStack)
+ m_supportsRuleDataStack = adoptPtrWillBeNoop(new RuleSourceDataList());
+
+ RefPtrWillBeRawPtr<CSSRuleSourceData> data = CSSRuleSourceData::create(CSSRuleSourceData::SUPPORTS_RULE);
+ data->ruleHeaderRange.start = m_tokenizer.tokenStartOffset();
+ m_supportsRuleDataStack->append(data);
+}
+
+void BisonCSSParser::markSupportsRuleHeaderEnd()
+{
+ ASSERT(m_supportsRuleDataStack && !m_supportsRuleDataStack->isEmpty());
+
+ if (m_tokenizer.is8BitSource())
+ m_supportsRuleDataStack->last()->ruleHeaderRange.end = m_tokenizer.tokenStart<LChar>() - m_tokenizer.m_dataStart8.get();
+ else
+ m_supportsRuleDataStack->last()->ruleHeaderRange.end = m_tokenizer.tokenStart<UChar>() - m_tokenizer.m_dataStart16.get();
+}
+
+PassRefPtrWillBeRawPtr<CSSRuleSourceData> BisonCSSParser::popSupportsRuleData()
+{
+ ASSERT(m_supportsRuleDataStack && !m_supportsRuleDataStack->isEmpty());
+ RefPtrWillBeRawPtr<CSSRuleSourceData> data = m_supportsRuleDataStack->last();
+ m_supportsRuleDataStack->removeLast();
+ return data.release();
+}
+
+BisonCSSParser::RuleList* BisonCSSParser::createRuleList()
+{
+ OwnPtrWillBeRawPtr<RuleList> list = adoptPtrWillBeNoop(new RuleList);
+ RuleList* listPtr = list.get();
+
+ m_parsedRuleLists.append(list.release());
+ return listPtr;
+}
+
+BisonCSSParser::RuleList* BisonCSSParser::appendRule(RuleList* ruleList, StyleRuleBase* rule)
+{
+ if (rule) {
+ if (!ruleList)
+ ruleList = createRuleList();
+ ruleList->append(rule);
+ }
+ return ruleList;
+}
+
+template <typename CharacterType>
+ALWAYS_INLINE static void makeLower(const CharacterType* input, CharacterType* output, unsigned length)
+{
+ // FIXME: If we need Unicode lowercasing here, then we probably want the real kind
+ // that can potentially change the length of the string rather than the character
+ // by character kind. If we don't need Unicode lowercasing, it would be good to
+ // simplify this function.
+
+ if (charactersAreAllASCII(input, length)) {
+ // Fast case for all-ASCII.
+ for (unsigned i = 0; i < length; i++)
+ output[i] = toASCIILower(input[i]);
+ } else {
+ for (unsigned i = 0; i < length; i++)
+ output[i] = Unicode::toLower(input[i]);
+ }
+}
+
+void BisonCSSParser::tokenToLowerCase(CSSParserString& token)
+{
+ // Since it's our internal token, we know that we created it out
+ // of our writable work buffers. Therefore the const_cast is just
+ // ugly and not a potential crash.
+ size_t length = token.length();
+ if (token.is8Bit()) {
+ makeLower(token.characters8(), const_cast<LChar*>(token.characters8()), length);
+ } else {
+ makeLower(token.characters16(), const_cast<UChar*>(token.characters16()), length);
+ }
+}
+
+void BisonCSSParser::endInvalidRuleHeader()
+{
+ if (m_ruleHeaderType == CSSRuleSourceData::UNKNOWN_RULE)
+ return;
+
+ CSSParserLocation location;
+ location.lineNumber = m_tokenizer.m_lineNumber;
+ location.offset = m_ruleHeaderStartOffset;
+ if (m_tokenizer.is8BitSource())
+ location.token.init(m_tokenizer.m_dataStart8.get() + m_ruleHeaderStartOffset, 0);
+ else
+ location.token.init(m_tokenizer.m_dataStart16.get() + m_ruleHeaderStartOffset, 0);
+
+ reportError(location, m_ruleHeaderType == CSSRuleSourceData::STYLE_RULE ? InvalidSelectorCSSError : InvalidRuleCSSError);
+
+ endRuleHeader();
+}
+
+void BisonCSSParser::reportError(const CSSParserLocation&, CSSParserError)
+{
+ // FIXME: error reporting temporatily disabled.
+}
+
+bool BisonCSSParser::isLoggingErrors()
+{
+ return m_logErrors && !m_ignoreErrors;
+}
+
+void BisonCSSParser::logError(const String& message, const CSSParserLocation& location)
+{
+ unsigned lineNumberInStyleSheet;
+ unsigned columnNumber = 0;
+ if (InspectorInstrumentation::hasFrontends()) {
+ ensureLineEndings();
+ TextPosition tokenPosition = TextPosition::fromOffsetAndLineEndings(location.offset, *m_lineEndings);
+ lineNumberInStyleSheet = tokenPosition.m_line.zeroBasedInt();
+ columnNumber = (lineNumberInStyleSheet ? 0 : m_startPosition.m_column.zeroBasedInt()) + tokenPosition.m_column.zeroBasedInt();
+ } else {
+ lineNumberInStyleSheet = location.lineNumber;
+ }
+ FrameConsole& console = m_styleSheet->singleOwnerDocument()->frame()->console();
+ console.addMessage(CSSMessageSource, WarningMessageLevel, message, m_styleSheet->baseURL().string(), lineNumberInStyleSheet + m_startPosition.m_line.zeroBasedInt() + 1, columnNumber + 1);
+}
+
+StyleRuleKeyframes* BisonCSSParser::createKeyframesRule(const String& name, PassOwnPtrWillBeRawPtr<WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > > popKeyframes, bool isPrefixed)
+{
+ OwnPtrWillBeRawPtr<WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > > keyframes = popKeyframes;
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+ RefPtrWillBeRawPtr<StyleRuleKeyframes> rule = StyleRuleKeyframes::create();
+ for (size_t i = 0; i < keyframes->size(); ++i)
+ rule->parserAppendKeyframe(keyframes->at(i));
+ rule->setName(name);
+ rule->setVendorPrefixed(isPrefixed);
+ StyleRuleKeyframes* rulePtr = rule.get();
+ m_parsedRules.append(rule.release());
+ return rulePtr;
+}
+
+static void recordSelectorStats(const CSSParserContext& context, const CSSSelectorList& selectorList)
+{
+ if (!context.useCounter())
+ return;
+
+ for (const CSSSelector* selector = selectorList.first(); selector; selector = CSSSelectorList::next(*selector)) {
+ for (const CSSSelector* current = selector; current ; current = current->tagHistory()) {
+ UseCounter::Feature feature = UseCounter::NumberOfFeatures;
+ switch (current->pseudoType()) {
+ case CSSSelector::PseudoUnresolved:
+ feature = UseCounter::CSSSelectorPseudoUnresolved;
+ break;
+ case CSSSelector::PseudoShadow:
+ feature = UseCounter::CSSSelectorPseudoShadow;
+ break;
+ case CSSSelector::PseudoContent:
+ feature = UseCounter::CSSSelectorPseudoContent;
+ break;
+ case CSSSelector::PseudoHost:
+ feature = UseCounter::CSSSelectorPseudoHost;
+ break;
+ case CSSSelector::PseudoHostContext:
+ feature = UseCounter::CSSSelectorPseudoHostContext;
+ break;
+ default:
+ break;
+ }
+ if (feature != UseCounter::NumberOfFeatures)
+ context.useCounter()->count(feature);
+ if (current->relation() == CSSSelector::ShadowDeep)
+ context.useCounter()->count(UseCounter::CSSDeepCombinator);
+ if (current->selectorList())
+ recordSelectorStats(context, *current->selectorList());
+ }
+ }
+}
+
+StyleRuleBase* BisonCSSParser::createStyleRule(Vector<OwnPtr<CSSParserSelector> >* selectors)
+{
+ StyleRule* result = 0;
+ if (selectors) {
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+ RefPtrWillBeRawPtr<StyleRule> rule = StyleRule::create();
+ rule->parserAdoptSelectorVector(*selectors);
+ rule->setProperties(createStylePropertySet());
+ result = rule.get();
+ m_parsedRules.append(rule.release());
+ recordSelectorStats(m_context, result->selectorList());
+ }
+ clearProperties();
+ return result;
+}
+
+StyleRuleBase* BisonCSSParser::createFontFaceRule()
+{
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+ for (unsigned i = 0; i < m_parsedProperties.size(); ++i) {
+ CSSProperty& property = m_parsedProperties[i];
+ if (property.id() == CSSPropertyFontVariant && property.value()->isPrimitiveValue())
+ property.wrapValueInCommaSeparatedList();
+ else if (property.id() == CSSPropertyFontFamily && (!property.value()->isValueList() || toCSSValueList(property.value())->length() != 1)) {
+ // Unlike font-family property, font-family descriptor in @font-face rule
+ // has to be a value list with exactly one family name. It cannot have a
+ // have 'initial' value and cannot 'inherit' from parent.
+ // See http://dev.w3.org/csswg/css3-fonts/#font-family-desc
+ clearProperties();
+ return 0;
+ }
+ }
+ RefPtrWillBeRawPtr<StyleRuleFontFace> rule = StyleRuleFontFace::create();
+ rule->setProperties(createStylePropertySet());
+ clearProperties();
+ StyleRuleFontFace* result = rule.get();
+ m_parsedRules.append(rule.release());
+ if (m_styleSheet)
+ m_styleSheet->setHasFontFaceRule(true);
+ return result;
+}
+
+void BisonCSSParser::addNamespace(const AtomicString& prefix, const AtomicString& uri)
+{
+ if (!m_styleSheet || !m_allowNamespaceDeclarations)
+ return;
+ m_allowImportRules = false;
+ m_styleSheet->parserAddNamespace(prefix, uri);
+ if (prefix.isEmpty() && !uri.isNull())
+ m_defaultNamespace = uri;
+}
+
+QualifiedName BisonCSSParser::determineNameInNamespace(const AtomicString& prefix, const AtomicString& localName)
+{
+ if (!m_styleSheet)
+ return QualifiedName(prefix, localName, m_defaultNamespace);
+ return QualifiedName(prefix, localName, m_styleSheet->determineNamespace(prefix));
+}
+
+CSSParserSelector* BisonCSSParser::rewriteSpecifiersWithNamespaceIfNeeded(CSSParserSelector* specifiers)
+{
+ if (m_defaultNamespace != starAtom || specifiers->crossesTreeScopes())
+ return rewriteSpecifiersWithElementName(nullAtom, starAtom, specifiers, /*tagIsForNamespaceRule*/true);
+ return specifiers;
+}
+
+CSSParserSelector* BisonCSSParser::rewriteSpecifiersWithElementName(const AtomicString& namespacePrefix, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule)
+{
+ AtomicString determinedNamespace = namespacePrefix != nullAtom && m_styleSheet ? m_styleSheet->determineNamespace(namespacePrefix) : m_defaultNamespace;
+ QualifiedName tag(namespacePrefix, elementName, determinedNamespace);
+
+ if (specifiers->crossesTreeScopes())
+ return rewriteSpecifiersWithElementNameForCustomPseudoElement(tag, elementName, specifiers, tagIsForNamespaceRule);
+
+ if (specifiers->isContentPseudoElement())
+ return rewriteSpecifiersWithElementNameForContentPseudoElement(tag, elementName, specifiers, tagIsForNamespaceRule);
+
+ // *:host never matches, so we can't discard the * otherwise we can't tell the
+ // difference between *:host and just :host.
+ if (tag == anyQName() && !specifiers->hasHostPseudoSelector())
+ return specifiers;
+ if (specifiers->pseudoType() != CSSSelector::PseudoCue)
+ specifiers->prependTagSelector(tag, tagIsForNamespaceRule);
+ return specifiers;
+}
+
+CSSParserSelector* BisonCSSParser::rewriteSpecifiersWithElementNameForCustomPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule)
+{
+ if (m_context.useCounter() && specifiers->pseudoType() == CSSSelector::PseudoUserAgentCustomElement)
+ m_context.useCounter()->count(UseCounter::CSSPseudoElementUserAgentCustomPseudo);
+
+ CSSParserSelector* lastShadowPseudo = specifiers;
+ CSSParserSelector* history = specifiers;
+ while (history->tagHistory()) {
+ history = history->tagHistory();
+ if (history->crossesTreeScopes() || history->hasShadowPseudo())
+ lastShadowPseudo = history;
+ }
+
+ if (lastShadowPseudo->tagHistory()) {
+ if (tag != anyQName())
+ lastShadowPseudo->tagHistory()->prependTagSelector(tag, tagIsForNamespaceRule);
+ return specifiers;
+ }
+
+ // For shadow-ID pseudo-elements to be correctly matched, the ShadowPseudo combinator has to be used.
+ // We therefore create a new Selector with that combinator here in any case, even if matching any (host) element in any namespace (i.e. '*').
+ OwnPtr<CSSParserSelector> elementNameSelector = adoptPtr(new CSSParserSelector(tag));
+ lastShadowPseudo->setTagHistory(elementNameSelector.release());
+ lastShadowPseudo->setRelation(CSSSelector::ShadowPseudo);
+ return specifiers;
+}
+
+CSSParserSelector* BisonCSSParser::rewriteSpecifiersWithElementNameForContentPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule)
+{
+ CSSParserSelector* last = specifiers;
+ CSSParserSelector* history = specifiers;
+ while (history->tagHistory()) {
+ history = history->tagHistory();
+ if (history->isContentPseudoElement() || history->relationIsAffectedByPseudoContent())
+ last = history;
+ }
+
+ if (last->tagHistory()) {
+ if (tag != anyQName())
+ last->tagHistory()->prependTagSelector(tag, tagIsForNamespaceRule);
+ return specifiers;
+ }
+
+ // For shadow-ID pseudo-elements to be correctly matched, the ShadowPseudo combinator has to be used.
+ // We therefore create a new Selector with that combinator here in any case, even if matching any (host) element in any namespace (i.e. '*').
+ OwnPtr<CSSParserSelector> elementNameSelector = adoptPtr(new CSSParserSelector(tag));
+ last->setTagHistory(elementNameSelector.release());
+ last->setRelation(CSSSelector::SubSelector);
+ return specifiers;
+}
+
+CSSParserSelector* BisonCSSParser::rewriteSpecifiers(CSSParserSelector* specifiers, CSSParserSelector* newSpecifier)
+{
+ if (newSpecifier->crossesTreeScopes()) {
+ // Unknown pseudo element always goes at the top of selector chain.
+ newSpecifier->appendTagHistory(CSSSelector::ShadowPseudo, sinkFloatingSelector(specifiers));
+ return newSpecifier;
+ }
+ if (newSpecifier->isContentPseudoElement()) {
+ newSpecifier->appendTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(specifiers));
+ return newSpecifier;
+ }
+ if (specifiers->crossesTreeScopes()) {
+ // Specifiers for unknown pseudo element go right behind it in the chain.
+ specifiers->insertTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(newSpecifier), CSSSelector::ShadowPseudo);
+ return specifiers;
+ }
+ if (specifiers->isContentPseudoElement()) {
+ specifiers->insertTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(newSpecifier), CSSSelector::SubSelector);
+ return specifiers;
+ }
+ specifiers->appendTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(newSpecifier));
+ return specifiers;
+}
+
+StyleRuleBase* BisonCSSParser::createPageRule(PassOwnPtr<CSSParserSelector> pageSelector)
+{
+ // FIXME: Margin at-rules are ignored.
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+ StyleRulePage* pageRule = 0;
+ if (pageSelector) {
+ RefPtrWillBeRawPtr<StyleRulePage> rule = StyleRulePage::create();
+ Vector<OwnPtr<CSSParserSelector> > selectorVector;
+ selectorVector.append(pageSelector);
+ rule->parserAdoptSelectorVector(selectorVector);
+ rule->setProperties(createStylePropertySet());
+ pageRule = rule.get();
+ m_parsedRules.append(rule.release());
+ }
+ clearProperties();
+ return pageRule;
+}
+
+StyleRuleBase* BisonCSSParser::createMarginAtRule(CSSSelector::MarginBoxType /* marginBox */)
+{
+ // FIXME: Implement margin at-rule here, using:
+ // - marginBox: margin box
+ // - m_parsedProperties: properties at [m_numParsedPropertiesBeforeMarginBox, m_parsedProperties.size()] are for this at-rule.
+ // Don't forget to also update the action for page symbol in CSSGrammar.y such that margin at-rule data is cleared if page_selector is invalid.
+
+ endDeclarationsForMarginBox();
+ return 0; // until this method is implemented.
+}
+
+void BisonCSSParser::startDeclarationsForMarginBox()
+{
+ m_numParsedPropertiesBeforeMarginBox = m_parsedProperties.size();
+}
+
+void BisonCSSParser::endDeclarationsForMarginBox()
+{
+ rollbackLastProperties(m_parsedProperties.size() - m_numParsedPropertiesBeforeMarginBox);
+ m_numParsedPropertiesBeforeMarginBox = INVALID_NUM_PARSED_PROPERTIES;
+}
+
+StyleKeyframe* BisonCSSParser::createKeyframe(CSSParserValueList* keys)
+{
+ OwnPtr<Vector<double> > keyVector = StyleKeyframe::createKeyList(keys);
+ if (keyVector->isEmpty())
+ return 0;
+
+ RefPtrWillBeRawPtr<StyleKeyframe> keyframe = StyleKeyframe::create();
+ keyframe->setKeys(keyVector.release());
+ keyframe->setProperties(createStylePropertySet());
+
+ clearProperties();
+
+ StyleKeyframe* keyframePtr = keyframe.get();
+ m_parsedKeyframes.append(keyframe.release());
+ return keyframePtr;
+}
+
+void BisonCSSParser::invalidBlockHit()
+{
+ if (m_styleSheet && !m_hadSyntacticallyValidCSSRule)
+ m_styleSheet->setHasSyntacticallyValidCSSHeader(false);
+}
+
+void BisonCSSParser::startRule()
+{
+ if (!m_observer)
+ return;
+
+ ASSERT(m_ruleHasHeader);
+ m_ruleHasHeader = false;
+}
+
+void BisonCSSParser::endRule(bool valid)
+{
+ if (!m_observer)
+ return;
+
+ if (m_ruleHasHeader)
+ m_observer->endRuleBody(m_tokenizer.safeUserStringTokenOffset(), !valid);
+ m_ruleHasHeader = true;
+}
+
+void BisonCSSParser::startRuleHeader(CSSRuleSourceData::Type ruleType)
+{
+ resumeErrorLogging();
+ m_ruleHeaderType = ruleType;
+ m_ruleHeaderStartOffset = m_tokenizer.safeUserStringTokenOffset();
+ m_ruleHeaderStartLineNumber = m_tokenizer.m_tokenStartLineNumber;
+ if (m_observer) {
+ ASSERT(!m_ruleHasHeader);
+ m_observer->startRuleHeader(ruleType, m_ruleHeaderStartOffset);
+ m_ruleHasHeader = true;
+ }
+}
+
+void BisonCSSParser::endRuleHeader()
+{
+ ASSERT(m_ruleHeaderType != CSSRuleSourceData::UNKNOWN_RULE);
+ m_ruleHeaderType = CSSRuleSourceData::UNKNOWN_RULE;
+ if (m_observer) {
+ ASSERT(m_ruleHasHeader);
+ m_observer->endRuleHeader(m_tokenizer.safeUserStringTokenOffset());
+ }
+}
+
+void BisonCSSParser::startSelector()
+{
+ if (m_observer)
+ m_observer->startSelector(m_tokenizer.safeUserStringTokenOffset());
+}
+
+void BisonCSSParser::endSelector()
+{
+ if (m_observer)
+ m_observer->endSelector(m_tokenizer.safeUserStringTokenOffset());
+}
+
+void BisonCSSParser::startRuleBody()
+{
+ if (m_observer)
+ m_observer->startRuleBody(m_tokenizer.safeUserStringTokenOffset());
+}
+
+void BisonCSSParser::startProperty()
+{
+ resumeErrorLogging();
+ if (m_observer)
+ m_observer->startProperty(m_tokenizer.safeUserStringTokenOffset());
+}
+
+void BisonCSSParser::endProperty(bool isImportantFound, bool isPropertyParsed, CSSParserError errorType)
+{
+ m_id = CSSPropertyInvalid;
+ if (m_observer)
+ m_observer->endProperty(isImportantFound, isPropertyParsed, m_tokenizer.safeUserStringTokenOffset(), errorType);
+}
+
+void BisonCSSParser::startEndUnknownRule()
+{
+ if (m_observer)
+ m_observer->startEndUnknownRule();
+}
+
+StyleRuleBase* BisonCSSParser::createViewportRule()
+{
+ // Allow @viewport rules from UA stylesheets even if the feature is disabled.
+ if (!RuntimeEnabledFeatures::cssViewportEnabled() && !isUASheetBehavior(m_context.mode()))
+ return 0;
+
+ m_allowImportRules = m_allowNamespaceDeclarations = false;
+
+ RefPtrWillBeRawPtr<StyleRuleViewport> rule = StyleRuleViewport::create();
+
+ rule->setProperties(createStylePropertySet());
+ clearProperties();
+
+ StyleRuleViewport* result = rule.get();
+ m_parsedRules.append(rule.release());
+
+ return result;
+}
+
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser.h b/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser.h
new file mode 100644
index 00000000000..e4447416394
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParser.h
@@ -0,0 +1,327 @@
+/*
+ * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
+ * Copyright (C) 2004, 2005, 2006, 2008, 2009, 2010 Apple Inc. All rights reserved.
+ * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
+ * Copyright (C) 2009 - 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef BisonCSSParser_h
+#define BisonCSSParser_h
+
+#include "core/CSSPropertyNames.h"
+#include "core/CSSValueKeywords.h"
+#include "core/css/CSSCalculationValue.h"
+#include "core/css/CSSFilterValue.h"
+#include "core/css/CSSGradientValue.h"
+#include "core/css/CSSParserMode.h"
+#include "core/css/CSSParserValues.h"
+#include "core/css/CSSProperty.h"
+#include "core/css/CSSPropertySourceData.h"
+#include "core/css/CSSSelector.h"
+#include "core/css/CSSTokenizer.h"
+#include "core/css/MediaQuery.h"
+#include "core/css/StylePropertySet.h"
+#include "core/css/parser/CSSParserObserver.h"
+#include "core/css/parser/CSSPropertyParser.h"
+#include "platform/graphics/Color.h"
+#include "wtf/HashSet.h"
+#include "wtf/OwnPtr.h"
+#include "wtf/Vector.h"
+#include "wtf/text/AtomicString.h"
+#include "wtf/text/TextPosition.h"
+
+namespace WebCore {
+
+class AnimationParseContext;
+class CSSArrayFunctionValue;
+class CSSBorderImageSliceValue;
+class CSSPrimitiveValue;
+class CSSSelectorList;
+class CSSValue;
+class CSSValueList;
+class CSSBasicShape;
+class CSSBasicShapeInset;
+class Document;
+class Element;
+class ImmutableStylePropertySet;
+class MediaQueryExp;
+class MediaQuerySet;
+class MutableStylePropertySet;
+class StyleKeyframe;
+class StylePropertyShorthand;
+class StyleRuleBase;
+class StyleRuleKeyframes;
+class StyleKeyframe;
+class StyleSheetContents;
+class UseCounter;
+
+// FIXME: This class is shared with CSSTokenizer so should we rename it to CSSSourceLocation?
+struct CSSParserLocation {
+ unsigned offset;
+ unsigned lineNumber;
+ CSSParserString token;
+};
+
+class BisonCSSParser {
+ STACK_ALLOCATED();
+ friend inline int cssyylex(void*, BisonCSSParser*);
+public:
+ explicit BisonCSSParser(const CSSParserContext&);
+ ~BisonCSSParser();
+
+ void rollbackLastProperties(int num);
+ void setCurrentProperty(CSSPropertyID);
+
+ void parseSheet(StyleSheetContents*, const String&, const TextPosition& startPosition = TextPosition::minimumPosition(), CSSParserObserver* = 0, bool = false);
+ PassRefPtrWillBeRawPtr<StyleRuleBase> parseRule(StyleSheetContents*, const String&);
+ PassRefPtrWillBeRawPtr<StyleKeyframe> parseKeyframeRule(StyleSheetContents*, const String&);
+ bool parseSupportsCondition(const String&);
+ static bool parseValue(MutableStylePropertySet*, CSSPropertyID, const String&, bool important, CSSParserMode, StyleSheetContents*);
+ static bool parseColor(RGBA32& color, const String&, bool strict = false);
+ static bool parseSystemColor(RGBA32& color, const String&);
+ static PassRefPtrWillBeRawPtr<CSSValueList> parseFontFaceValue(const AtomicString&);
+ static PassRefPtrWillBeRawPtr<CSSValue> parseAnimationTimingFunctionValue(const String&);
+ bool parseDeclaration(MutableStylePropertySet*, const String&, CSSParserObserver*, StyleSheetContents* contextStyleSheet);
+ static PassRefPtr<ImmutableStylePropertySet> parseInlineStyleDeclaration(const String&, Element*);
+ PassRefPtrWillBeRawPtr<MediaQuerySet> parseMediaQueryList(const String&);
+ PassOwnPtr<Vector<double> > parseKeyframeKeyList(const String&);
+
+ static bool parseValue(MutableStylePropertySet*, CSSPropertyID, const String&, bool important, const Document&);
+
+ bool parseValue(CSSPropertyID, bool important);
+ void parseSelector(const String&, CSSSelectorList&);
+
+ CSSParserSelector* createFloatingSelector();
+ CSSParserSelector* createFloatingSelectorWithTagName(const QualifiedName&);
+ PassOwnPtr<CSSParserSelector> sinkFloatingSelector(CSSParserSelector*);
+
+ Vector<OwnPtr<CSSParserSelector> >* createFloatingSelectorVector();
+ PassOwnPtr<Vector<OwnPtr<CSSParserSelector> > > sinkFloatingSelectorVector(Vector<OwnPtr<CSSParserSelector> >*);
+
+ CSSParserValueList* createFloatingValueList();
+ PassOwnPtr<CSSParserValueList> sinkFloatingValueList(CSSParserValueList*);
+
+ CSSParserFunction* createFloatingFunction();
+ CSSParserFunction* createFloatingFunction(const CSSParserString& name, PassOwnPtr<CSSParserValueList> args);
+ PassOwnPtr<CSSParserFunction> sinkFloatingFunction(CSSParserFunction*);
+
+ CSSParserValue& sinkFloatingValue(CSSParserValue&);
+
+ MediaQuerySet* createMediaQuerySet();
+ StyleRuleBase* createImportRule(const CSSParserString&, MediaQuerySet*);
+ StyleKeyframe* createKeyframe(CSSParserValueList*);
+ StyleRuleKeyframes* createKeyframesRule(const String&, PassOwnPtrWillBeRawPtr<WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > >, bool isPrefixed);
+
+ typedef WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> > RuleList;
+ StyleRuleBase* createMediaRule(MediaQuerySet*, RuleList*);
+ RuleList* createRuleList();
+ RuleList* appendRule(RuleList*, StyleRuleBase*);
+ StyleRuleBase* createStyleRule(Vector<OwnPtr<CSSParserSelector> >* selectors);
+ StyleRuleBase* createFontFaceRule();
+ StyleRuleBase* createPageRule(PassOwnPtr<CSSParserSelector> pageSelector);
+ StyleRuleBase* createMarginAtRule(CSSSelector::MarginBoxType);
+ StyleRuleBase* createSupportsRule(bool conditionIsSupported, RuleList*);
+ void markSupportsRuleHeaderStart();
+ void markSupportsRuleHeaderEnd();
+ PassRefPtrWillBeRawPtr<CSSRuleSourceData> popSupportsRuleData();
+ StyleRuleBase* createHostRule(RuleList* rules);
+
+ void startDeclarationsForMarginBox();
+ void endDeclarationsForMarginBox();
+
+ MediaQueryExp* createFloatingMediaQueryExp(const AtomicString&, CSSParserValueList*);
+ PassOwnPtrWillBeRawPtr<MediaQueryExp> sinkFloatingMediaQueryExp(MediaQueryExp*);
+ WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> >* createFloatingMediaQueryExpList();
+ PassOwnPtrWillBeRawPtr<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > > sinkFloatingMediaQueryExpList(WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> >*);
+ MediaQuery* createFloatingMediaQuery(MediaQuery::Restrictor, const AtomicString&, PassOwnPtrWillBeRawPtr<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > >);
+ MediaQuery* createFloatingMediaQuery(PassOwnPtrWillBeRawPtr<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > >);
+ MediaQuery* createFloatingNotAllQuery();
+ PassOwnPtrWillBeRawPtr<MediaQuery> sinkFloatingMediaQuery(MediaQuery*);
+
+ WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >* createFloatingKeyframeVector();
+ PassOwnPtrWillBeRawPtr<WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > > sinkFloatingKeyframeVector(WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> >*);
+
+ void addNamespace(const AtomicString& prefix, const AtomicString& uri);
+ QualifiedName determineNameInNamespace(const AtomicString& prefix, const AtomicString& localName);
+
+ CSSParserSelector* rewriteSpecifiersWithElementName(const AtomicString& namespacePrefix, const AtomicString& elementName, CSSParserSelector*, bool isNamespacePlaceholder = false);
+ CSSParserSelector* rewriteSpecifiersWithElementNameForCustomPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule);
+ CSSParserSelector* rewriteSpecifiersWithElementNameForContentPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule);
+ CSSParserSelector* rewriteSpecifiersWithNamespaceIfNeeded(CSSParserSelector*);
+ CSSParserSelector* rewriteSpecifiers(CSSParserSelector*, CSSParserSelector*);
+ CSSParserSelector* rewriteSpecifiersForShadowDistributed(CSSParserSelector* specifiers, CSSParserSelector* distributedPseudoElementSelector);
+
+ void invalidBlockHit();
+
+ Vector<OwnPtr<CSSParserSelector> >* reusableSelectorVector() { return &m_reusableSelectorVector; }
+
+ void clearProperties();
+
+ PassRefPtr<ImmutableStylePropertySet> createStylePropertySet();
+
+ CSSParserContext m_context;
+
+ bool m_important;
+ CSSPropertyID m_id;
+ RawPtrWillBeMember<StyleSheetContents> m_styleSheet;
+ RefPtrWillBeMember<StyleRuleBase> m_rule;
+ RefPtrWillBeMember<StyleKeyframe> m_keyframe;
+ RefPtrWillBeMember<MediaQuerySet> m_mediaList;
+ OwnPtr<CSSParserValueList> m_valueList;
+ bool m_supportsCondition;
+
+ WillBeHeapVector<CSSProperty, 256> m_parsedProperties;
+ CSSSelectorList* m_selectorListForParseSelector;
+
+ unsigned m_numParsedPropertiesBeforeMarginBox;
+
+ bool m_hadSyntacticallyValidCSSRule;
+ bool m_logErrors;
+ bool m_ignoreErrors;
+
+ AtomicString m_defaultNamespace;
+
+ // tokenizer methods and data
+ CSSParserObserver* m_observer;
+
+ // Local functions which just call into CSSParserObserver if non-null.
+ void startRule();
+ void endRule(bool valid);
+ void startRuleHeader(CSSRuleSourceData::Type);
+ void endRuleHeader();
+ void startSelector();
+ void endSelector();
+ void startRuleBody();
+ void startProperty();
+ void endProperty(bool isImportantFound, bool isPropertyParsed, CSSParserError = NoCSSError);
+ void startEndUnknownRule();
+
+ void endInvalidRuleHeader();
+ void reportError(const CSSParserLocation&, CSSParserError = GeneralCSSError);
+ void resumeErrorLogging() { m_ignoreErrors = false; }
+ void setLocationLabel(const CSSParserLocation& location) { m_locationLabel = location; }
+ const CSSParserLocation& lastLocationLabel() const { return m_locationLabel; }
+
+ void tokenToLowerCase(CSSParserString& token);
+
+ void markViewportRuleBodyStart() { m_inViewport = true; }
+ void markViewportRuleBodyEnd() { m_inViewport = false; }
+ StyleRuleBase* createViewportRule();
+
+ CSSParserLocation currentLocation() { return m_tokenizer.currentLocation(); }
+
+private:
+ class StyleDeclarationScope {
+ STACK_ALLOCATED();
+ WTF_MAKE_NONCOPYABLE(StyleDeclarationScope);
+ public:
+ StyleDeclarationScope(BisonCSSParser* parser, const StylePropertySet* declaration)
+ : m_parser(parser)
+ , m_mode(declaration->cssParserMode())
+ {
+ if (isCSSViewportParsingEnabledForMode(m_mode)) {
+ ASSERT(!m_parser->inViewport());
+ m_parser->markViewportRuleBodyStart();
+ }
+ }
+
+ ~StyleDeclarationScope()
+ {
+ if (isCSSViewportParsingEnabledForMode(m_mode))
+ m_parser->markViewportRuleBodyEnd();
+ }
+
+ private:
+ BisonCSSParser* m_parser;
+ CSSParserMode m_mode;
+ };
+
+ inline void ensureLineEndings();
+
+ void setStyleSheet(StyleSheetContents* styleSheet) { m_styleSheet = styleSheet; }
+
+ bool inViewport() const { return m_inViewport; }
+
+ void recheckAtKeyword(const UChar* str, int len);
+
+ template<unsigned prefixLength, unsigned suffixLength>
+ inline void setupParser(const char (&prefix)[prefixLength], const String& string, const char (&suffix)[suffixLength])
+ {
+ setupParser(prefix, prefixLength - 1, string, suffix, suffixLength - 1);
+ }
+ void setupParser(const char* prefix, unsigned prefixLength, const String&, const char* suffix, unsigned suffixLength);
+
+ bool parseValue(MutableStylePropertySet*, CSSPropertyID, const String&, bool important, StyleSheetContents* contextStyleSheet);
+ PassRefPtr<ImmutableStylePropertySet> parseDeclaration(const String&, StyleSheetContents* contextStyleSheet);
+
+ bool parseColor(const String&);
+
+ const String* m_source;
+ TextPosition m_startPosition;
+ CSSRuleSourceData::Type m_ruleHeaderType;
+ unsigned m_ruleHeaderStartOffset;
+ int m_ruleHeaderStartLineNumber;
+ OwnPtr<Vector<unsigned> > m_lineEndings;
+
+ bool m_ruleHasHeader;
+
+ bool m_allowImportRules;
+ bool m_allowNamespaceDeclarations;
+
+ bool m_inViewport;
+
+ CSSParserLocation m_locationLabel;
+
+ WillBeHeapVector<RefPtrWillBeMember<StyleRuleBase> > m_parsedRules;
+ WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > m_parsedKeyframes;
+ WillBeHeapVector<RefPtrWillBeMember<MediaQuerySet> > m_parsedMediaQuerySets;
+ WillBeHeapVector<OwnPtrWillBeMember<RuleList> > m_parsedRuleLists;
+ Vector<CSSParserSelector*> m_floatingSelectors;
+ Vector<Vector<OwnPtr<CSSParserSelector> >*> m_floatingSelectorVectors;
+ Vector<CSSParserValueList*> m_floatingValueLists;
+ Vector<CSSParserFunction*> m_floatingFunctions;
+
+ OwnPtrWillBeMember<MediaQuery> m_floatingMediaQuery;
+ OwnPtrWillBeMember<MediaQueryExp> m_floatingMediaQueryExp;
+ OwnPtrWillBeMember<WillBeHeapVector<OwnPtrWillBeMember<MediaQueryExp> > > m_floatingMediaQueryExpList;
+
+ OwnPtrWillBeMember<WillBeHeapVector<RefPtrWillBeMember<StyleKeyframe> > > m_floatingKeyframeVector;
+
+ Vector<OwnPtr<CSSParserSelector> > m_reusableSelectorVector;
+
+ OwnPtrWillBeMember<RuleSourceDataList> m_supportsRuleDataStack;
+
+ bool isLoggingErrors();
+ void logError(const String& message, const CSSParserLocation&);
+
+ CSSTokenizer m_tokenizer;
+
+ friend class TransformOperationInfo;
+ friend class FilterOperationInfo;
+};
+
+inline int cssyylex(void* yylval, BisonCSSParser* parser)
+{
+ return parser->m_tokenizer.lex(yylval);
+}
+
+bool isValidNthToken(const CSSParserString&);
+
+} // namespace WebCore
+
+#endif // BisonCSSParser_h
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParserTest.cpp b/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParserTest.cpp
new file mode 100644
index 00000000000..f2e2f36e11f
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/BisonCSSParserTest.cpp
@@ -0,0 +1,67 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/BisonCSSParser.h"
+
+#include "core/css/CSSTimingFunctionValue.h"
+#include "platform/animation/TimingFunction.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+TEST(BisonCSSParserTest, ParseAnimationTimingFunctionValue)
+{
+ RefPtrWillBeRawPtr<CSSValue> timingFunctionValue;
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("ease");
+ EXPECT_EQ(CSSValueEase, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("linear");
+ EXPECT_EQ(CSSValueLinear, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("ease-in");
+ EXPECT_EQ(CSSValueEaseIn, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("ease-out");
+ EXPECT_EQ(CSSValueEaseOut, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("ease-in-out");
+ EXPECT_EQ(CSSValueEaseInOut, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("step-start");
+ EXPECT_EQ(CSSValueStepStart, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("step-middle");
+ EXPECT_EQ(CSSValueStepMiddle, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("step-end");
+ EXPECT_EQ(CSSValueStepEnd, toCSSPrimitiveValue(timingFunctionValue.get())->getValueID());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("steps(3, start)");
+ EXPECT_TRUE(CSSStepsTimingFunctionValue::create(3, StepsTimingFunction::StepAtStart)->equals(toCSSStepsTimingFunctionValue(*timingFunctionValue.get())));
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("steps(3, middle)");
+ EXPECT_TRUE(CSSStepsTimingFunctionValue::create(3, StepsTimingFunction::StepAtMiddle)->equals(toCSSStepsTimingFunctionValue(*timingFunctionValue.get())));
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("steps(3, end)");
+ EXPECT_TRUE(CSSStepsTimingFunctionValue::create(3, StepsTimingFunction::StepAtEnd)->equals(toCSSStepsTimingFunctionValue(*timingFunctionValue.get())));
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("steps(3, nowhere)");
+ EXPECT_EQ(0, timingFunctionValue.get());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("steps(-3, end)");
+ EXPECT_EQ(0, timingFunctionValue.get());
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("steps(3)");
+ EXPECT_TRUE(CSSStepsTimingFunctionValue::create(3, StepsTimingFunction::StepAtEnd)->equals(toCSSStepsTimingFunctionValue(*timingFunctionValue.get())));
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("cubic-bezier(0.1, 5, 0.23, 0)");
+ EXPECT_TRUE(CSSCubicBezierTimingFunctionValue::create(0.1, 5, 0.23, 0)->equals(toCSSCubicBezierTimingFunctionValue(*timingFunctionValue.get())));
+
+ timingFunctionValue = BisonCSSParser::parseAnimationTimingFunctionValue("cubic-bezier(0.1, 0, 4, 0.4)");
+ EXPECT_EQ(0, timingFunctionValue.get());
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMapForEachCallback.idl b/chromium/third_party/WebKit/Source/core/css/parser/CSSParserIdioms.h
index 11a6cfcb581..4217d0a4368 100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSVariablesMapForEachCallback.idl
+++ b/chromium/third_party/WebKit/Source/core/css/parser/CSSParserIdioms.h
@@ -11,6 +11,9 @@
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
@@ -25,7 +28,20 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-callback interface CSSVariablesMapForEachCallback {
- [CallWith=ThisValue] void handleItem(DOMString value, DOMString name, CSSVariablesMap map);
- void handleItem(DOMString value, DOMString name, CSSVariablesMap map);
-};
+#ifndef CSSParserIdioms_h
+#define CSSParserIdioms_h
+
+#include "wtf/unicode/Unicode.h"
+
+namespace WebCore {
+
+// Space characters as defined by the CSS specification.
+// http://www.w3.org/TR/css3-syntax/#whitespace
+inline bool isCSSSpace(UChar c)
+{
+ return c == ' ' || c == '\t' || c == '\n';
+}
+
+}
+
+#endif
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/CSSParserObserver.h b/chromium/third_party/WebKit/Source/core/css/parser/CSSParserObserver.h
new file mode 100644
index 00000000000..c6711a4eab2
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/CSSParserObserver.h
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
+ * Copyright (C) 2004, 2005, 2006, 2008, 2009, 2010 Apple Inc. All rights reserved.
+ * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
+ * Copyright (C) 2009 - 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef CSSParserObserver_h
+#define CSSParserObserver_h
+
+#include "core/css/CSSPropertySourceData.h"
+
+namespace WebCore {
+
+// FIXME: Although the parser produces these, they're all ignored!
+enum CSSParserError {
+ NoCSSError,
+ PropertyDeclarationCSSError,
+ InvalidPropertyValueCSSError,
+ InvalidPropertyCSSError,
+ InvalidSelectorCSSError,
+ InvalidSupportsConditionCSSError,
+ InvalidRuleCSSError,
+ InvalidMediaQueryCSSError,
+ InvalidKeyframeSelectorCSSError,
+ InvalidSelectorPseudoCSSError,
+ UnterminatedCommentCSSError,
+ GeneralCSSError
+};
+
+// FIXME: What are these actually used for? There is probably
+// a better way for the parser to communicate this information
+// to the Inspector.
+
+// This only implemented by StyleSheetHandler in InspectorStyleSheet.cpp.
+class CSSParserObserver {
+ STACK_ALLOCATED();
+public:
+ virtual void startRuleHeader(CSSRuleSourceData::Type, unsigned offset) = 0;
+ virtual void endRuleHeader(unsigned offset) = 0;
+ virtual void startSelector(unsigned offset) = 0;
+ virtual void endSelector(unsigned offset) = 0;
+ virtual void startRuleBody(unsigned offset) = 0;
+ virtual void endRuleBody(unsigned offset, bool error) = 0;
+ virtual void startEndUnknownRule() = 0;
+ virtual void startProperty(unsigned offset) = 0;
+ virtual void endProperty(bool isImportant, bool isParsed, unsigned offset, CSSParserError) = 0;
+ virtual void startComment(unsigned offset) = 0;
+ virtual void endComment(unsigned offset) = 0;
+};
+
+} // namespace WebCore
+
+#endif // CSSParserObserver_h
diff --git a/chromium/third_party/WebKit/Source/core/css/CSSParser-in.cpp b/chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.cpp
index 7b540fd7b14..5431a1a06c4 100755..100644
--- a/chromium/third_party/WebKit/Source/core/css/CSSParser-in.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.cpp
@@ -25,11 +25,11 @@
*/
#include "config.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/CSSPropertyParser.h"
-#include "CSSValueKeywords.h"
-#include "RuntimeEnabledFeatures.h"
-#include "StylePropertyShorthand.h"
+// FIXME: Way too many!
+#include "core/CSSValueKeywords.h"
+#include "core/StylePropertyShorthand.h"
#include "core/css/CSSArrayFunctionValue.h"
#include "core/css/CSSAspectRatioValue.h"
#include "core/css/CSSBasicShapes.h"
@@ -42,7 +42,7 @@
#include "core/css/CSSFunctionValue.h"
#include "core/css/CSSGradientValue.h"
#include "core/css/CSSGridLineNamesValue.h"
-#include "core/css/CSSGridTemplateValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
#include "core/css/CSSImageSetValue.h"
#include "core/css/CSSImageValue.h"
#include "core/css/CSSInheritedValue.h"
@@ -50,39 +50,30 @@
#include "core/css/CSSKeyframeRule.h"
#include "core/css/CSSKeyframesRule.h"
#include "core/css/CSSLineBoxContainValue.h"
-#include "core/css/CSSMixFunctionValue.h"
+#include "core/css/CSSParserValues.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSPropertySourceData.h"
#include "core/css/CSSReflectValue.h"
#include "core/css/CSSSVGDocumentValue.h"
#include "core/css/CSSSelector.h"
-#include "core/css/CSSShaderValue.h"
#include "core/css/CSSShadowValue.h"
-#include "core/css/CSSStyleSheet.h"
#include "core/css/CSSTimingFunctionValue.h"
#include "core/css/CSSTransformValue.h"
#include "core/css/CSSUnicodeRangeValue.h"
#include "core/css/CSSValueList.h"
#include "core/css/CSSValuePool.h"
-#include "core/css/CSSVariableValue.h"
#include "core/css/Counter.h"
#include "core/css/HashTools.h"
-#include "core/css/MediaList.h"
-#include "core/css/MediaQueryExp.h"
#include "core/css/Pair.h"
#include "core/css/Rect.h"
-#include "core/css/StylePropertySet.h"
-#include "core/css/StyleRule.h"
-#include "core/css/StyleRuleImport.h"
-#include "core/css/StyleSheetContents.h"
-#include "core/dom/Document.h"
+#include "core/css/RuntimeCSSEnabled.h"
+#include "core/css/parser/CSSParserIdioms.h"
#include "core/html/parser/HTMLParserIdioms.h"
#include "core/inspector/InspectorInstrumentation.h"
-#include "core/page/PageConsole.h"
-#include "core/frame/Settings.h"
#include "core/rendering/RenderTheme.h"
-#include "core/svg/SVGParserUtilities.h"
+#include "core/svg/SVGPaint.h"
#include "platform/FloatConversion.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "wtf/BitArray.h"
#include "wtf/HexNumber.h"
#include "wtf/text/StringBuffer.h"
@@ -91,21 +82,10 @@
#include "wtf/text/TextEncoding.h"
#include <limits.h>
-#define YYDEBUG 0
-
-#if YYDEBUG > 0
-extern int cssyydebug;
-#endif
-
-extern int cssyyparse(WebCore::CSSParser*);
-
-using namespace std;
-using namespace WTF;
-
namespace WebCore {
-static const unsigned INVALID_NUM_PARSED_PROPERTIES = UINT_MAX;
static const double MAX_SCALE = 1000000;
+static const unsigned minRepetitions = 10000;
template <unsigned N>
static bool equal(const CSSParserString& a, const char (&b)[N])
@@ -134,1186 +114,34 @@ static bool equalIgnoringCase(CSSParserValue* value, const char (&b)[N])
return equalIgnoringCase(value->string, b);
}
-static PassRefPtr<CSSPrimitiveValue> createPrimitiveValuePair(PassRefPtr<CSSPrimitiveValue> first, PassRefPtr<CSSPrimitiveValue> second, Pair::IdenticalValuesPolicy identicalValuesPolicy = Pair::DropIdenticalValues)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createPrimitiveValuePair(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> first, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> second, Pair::IdenticalValuesPolicy identicalValuesPolicy = Pair::DropIdenticalValues)
{
return cssValuePool().createValue(Pair::create(first, second, identicalValuesPolicy));
}
-class AnimationParseContext {
-public:
- AnimationParseContext()
- : m_animationPropertyKeywordAllowed(true)
- , m_firstAnimationCommitted(false)
- , m_hasSeenAnimationPropertyKeyword(false)
- {
- }
-
- void commitFirstAnimation()
- {
- m_firstAnimationCommitted = true;
- }
-
- bool hasCommittedFirstAnimation() const
- {
- return m_firstAnimationCommitted;
- }
-
- void commitAnimationPropertyKeyword()
- {
- m_animationPropertyKeywordAllowed = false;
- }
-
- bool animationPropertyKeywordAllowed() const
- {
- return m_animationPropertyKeywordAllowed;
- }
-
- bool hasSeenAnimationPropertyKeyword() const
- {
- return m_hasSeenAnimationPropertyKeyword;
- }
-
- void sawAnimationPropertyKeyword()
- {
- m_hasSeenAnimationPropertyKeyword = true;
- }
-
-private:
- bool m_animationPropertyKeywordAllowed;
- bool m_firstAnimationCommitted;
- bool m_hasSeenAnimationPropertyKeyword;
-};
-
-CSSParser::CSSParser(const CSSParserContext& context, UseCounter* counter)
- : m_context(context)
- , m_important(false)
- , m_id(CSSPropertyInvalid)
- , m_styleSheet(0)
- , m_supportsCondition(false)
- , m_selectorListForParseSelector(0)
- , m_numParsedPropertiesBeforeMarginBox(INVALID_NUM_PARSED_PROPERTIES)
+CSSPropertyParser::CSSPropertyParser(OwnPtr<CSSParserValueList>& valueList,
+ const CSSParserContext& context, bool inViewport, bool savedImportant,
+ WillBeHeapVector<CSSProperty, 256>& parsedProperties,
+ CSSRuleSourceData::Type ruleType)
+ : m_valueList(valueList)
+ , m_context(context)
+ , m_inViewport(inViewport)
+ , m_important(savedImportant) // See comment in header, should be removed.
+ , m_parsedProperties(parsedProperties)
+ , m_ruleType(ruleType)
, m_inParseShorthand(0)
, m_currentShorthand(CSSPropertyInvalid)
, m_implicitShorthand(false)
- , m_hasFontFaceOnlyValues(false)
- , m_hadSyntacticallyValidCSSRule(false)
- , m_logErrors(false)
- , m_ignoreErrors(false)
- , m_inFilterRule(false)
- , m_defaultNamespace(starAtom)
- , m_sourceDataHandler(0)
- , m_source(0)
- , m_ruleHeaderType(CSSRuleSourceData::UNKNOWN_RULE)
- , m_allowImportRules(true)
- , m_allowNamespaceDeclarations(true)
- , m_inViewport(false)
- , m_useCounter(counter)
- , m_tokenizer(*this)
-{
-#if YYDEBUG > 0
- cssyydebug = 1;
-#endif
- CSSPropertySourceData::init();
-}
-
-CSSParser::~CSSParser()
-{
- clearProperties();
-
- deleteAllValues(m_floatingSelectors);
- deleteAllValues(m_floatingSelectorVectors);
- deleteAllValues(m_floatingValueLists);
- deleteAllValues(m_floatingFunctions);
-}
-
-void CSSParser::setupParser(const char* prefix, unsigned prefixLength, const String& string, const char* suffix, unsigned suffixLength)
-{
- m_tokenizer.setupTokenizer(prefix, prefixLength, string, suffix, suffixLength);
- m_ruleHasHeader = true;
-}
-
-void CSSParser::parseSheet(StyleSheetContents* sheet, const String& string, const TextPosition& startPosition, SourceDataHandler* sourceDataHandler, bool logErrors)
-{
- setStyleSheet(sheet);
- m_defaultNamespace = starAtom; // Reset the default namespace.
- m_sourceDataHandler = sourceDataHandler;
- m_logErrors = logErrors && sheet->singleOwnerDocument() && !sheet->baseURL().isEmpty() && sheet->singleOwnerDocument()->page();
- m_ignoreErrors = false;
- m_tokenizer.m_lineNumber = 0;
- m_startPosition = startPosition;
- m_source = &string;
- m_tokenizer.m_internal = false;
- setupParser("", string, "");
- cssyyparse(this);
- sheet->shrinkToFit();
- m_source = 0;
- m_sourceDataHandler = 0;
- m_rule = 0;
- m_lineEndings.clear();
- m_ignoreErrors = false;
- m_logErrors = false;
- m_tokenizer.m_internal = true;
-}
-
-PassRefPtr<StyleRuleBase> CSSParser::parseRule(StyleSheetContents* sheet, const String& string)
-{
- setStyleSheet(sheet);
- m_allowNamespaceDeclarations = false;
- setupParser("@-internal-rule ", string, "");
- cssyyparse(this);
- return m_rule.release();
-}
-
-PassRefPtr<StyleKeyframe> CSSParser::parseKeyframeRule(StyleSheetContents* sheet, const String& string)
-{
- setStyleSheet(sheet);
- setupParser("@-internal-keyframe-rule ", string, "");
- cssyyparse(this);
- return m_keyframe.release();
-}
-
-PassOwnPtr<Vector<double> > CSSParser::parseKeyframeKeyList(const String& string)
-{
- setupParser("@-internal-keyframe-key-list ", string, "");
- cssyyparse(this);
- ASSERT(m_valueList);
- return StyleKeyframe::createKeyList(m_valueList.get());
-}
-
-bool CSSParser::parseSupportsCondition(const String& string)
-{
- m_supportsCondition = false;
- setupParser("@-internal-supports-condition ", string, "");
- cssyyparse(this);
- return m_supportsCondition;
-}
-
-static inline bool isColorPropertyID(CSSPropertyID propertyId)
-{
- switch (propertyId) {
- case CSSPropertyColor:
- case CSSPropertyBackgroundColor:
- case CSSPropertyBorderBottomColor:
- case CSSPropertyBorderLeftColor:
- case CSSPropertyBorderRightColor:
- case CSSPropertyBorderTopColor:
- case CSSPropertyOutlineColor:
- case CSSPropertyTextLineThroughColor:
- case CSSPropertyTextOverlineColor:
- case CSSPropertyTextUnderlineColor:
- case CSSPropertyWebkitBorderAfterColor:
- case CSSPropertyWebkitBorderBeforeColor:
- case CSSPropertyWebkitBorderEndColor:
- case CSSPropertyWebkitBorderStartColor:
- case CSSPropertyWebkitColumnRuleColor:
- case CSSPropertyWebkitTextEmphasisColor:
- case CSSPropertyWebkitTextFillColor:
- case CSSPropertyWebkitTextStrokeColor:
- return true;
- case CSSPropertyTextDecorationColor:
- return RuntimeEnabledFeatures::css3TextDecorationsEnabled();
- default:
- return false;
- }
-}
-
-static bool parseColorValue(MutableStylePropertySet* declaration, CSSPropertyID propertyId, const String& string, bool important, CSSParserMode cssParserMode)
-{
- ASSERT(!string.isEmpty());
- bool quirksMode = isQuirksModeBehavior(cssParserMode);
- if (!isColorPropertyID(propertyId))
- return false;
- CSSParserString cssString;
- cssString.init(string);
- CSSValueID valueID = cssValueKeywordID(cssString);
- bool validPrimitive = false;
- if (valueID == CSSValueWebkitText) {
- validPrimitive = true;
- } else if (valueID == CSSValueCurrentcolor) {
- validPrimitive = true;
- } else if ((valueID >= CSSValueAqua && valueID <= CSSValueWindowtext) || valueID == CSSValueMenu
- || (quirksMode && valueID >= CSSValueWebkitFocusRingColor && valueID < CSSValueWebkitText)) {
- validPrimitive = true;
- }
-
- if (validPrimitive) {
- RefPtr<CSSValue> value = cssValuePool().createIdentifierValue(valueID);
- declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
- return true;
- }
- RGBA32 color;
- if (!CSSParser::fastParseColor(color, string, !quirksMode && string[0] != '#'))
- return false;
- RefPtr<CSSValue> value = cssValuePool().createColorValue(color);
- declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
- return true;
-}
-
-static inline bool isSimpleLengthPropertyID(CSSPropertyID propertyId, bool& acceptsNegativeNumbers)
-{
- switch (propertyId) {
- case CSSPropertyFontSize:
- case CSSPropertyHeight:
- case CSSPropertyWidth:
- case CSSPropertyMinHeight:
- case CSSPropertyMinWidth:
- case CSSPropertyPaddingBottom:
- case CSSPropertyPaddingLeft:
- case CSSPropertyPaddingRight:
- case CSSPropertyPaddingTop:
- case CSSPropertyWebkitLogicalWidth:
- case CSSPropertyWebkitLogicalHeight:
- case CSSPropertyWebkitMinLogicalWidth:
- case CSSPropertyWebkitMinLogicalHeight:
- case CSSPropertyWebkitPaddingAfter:
- case CSSPropertyWebkitPaddingBefore:
- case CSSPropertyWebkitPaddingEnd:
- case CSSPropertyWebkitPaddingStart:
- acceptsNegativeNumbers = false;
- return true;
- case CSSPropertyShapeMargin:
- case CSSPropertyShapePadding:
- acceptsNegativeNumbers = false;
- return RuntimeEnabledFeatures::cssShapesEnabled();
- case CSSPropertyBottom:
- case CSSPropertyLeft:
- case CSSPropertyMarginBottom:
- case CSSPropertyMarginLeft:
- case CSSPropertyMarginRight:
- case CSSPropertyMarginTop:
- case CSSPropertyRight:
- case CSSPropertyTop:
- case CSSPropertyWebkitMarginAfter:
- case CSSPropertyWebkitMarginBefore:
- case CSSPropertyWebkitMarginEnd:
- case CSSPropertyWebkitMarginStart:
- acceptsNegativeNumbers = true;
- return true;
- default:
- return false;
- }
-}
-
-template <typename CharacterType>
-static inline bool parseSimpleLength(const CharacterType* characters, unsigned& length, CSSPrimitiveValue::UnitTypes& unit, double& number)
-{
- if (length > 2 && (characters[length - 2] | 0x20) == 'p' && (characters[length - 1] | 0x20) == 'x') {
- length -= 2;
- unit = CSSPrimitiveValue::CSS_PX;
- } else if (length > 1 && characters[length - 1] == '%') {
- length -= 1;
- unit = CSSPrimitiveValue::CSS_PERCENTAGE;
- }
-
- // We rely on charactersToDouble for validation as well. The function
- // will set "ok" to "false" if the entire passed-in character range does
- // not represent a double.
- bool ok;
- number = charactersToDouble(characters, length, &ok);
- return ok;
-}
-
-static bool parseSimpleLengthValue(MutableStylePropertySet* declaration, CSSPropertyID propertyId, const String& string, bool important, CSSParserMode cssParserMode)
-{
- ASSERT(!string.isEmpty());
- bool acceptsNegativeNumbers;
-
- // In @viewport, width and height are shorthands, not simple length values.
- if (isCSSViewportParsingEnabledForMode(cssParserMode) || !isSimpleLengthPropertyID(propertyId, acceptsNegativeNumbers))
- return false;
-
- unsigned length = string.length();
- double number;
- CSSPrimitiveValue::UnitTypes unit = CSSPrimitiveValue::CSS_NUMBER;
-
- if (string.is8Bit()) {
- if (!parseSimpleLength(string.characters8(), length, unit, number))
- return false;
- } else {
- if (!parseSimpleLength(string.characters16(), length, unit, number))
- return false;
- }
-
- if (unit == CSSPrimitiveValue::CSS_NUMBER) {
- bool quirksMode = isQuirksModeBehavior(cssParserMode);
- if (number && !quirksMode)
- return false;
- unit = CSSPrimitiveValue::CSS_PX;
- }
- if (number < 0 && !acceptsNegativeNumbers)
- return false;
-
- RefPtr<CSSValue> value = cssValuePool().createValue(number, unit);
- declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
- return true;
-}
-
-static inline bool isValidKeywordPropertyAndValue(CSSPropertyID propertyId, int valueID, const CSSParserContext& parserContext)
-{
- if (!valueID)
- return false;
-
- switch (propertyId) {
- case CSSPropertyBorderCollapse: // collapse | separate | inherit
- if (valueID == CSSValueCollapse || valueID == CSSValueSeparate)
- return true;
- break;
- case CSSPropertyBorderTopStyle: // <border-style> | inherit
- case CSSPropertyBorderRightStyle: // Defined as: none | hidden | dotted | dashed |
- case CSSPropertyBorderBottomStyle: // solid | double | groove | ridge | inset | outset
- case CSSPropertyBorderLeftStyle:
- case CSSPropertyWebkitBorderAfterStyle:
- case CSSPropertyWebkitBorderBeforeStyle:
- case CSSPropertyWebkitBorderEndStyle:
- case CSSPropertyWebkitBorderStartStyle:
- case CSSPropertyWebkitColumnRuleStyle:
- if (valueID >= CSSValueNone && valueID <= CSSValueDouble)
- return true;
- break;
- case CSSPropertyBoxSizing:
- if (valueID == CSSValueBorderBox || valueID == CSSValueContentBox)
- return true;
- break;
- case CSSPropertyCaptionSide: // top | bottom | left | right | inherit
- if (valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueTop || valueID == CSSValueBottom)
- return true;
- break;
- case CSSPropertyClear: // none | left | right | both | inherit
- if (valueID == CSSValueNone || valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueBoth)
- return true;
- break;
- case CSSPropertyDirection: // ltr | rtl | inherit
- if (valueID == CSSValueLtr || valueID == CSSValueRtl)
- return true;
- break;
- case CSSPropertyDisplay:
- // inline | block | list-item | inline-block | table |
- // inline-table | table-row-group | table-header-group | table-footer-group | table-row |
- // table-column-group | table-column | table-cell | table-caption | -webkit-box | -webkit-inline-box | none | inherit
- // flex | inline-flex | -webkit-flex | -webkit-inline-flex | grid | inline-grid | lazy-block
- if ((valueID >= CSSValueInline && valueID <= CSSValueInlineFlex) || valueID == CSSValueWebkitFlex || valueID == CSSValueWebkitInlineFlex || valueID == CSSValueNone)
- return true;
- if (valueID == CSSValueGrid || valueID == CSSValueInlineGrid)
- return RuntimeEnabledFeatures::cssGridLayoutEnabled();
- break;
-
- case CSSPropertyEmptyCells: // show | hide | inherit
- if (valueID == CSSValueShow || valueID == CSSValueHide)
- return true;
- break;
- case CSSPropertyFloat: // left | right | none | center (for buggy CSS, maps to none)
- if (valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueNone || valueID == CSSValueCenter)
- return true;
- break;
- case CSSPropertyFontStyle: // normal | italic | oblique | inherit
- if (valueID == CSSValueNormal || valueID == CSSValueItalic || valueID == CSSValueOblique)
- return true;
- break;
- case CSSPropertyImageRendering: // auto | optimizeContrast
- if (valueID == CSSValueAuto || valueID == CSSValueWebkitOptimizeContrast)
- return true;
- break;
- case CSSPropertyIsolation: // auto | isolate
- if (valueID == CSSValueAuto || valueID == CSSValueIsolate)
- return RuntimeEnabledFeatures::cssCompositingEnabled();
- break;
- case CSSPropertyListStylePosition: // inside | outside | inherit
- if (valueID == CSSValueInside || valueID == CSSValueOutside)
- return true;
- break;
- case CSSPropertyListStyleType:
- // See section CSS_PROP_LIST_STYLE_TYPE of file CSSValueKeywords.in
- // for the list of supported list-style-types.
- if ((valueID >= CSSValueDisc && valueID <= CSSValueKatakanaIroha) || valueID == CSSValueNone)
- return true;
- break;
- case CSSPropertyObjectFit:
- if (RuntimeEnabledFeatures::objectFitPositionEnabled()) {
- if (valueID == CSSValueFill || valueID == CSSValueContain || valueID == CSSValueCover || valueID == CSSValueNone || valueID == CSSValueScaleDown)
- return true;
- }
- break;
- case CSSPropertyOutlineStyle: // (<border-style> except hidden) | auto | inherit
- if (valueID == CSSValueAuto || valueID == CSSValueNone || (valueID >= CSSValueInset && valueID <= CSSValueDouble))
- return true;
- break;
- case CSSPropertyOverflowWrap: // normal | break-word
- case CSSPropertyWordWrap:
- if (valueID == CSSValueNormal || valueID == CSSValueBreakWord)
- return true;
- break;
- case CSSPropertyOverflowX: // visible | hidden | scroll | auto | overlay | inherit
- if (valueID == CSSValueVisible || valueID == CSSValueHidden || valueID == CSSValueScroll || valueID == CSSValueAuto || valueID == CSSValueOverlay)
- return true;
- break;
- case CSSPropertyOverflowY: // visible | hidden | scroll | auto | overlay | inherit | -webkit-paged-x | -webkit-paged-y
- if (valueID == CSSValueVisible || valueID == CSSValueHidden || valueID == CSSValueScroll || valueID == CSSValueAuto || valueID == CSSValueOverlay || valueID == CSSValueWebkitPagedX || valueID == CSSValueWebkitPagedY)
- return true;
- break;
- case CSSPropertyPageBreakAfter: // auto | always | avoid | left | right | inherit
- case CSSPropertyPageBreakBefore:
- case CSSPropertyWebkitColumnBreakAfter:
- case CSSPropertyWebkitColumnBreakBefore:
- if (valueID == CSSValueAuto || valueID == CSSValueAlways || valueID == CSSValueAvoid || valueID == CSSValueLeft || valueID == CSSValueRight)
- return true;
- break;
- case CSSPropertyPageBreakInside: // avoid | auto | inherit
- case CSSPropertyWebkitColumnBreakInside:
- if (valueID == CSSValueAuto || valueID == CSSValueAvoid)
- return true;
- break;
- case CSSPropertyPointerEvents:
- // none | visiblePainted | visibleFill | visibleStroke | visible |
- // painted | fill | stroke | auto | all | bounding-box | inherit
- if (valueID == CSSValueVisible || valueID == CSSValueNone || valueID == CSSValueAll || valueID == CSSValueAuto || (valueID >= CSSValueVisiblepainted && valueID <= CSSValueBoundingBox))
- return true;
- break;
- case CSSPropertyPosition: // static | relative | absolute | fixed | sticky | inherit
- if (valueID == CSSValueStatic || valueID == CSSValueRelative || valueID == CSSValueAbsolute || valueID == CSSValueFixed
- || (RuntimeEnabledFeatures::cssStickyPositionEnabled() && valueID == CSSValueSticky))
- return true;
- break;
- case CSSPropertyResize: // none | both | horizontal | vertical | auto
- if (valueID == CSSValueNone || valueID == CSSValueBoth || valueID == CSSValueHorizontal || valueID == CSSValueVertical || valueID == CSSValueAuto)
- return true;
- break;
- case CSSPropertySpeak: // none | normal | spell-out | digits | literal-punctuation | no-punctuation | inherit
- if (valueID == CSSValueNone || valueID == CSSValueNormal || valueID == CSSValueSpellOut || valueID == CSSValueDigits || valueID == CSSValueLiteralPunctuation || valueID == CSSValueNoPunctuation)
- return true;
- break;
- case CSSPropertyTableLayout: // auto | fixed | inherit
- if (valueID == CSSValueAuto || valueID == CSSValueFixed)
- return true;
- break;
- case CSSPropertyTextAlignLast:
- // auto | start | end | left | right | center | justify
- if (RuntimeEnabledFeatures::css3TextEnabled()
- && ((valueID >= CSSValueLeft && valueID <= CSSValueJustify) || valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueAuto))
- return true;
- break;
- case CSSPropertyTextJustify:
- // auto | none | inter-word | distribute
- if (RuntimeEnabledFeatures::css3TextEnabled()
- && (valueID == CSSValueInterWord || valueID == CSSValueDistribute || valueID == CSSValueAuto || valueID == CSSValueNone))
- return true;
- break;
- case CSSPropertyTextLineThroughMode:
- case CSSPropertyTextOverlineMode:
- case CSSPropertyTextUnderlineMode:
- if (valueID == CSSValueContinuous || valueID == CSSValueSkipWhiteSpace)
- return true;
- break;
- case CSSPropertyTextLineThroughStyle:
- case CSSPropertyTextOverlineStyle:
- case CSSPropertyTextUnderlineStyle:
- if (valueID == CSSValueNone || valueID == CSSValueSolid || valueID == CSSValueDouble || valueID == CSSValueDashed || valueID == CSSValueDotDash || valueID == CSSValueDotDotDash || valueID == CSSValueWave)
- return true;
- break;
- case CSSPropertyTextOverflow: // clip | ellipsis
- if (valueID == CSSValueClip || valueID == CSSValueEllipsis)
- return true;
- break;
- case CSSPropertyTextRendering: // auto | optimizeSpeed | optimizeLegibility | geometricPrecision
- if (valueID == CSSValueAuto || valueID == CSSValueOptimizespeed || valueID == CSSValueOptimizelegibility || valueID == CSSValueGeometricprecision)
- return true;
- break;
- case CSSPropertyTextTransform: // capitalize | uppercase | lowercase | none | inherit
- if ((valueID >= CSSValueCapitalize && valueID <= CSSValueLowercase) || valueID == CSSValueNone)
- return true;
- break;
- case CSSPropertyTouchActionDelay: // none | script
- if (RuntimeEnabledFeatures::cssTouchActionEnabled() && (valueID == CSSValueScript || valueID == CSSValueNone))
- return true;
- break;
- case CSSPropertyVisibility: // visible | hidden | collapse | inherit
- if (valueID == CSSValueVisible || valueID == CSSValueHidden || valueID == CSSValueCollapse)
- return true;
- break;
- case CSSPropertyWebkitAppearance:
- if ((valueID >= CSSValueCheckbox && valueID <= CSSValueTextarea) || valueID == CSSValueNone)
- return true;
- break;
- case CSSPropertyWebkitBackfaceVisibility:
- if (valueID == CSSValueVisible || valueID == CSSValueHidden)
- return true;
- break;
- case CSSPropertyMixBlendMode:
- if (RuntimeEnabledFeatures::cssCompositingEnabled() && (valueID == CSSValueNormal || valueID == CSSValueMultiply || valueID == CSSValueScreen
- || valueID == CSSValueOverlay || valueID == CSSValueDarken || valueID == CSSValueLighten || valueID == CSSValueColorDodge
- || valueID == CSSValueColorBurn || valueID == CSSValueHardLight || valueID == CSSValueSoftLight || valueID == CSSValueDifference
- || valueID == CSSValueExclusion || valueID == CSSValueHue || valueID == CSSValueSaturation || valueID == CSSValueColor
- || valueID == CSSValueLuminosity))
- return true;
- break;
- case CSSPropertyWebkitBorderFit:
- if (valueID == CSSValueBorder || valueID == CSSValueLines)
- return true;
- break;
- case CSSPropertyWebkitBoxAlign:
- if (valueID == CSSValueStretch || valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueCenter || valueID == CSSValueBaseline)
- return true;
- break;
- case CSSPropertyWebkitBoxDecorationBreak:
- if (valueID == CSSValueClone || valueID == CSSValueSlice)
- return true;
- break;
- case CSSPropertyWebkitBoxDirection:
- if (valueID == CSSValueNormal || valueID == CSSValueReverse)
- return true;
- break;
- case CSSPropertyWebkitBoxLines:
- if (valueID == CSSValueSingle || valueID == CSSValueMultiple)
- return true;
- break;
- case CSSPropertyWebkitBoxOrient:
- if (valueID == CSSValueHorizontal || valueID == CSSValueVertical || valueID == CSSValueInlineAxis || valueID == CSSValueBlockAxis)
- return true;
- break;
- case CSSPropertyWebkitBoxPack:
- if (valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueCenter || valueID == CSSValueJustify)
- return true;
- break;
- case CSSPropertyInternalCallback:
- // This property is only injected programmatically, not parsed from stylesheets.
- return false;
- case CSSPropertyColumnFill:
- if (RuntimeEnabledFeatures::regionBasedColumnsEnabled()) {
- if (valueID == CSSValueAuto || valueID == CSSValueBalance)
- return true;
- }
- break;
- case CSSPropertyAlignContent:
- if (valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueSpaceBetween || valueID == CSSValueSpaceAround || valueID == CSSValueStretch)
- return true;
- break;
- case CSSPropertyAlignItems:
- if (valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueBaseline || valueID == CSSValueStretch)
- return true;
- break;
- case CSSPropertyAlignSelf:
- if (valueID == CSSValueAuto || valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueBaseline || valueID == CSSValueStretch)
- return true;
- break;
- case CSSPropertyFlexDirection:
- if (valueID == CSSValueRow || valueID == CSSValueRowReverse || valueID == CSSValueColumn || valueID == CSSValueColumnReverse)
- return true;
- break;
- case CSSPropertyFlexWrap:
- if (valueID == CSSValueNowrap || valueID == CSSValueWrap || valueID == CSSValueWrapReverse)
- return true;
- break;
- case CSSPropertyJustifyContent:
- if (valueID == CSSValueFlexStart || valueID == CSSValueFlexEnd || valueID == CSSValueCenter || valueID == CSSValueSpaceBetween || valueID == CSSValueSpaceAround)
- return true;
- break;
- case CSSPropertyFontKerning:
- if (valueID == CSSValueAuto || valueID == CSSValueNormal || valueID == CSSValueNone)
- return true;
- break;
- case CSSPropertyWebkitFontSmoothing:
- if (valueID == CSSValueAuto || valueID == CSSValueNone || valueID == CSSValueAntialiased || valueID == CSSValueSubpixelAntialiased)
- return true;
- break;
- case CSSPropertyGridAutoFlow:
- if (valueID == CSSValueNone || valueID == CSSValueRow || valueID == CSSValueColumn)
- return RuntimeEnabledFeatures::cssGridLayoutEnabled();
- break;
- case CSSPropertyWebkitLineAlign:
- if (valueID == CSSValueNone || valueID == CSSValueEdges)
- return true;
- break;
- case CSSPropertyWebkitLineBreak: // auto | loose | normal | strict | after-white-space
- if (valueID == CSSValueAuto || valueID == CSSValueLoose || valueID == CSSValueNormal || valueID == CSSValueStrict || valueID == CSSValueAfterWhiteSpace)
- return true;
- break;
- case CSSPropertyWebkitLineSnap:
- if (valueID == CSSValueNone || valueID == CSSValueBaseline || valueID == CSSValueContain)
- return true;
- break;
- case CSSPropertyWebkitMarginAfterCollapse:
- case CSSPropertyWebkitMarginBeforeCollapse:
- case CSSPropertyWebkitMarginBottomCollapse:
- case CSSPropertyWebkitMarginTopCollapse:
- if (valueID == CSSValueCollapse || valueID == CSSValueSeparate || valueID == CSSValueDiscard)
- return true;
- break;
- case CSSPropertyInternalMarqueeDirection:
- if (valueID == CSSValueForwards || valueID == CSSValueBackwards || valueID == CSSValueAhead || valueID == CSSValueReverse || valueID == CSSValueLeft || valueID == CSSValueRight || valueID == CSSValueDown
- || valueID == CSSValueUp || valueID == CSSValueAuto)
- return true;
- break;
- case CSSPropertyInternalMarqueeStyle:
- if (valueID == CSSValueNone || valueID == CSSValueSlide || valueID == CSSValueScroll || valueID == CSSValueAlternate)
- return true;
- break;
- case CSSPropertyWebkitPrintColorAdjust:
- if (valueID == CSSValueExact || valueID == CSSValueEconomy)
- return true;
- break;
- case CSSPropertyWebkitRegionBreakAfter:
- case CSSPropertyWebkitRegionBreakBefore:
- if (RuntimeEnabledFeatures::cssRegionsEnabled() && (valueID == CSSValueAuto || valueID == CSSValueAlways || valueID == CSSValueAvoid || valueID == CSSValueLeft || valueID == CSSValueRight))
- return true;
- break;
- case CSSPropertyWebkitRegionBreakInside:
- if (RuntimeEnabledFeatures::cssRegionsEnabled() && (valueID == CSSValueAuto || valueID == CSSValueAvoid))
- return true;
- break;
- case CSSPropertyWebkitRegionFragment:
- if (RuntimeEnabledFeatures::cssRegionsEnabled() && (valueID == CSSValueAuto || valueID == CSSValueBreak))
- return true;
- break;
- case CSSPropertyWebkitRtlOrdering:
- if (valueID == CSSValueLogical || valueID == CSSValueVisual)
- return true;
- break;
-
- case CSSPropertyWebkitRubyPosition:
- if (valueID == CSSValueBefore || valueID == CSSValueAfter)
- return true;
- break;
-
- case CSSPropertyWebkitTextCombine:
- if (valueID == CSSValueNone || valueID == CSSValueHorizontal)
- return true;
- break;
- case CSSPropertyWebkitTextEmphasisPosition:
- if (valueID == CSSValueOver || valueID == CSSValueUnder)
- return true;
- break;
- case CSSPropertyWebkitTextSecurity:
- // disc | circle | square | none | inherit
- if (valueID == CSSValueDisc || valueID == CSSValueCircle || valueID == CSSValueSquare || valueID == CSSValueNone)
- return true;
- break;
- case CSSPropertyWebkitTransformStyle:
- if (valueID == CSSValueFlat || valueID == CSSValuePreserve3d)
- return true;
- break;
- case CSSPropertyWebkitUserDrag: // auto | none | element
- if (valueID == CSSValueAuto || valueID == CSSValueNone || valueID == CSSValueElement)
- return true;
- break;
- case CSSPropertyWebkitUserModify: // read-only | read-write
- if (valueID == CSSValueReadOnly || valueID == CSSValueReadWrite || valueID == CSSValueReadWritePlaintextOnly)
- return true;
- break;
- case CSSPropertyWebkitUserSelect: // auto | none | text | all
- if (valueID == CSSValueAuto || valueID == CSSValueNone || valueID == CSSValueText || valueID == CSSValueAll)
- return true;
- break;
- case CSSPropertyWebkitWrapFlow:
- if (!RuntimeEnabledFeatures::cssExclusionsEnabled())
- return false;
- if (valueID == CSSValueAuto || valueID == CSSValueBoth || valueID == CSSValueStart || valueID == CSSValueEnd || valueID == CSSValueMaximum || valueID == CSSValueClear)
- return true;
- break;
- case CSSPropertyWebkitWrapThrough:
- if (!RuntimeEnabledFeatures::cssExclusionsEnabled())
- return false;
- if (valueID == CSSValueWrap || valueID == CSSValueNone)
- return true;
- break;
- case CSSPropertyWebkitWritingMode:
- if (valueID >= CSSValueHorizontalTb && valueID <= CSSValueHorizontalBt)
- return true;
- break;
- case CSSPropertyWhiteSpace: // normal | pre | nowrap | inherit
- if (valueID == CSSValueNormal || valueID == CSSValuePre || valueID == CSSValuePreWrap || valueID == CSSValuePreLine || valueID == CSSValueNowrap)
- return true;
- break;
- case CSSPropertyWordBreak: // normal | break-all | break-word (this is a custom extension)
- if (valueID == CSSValueNormal || valueID == CSSValueBreakAll || valueID == CSSValueBreakWord)
- return true;
- break;
- default:
- ASSERT_NOT_REACHED();
- return false;
- }
- return false;
-}
-
-static inline bool isKeywordPropertyID(CSSPropertyID propertyId)
-{
- switch (propertyId) {
- case CSSPropertyMixBlendMode:
- case CSSPropertyIsolation:
- case CSSPropertyBorderBottomStyle:
- case CSSPropertyBorderCollapse:
- case CSSPropertyBorderLeftStyle:
- case CSSPropertyBorderRightStyle:
- case CSSPropertyBorderTopStyle:
- case CSSPropertyBoxSizing:
- case CSSPropertyCaptionSide:
- case CSSPropertyClear:
- case CSSPropertyDirection:
- case CSSPropertyDisplay:
- case CSSPropertyEmptyCells:
- case CSSPropertyFloat:
- case CSSPropertyFontStyle:
- case CSSPropertyImageRendering:
- case CSSPropertyListStylePosition:
- case CSSPropertyListStyleType:
- case CSSPropertyObjectFit:
- case CSSPropertyOutlineStyle:
- case CSSPropertyOverflowWrap:
- case CSSPropertyOverflowX:
- case CSSPropertyOverflowY:
- case CSSPropertyPageBreakAfter:
- case CSSPropertyPageBreakBefore:
- case CSSPropertyPageBreakInside:
- case CSSPropertyPointerEvents:
- case CSSPropertyPosition:
- case CSSPropertyResize:
- case CSSPropertySpeak:
- case CSSPropertyTableLayout:
- case CSSPropertyTextAlignLast:
- case CSSPropertyTextJustify:
- case CSSPropertyTextLineThroughMode:
- case CSSPropertyTextLineThroughStyle:
- case CSSPropertyTextOverflow:
- case CSSPropertyTextOverlineMode:
- case CSSPropertyTextOverlineStyle:
- case CSSPropertyTextRendering:
- case CSSPropertyTextTransform:
- case CSSPropertyTextUnderlineMode:
- case CSSPropertyTextUnderlineStyle:
- case CSSPropertyTouchActionDelay:
- case CSSPropertyVisibility:
- case CSSPropertyWebkitAppearance:
- case CSSPropertyWebkitBackfaceVisibility:
- case CSSPropertyWebkitBorderAfterStyle:
- case CSSPropertyWebkitBorderBeforeStyle:
- case CSSPropertyWebkitBorderEndStyle:
- case CSSPropertyWebkitBorderFit:
- case CSSPropertyWebkitBorderStartStyle:
- case CSSPropertyWebkitBoxAlign:
- case CSSPropertyWebkitBoxDecorationBreak:
- case CSSPropertyWebkitBoxDirection:
- case CSSPropertyWebkitBoxLines:
- case CSSPropertyWebkitBoxOrient:
- case CSSPropertyWebkitBoxPack:
- case CSSPropertyInternalCallback:
- case CSSPropertyWebkitColumnBreakAfter:
- case CSSPropertyWebkitColumnBreakBefore:
- case CSSPropertyWebkitColumnBreakInside:
- case CSSPropertyColumnFill:
- case CSSPropertyWebkitColumnRuleStyle:
- case CSSPropertyAlignContent:
- case CSSPropertyAlignItems:
- case CSSPropertyAlignSelf:
- case CSSPropertyFlexDirection:
- case CSSPropertyFlexWrap:
- case CSSPropertyJustifyContent:
- case CSSPropertyFontKerning:
- case CSSPropertyWebkitFontSmoothing:
- case CSSPropertyGridAutoFlow:
- case CSSPropertyWebkitLineAlign:
- case CSSPropertyWebkitLineBreak:
- case CSSPropertyWebkitLineSnap:
- case CSSPropertyWebkitMarginAfterCollapse:
- case CSSPropertyWebkitMarginBeforeCollapse:
- case CSSPropertyWebkitMarginBottomCollapse:
- case CSSPropertyWebkitMarginTopCollapse:
- case CSSPropertyInternalMarqueeDirection:
- case CSSPropertyInternalMarqueeStyle:
- case CSSPropertyWebkitPrintColorAdjust:
- case CSSPropertyWebkitRegionBreakAfter:
- case CSSPropertyWebkitRegionBreakBefore:
- case CSSPropertyWebkitRegionBreakInside:
- case CSSPropertyWebkitRegionFragment:
- case CSSPropertyWebkitRtlOrdering:
- case CSSPropertyWebkitRubyPosition:
- case CSSPropertyWebkitTextCombine:
- case CSSPropertyWebkitTextEmphasisPosition:
- case CSSPropertyWebkitTextSecurity:
- case CSSPropertyWebkitTransformStyle:
- case CSSPropertyWebkitUserDrag:
- case CSSPropertyWebkitUserModify:
- case CSSPropertyWebkitUserSelect:
- case CSSPropertyWebkitWrapFlow:
- case CSSPropertyWebkitWrapThrough:
- case CSSPropertyWebkitWritingMode:
- case CSSPropertyWhiteSpace:
- case CSSPropertyWordBreak:
- case CSSPropertyWordWrap:
- return true;
- default:
- return false;
- }
-}
-
-static bool parseKeywordValue(MutableStylePropertySet* declaration, CSSPropertyID propertyId, const String& string, bool important, const CSSParserContext& parserContext)
-{
- ASSERT(!string.isEmpty());
-
- if (!isKeywordPropertyID(propertyId)) {
- // All properties accept the values of "initial" and "inherit".
- String lowerCaseString = string.lower();
- if (lowerCaseString != "initial" && lowerCaseString != "inherit")
- return false;
-
- // Parse initial/inherit shorthands using the CSSParser.
- if (shorthandForProperty(propertyId).length())
- return false;
- }
-
- CSSParserString cssString;
- cssString.init(string);
- CSSValueID valueID = cssValueKeywordID(cssString);
-
- if (!valueID)
- return false;
-
- RefPtr<CSSValue> value;
- if (valueID == CSSValueInherit)
- value = cssValuePool().createInheritedValue();
- else if (valueID == CSSValueInitial)
- value = cssValuePool().createExplicitInitialValue();
- else if (isValidKeywordPropertyAndValue(propertyId, valueID, parserContext))
- value = cssValuePool().createIdentifierValue(valueID);
- else
- return false;
-
- declaration->addParsedProperty(CSSProperty(propertyId, value.release(), important));
- return true;
-}
-
-template <typename CharacterType>
-static bool parseTransformTranslateArguments(CSSTransformValue* transformValue, CharacterType* characters, unsigned length, unsigned start, unsigned expectedCount)
-{
- while (expectedCount) {
- size_t end = WTF::find(characters, length, expectedCount == 1 ? ')' : ',', start);
- if (end == kNotFound || (expectedCount == 1 && end != length - 1))
- return false;
- unsigned argumentLength = end - start;
- CSSPrimitiveValue::UnitTypes unit = CSSPrimitiveValue::CSS_NUMBER;
- double number;
- if (!parseSimpleLength(characters + start, argumentLength, unit, number))
- return false;
- if (unit != CSSPrimitiveValue::CSS_PX && (number || unit != CSSPrimitiveValue::CSS_NUMBER))
- return false;
- transformValue->append(cssValuePool().createValue(number, CSSPrimitiveValue::CSS_PX));
- start = end + 1;
- --expectedCount;
- }
- return true;
-}
-
-static bool parseTranslateTransformValue(MutableStylePropertySet* properties, CSSPropertyID propertyID, const String& string, bool important)
-{
- if (propertyID != CSSPropertyWebkitTransform)
- return false;
- static const unsigned shortestValidTransformStringLength = 12;
- static const unsigned likelyMultipartTransformStringLengthCutoff = 32;
- if (string.length() < shortestValidTransformStringLength || string.length() > likelyMultipartTransformStringLengthCutoff)
- return false;
- if (!string.startsWith("translate", false))
- return false;
- UChar c9 = toASCIILower(string[9]);
- UChar c10 = toASCIILower(string[10]);
-
- CSSTransformValue::TransformOperationType transformType;
- unsigned expectedArgumentCount = 1;
- unsigned argumentStart = 11;
- if (c9 == 'x' && c10 == '(')
- transformType = CSSTransformValue::TranslateXTransformOperation;
- else if (c9 == 'y' && c10 == '(')
- transformType = CSSTransformValue::TranslateYTransformOperation;
- else if (c9 == 'z' && c10 == '(')
- transformType = CSSTransformValue::TranslateZTransformOperation;
- else if (c9 == '(') {
- transformType = CSSTransformValue::TranslateTransformOperation;
- expectedArgumentCount = 2;
- argumentStart = 10;
- } else if (c9 == '3' && c10 == 'd' && string[11] == '(') {
- transformType = CSSTransformValue::Translate3DTransformOperation;
- expectedArgumentCount = 3;
- argumentStart = 12;
- } else
- return false;
-
- RefPtr<CSSTransformValue> transformValue = CSSTransformValue::create(transformType);
- bool success;
- if (string.is8Bit())
- success = parseTransformTranslateArguments(transformValue.get(), string.characters8(), string.length(), argumentStart, expectedArgumentCount);
- else
- success = parseTransformTranslateArguments(transformValue.get(), string.characters16(), string.length(), argumentStart, expectedArgumentCount);
- if (!success)
- return false;
- RefPtr<CSSValueList> result = CSSValueList::createSpaceSeparated();
- result->append(transformValue.release());
- properties->addParsedProperty(CSSProperty(CSSPropertyWebkitTransform, result.release(), important));
- return true;
-}
-
-PassRefPtr<CSSValueList> CSSParser::parseFontFaceValue(const AtomicString& string)
-{
- if (string.isEmpty())
- return 0;
- RefPtr<MutableStylePropertySet> dummyStyle = MutableStylePropertySet::create();
- if (!parseValue(dummyStyle.get(), CSSPropertyFontFamily, string, false, HTMLQuirksMode, 0))
- return 0;
-
- RefPtr<CSSValue> fontFamily = dummyStyle->getPropertyCSSValue(CSSPropertyFontFamily);
- if (!fontFamily->isValueList())
- return 0;
-
- return toCSSValueList(dummyStyle->getPropertyCSSValue(CSSPropertyFontFamily).get());
-}
-
-bool CSSParser::parseValue(MutableStylePropertySet* declaration, CSSPropertyID propertyID, const String& string, bool important, const Document& document)
-{
- ASSERT(!string.isEmpty());
-
- CSSParserContext context(document);
-
- if (parseSimpleLengthValue(declaration, propertyID, string, important, context.mode()))
- return true;
- if (parseColorValue(declaration, propertyID, string, important, context.mode()))
- return true;
- if (parseKeywordValue(declaration, propertyID, string, important, context))
- return true;
-
- CSSParser parser(context, UseCounter::getFrom(&document));
- return parser.parseValue(declaration, propertyID, string, important, static_cast<StyleSheetContents*>(0));
-}
-
-bool CSSParser::parseValue(MutableStylePropertySet* declaration, CSSPropertyID propertyID, const String& string, bool important, CSSParserMode cssParserMode, StyleSheetContents* contextStyleSheet)
-{
- ASSERT(!string.isEmpty());
- if (parseSimpleLengthValue(declaration, propertyID, string, important, cssParserMode))
- return true;
- if (parseColorValue(declaration, propertyID, string, important, cssParserMode))
- return true;
-
- CSSParserContext context(cssParserMode);
- if (contextStyleSheet) {
- context = contextStyleSheet->parserContext();
- context.setMode(cssParserMode);
- }
-
- if (parseKeywordValue(declaration, propertyID, string, important, context))
- return true;
- if (parseTranslateTransformValue(declaration, propertyID, string, important))
- return true;
-
- CSSParser parser(context);
- return parser.parseValue(declaration, propertyID, string, important, contextStyleSheet);
-}
-
-bool CSSParser::parseValue(MutableStylePropertySet* declaration, CSSPropertyID propertyID, const String& string, bool important, StyleSheetContents* contextStyleSheet)
-{
- // FIXME: Check RuntimeCSSEnabled::isPropertyEnabled or isValueEnabledForProperty.
-
- if (m_useCounter)
- m_useCounter->count(m_context, propertyID);
-
- setStyleSheet(contextStyleSheet);
-
- setupParser("@-internal-value ", string, "");
-
- m_id = propertyID;
- m_important = important;
-
- {
- StyleDeclarationScope scope(this, declaration);
- cssyyparse(this);
- }
-
- m_rule = 0;
- m_id = CSSPropertyInvalid;
-
- bool ok = false;
- if (m_hasFontFaceOnlyValues)
- deleteFontFaceOnlyValues();
- if (!m_parsedProperties.isEmpty()) {
- ok = true;
- declaration->addParsedProperties(m_parsedProperties);
- clearProperties();
- }
-
- return ok;
-}
-
-// The color will only be changed when string contains a valid CSS color, so callers
-// can set it to a default color and ignore the boolean result.
-bool CSSParser::parseColor(RGBA32& color, const String& string, bool strict)
-{
- // First try creating a color specified by name, rgba(), rgb() or "#" syntax.
- if (fastParseColor(color, string, strict))
- return true;
-
- CSSParser parser(HTMLStandardMode);
-
- // In case the fast-path parser didn't understand the color, try the full parser.
- if (!parser.parseColor(string))
- return false;
-
- CSSValue* value = parser.m_parsedProperties.first().value();
- if (!value->isPrimitiveValue())
- return false;
-
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (!primitiveValue->isRGBColor())
- return false;
-
- color = primitiveValue->getRGBA32Value();
- return true;
-}
-
-bool CSSParser::parseColor(const String& string)
-{
- setupParser("@-internal-decls color:", string, "");
- cssyyparse(this);
- m_rule = 0;
-
- return !m_parsedProperties.isEmpty() && m_parsedProperties.first().id() == CSSPropertyColor;
-}
-
-bool CSSParser::parseSystemColor(RGBA32& color, const String& string, Document* document)
-{
- if (!document || !document->page())
- return false;
-
- CSSParserString cssColor;
- cssColor.init(string);
- CSSValueID id = cssValueKeywordID(cssColor);
- if (id <= 0)
- return false;
-
- color = RenderTheme::theme().systemColor(id).rgb();
- return true;
-}
-
-void CSSParser::parseSelector(const String& string, CSSSelectorList& selectorList)
-{
- m_selectorListForParseSelector = &selectorList;
-
- setupParser("@-internal-selector ", string, "");
-
- cssyyparse(this);
-
- m_selectorListForParseSelector = 0;
-}
-
-PassRefPtr<ImmutableStylePropertySet> CSSParser::parseInlineStyleDeclaration(const String& string, Element* element)
-{
- Document& document = element->document();
- CSSParserContext context = document.elementSheet()->contents()->parserContext();
- context.setMode((element->isHTMLElement() && !document.inQuirksMode()) ? HTMLStandardMode : HTMLQuirksMode);
- return CSSParser(context, UseCounter::getFrom(&document)).parseDeclaration(string, document.elementSheet()->contents());
-}
-
-PassRefPtr<ImmutableStylePropertySet> CSSParser::parseDeclaration(const String& string, StyleSheetContents* contextStyleSheet)
-{
- setStyleSheet(contextStyleSheet);
-
- setupParser("@-internal-decls ", string, "");
- cssyyparse(this);
- m_rule = 0;
-
- if (m_hasFontFaceOnlyValues)
- deleteFontFaceOnlyValues();
-
- RefPtr<ImmutableStylePropertySet> style = createStylePropertySet();
- clearProperties();
- return style.release();
-}
-
-
-bool CSSParser::parseDeclaration(MutableStylePropertySet* declaration, const String& string, SourceDataHandler* sourceDataHandler, StyleSheetContents* contextStyleSheet)
-{
- setStyleSheet(contextStyleSheet);
-
- m_sourceDataHandler = sourceDataHandler;
-
- setupParser("@-internal-decls ", string, "");
- if (m_sourceDataHandler) {
- m_sourceDataHandler->startRuleHeader(CSSRuleSourceData::STYLE_RULE, 0);
- m_sourceDataHandler->endRuleHeader(1);
- m_sourceDataHandler->startRuleBody(0);
- }
-
- {
- StyleDeclarationScope scope(this, declaration);
- cssyyparse(this);
- }
-
- m_rule = 0;
-
- bool ok = false;
- if (m_hasFontFaceOnlyValues)
- deleteFontFaceOnlyValues();
- if (!m_parsedProperties.isEmpty()) {
- ok = true;
- declaration->addParsedProperties(m_parsedProperties);
- clearProperties();
- }
-
- if (m_sourceDataHandler)
- m_sourceDataHandler->endRuleBody(string.length(), false);
- m_sourceDataHandler = 0;
-
- return ok;
-}
-
-PassRefPtr<MediaQuerySet> CSSParser::parseMediaQueryList(const String& string)
{
- ASSERT(!m_mediaList);
-
- // can't use { because tokenizer state switches from mediaquery to initial state when it sees { token.
- // instead insert one " " (which is caught by maybe_space in CSSGrammar.y)
- setupParser("@-internal-medialist ", string, "");
- cssyyparse(this);
-
- ASSERT(m_mediaList);
- return m_mediaList.release();
}
-static inline void filterProperties(bool important, const CSSParser::ParsedPropertyVector& input, Vector<CSSProperty, 256>& output, size_t& unusedEntries, BitArray<numCSSProperties>& seenProperties, HashSet<AtomicString>& seenVariables)
+CSSPropertyParser::~CSSPropertyParser()
{
- // Add properties in reverse order so that highest priority definitions are reached first. Duplicate definitions can then be ignored when found.
- for (int i = input.size() - 1; i >= 0; --i) {
- const CSSProperty& property = input[i];
- if (property.isImportant() != important)
- continue;
- if (property.id() == CSSPropertyVariable) {
- const AtomicString& name = toCSSVariableValue(property.value())->name();
- if (!seenVariables.add(name).isNewEntry)
- continue;
- output[--unusedEntries] = property;
- continue;
- }
- const unsigned propertyIDIndex = property.id() - firstCSSProperty;
- if (seenProperties.get(propertyIDIndex))
- continue;
- seenProperties.set(propertyIDIndex);
- output[--unusedEntries] = property;
- }
}
-PassRefPtr<ImmutableStylePropertySet> CSSParser::createStylePropertySet()
+void CSSPropertyParser::addPropertyWithPrefixingVariant(CSSPropertyID propId, PassRefPtrWillBeRawPtr<CSSValue> value, bool important, bool implicit)
{
- BitArray<numCSSProperties> seenProperties;
- size_t unusedEntries = m_parsedProperties.size();
- Vector<CSSProperty, 256> results(unusedEntries);
-
- // Important properties have higher priority, so add them first. Duplicate definitions can then be ignored when found.
- HashSet<AtomicString> seenVariables;
- filterProperties(true, m_parsedProperties, results, unusedEntries, seenProperties, seenVariables);
- filterProperties(false, m_parsedProperties, results, unusedEntries, seenProperties, seenVariables);
- if (unusedEntries)
- results.remove(0, unusedEntries);
-
- CSSParserMode mode = inViewport() ? CSSViewportRuleMode : m_context.mode();
-
- return ImmutableStylePropertySet::create(results.data(), results.size(), mode);
-}
-
-void CSSParser::addPropertyWithPrefixingVariant(CSSPropertyID propId, PassRefPtr<CSSValue> value, bool important, bool implicit)
-{
- RefPtr<CSSValue> val = value.get();
+ RefPtrWillBeRawPtr<CSSValue> val = value.get();
addProperty(propId, value, important, implicit);
CSSPropertyID prefixingVariant = prefixingVariantForPropertyId(propId);
@@ -1330,11 +158,10 @@ void CSSParser::addPropertyWithPrefixingVariant(CSSPropertyID propId, PassRefPtr
}
}
-void CSSParser::addProperty(CSSPropertyID propId, PassRefPtr<CSSValue> value, bool important, bool implicit)
+void CSSPropertyParser::addProperty(CSSPropertyID propId, PassRefPtrWillBeRawPtr<CSSValue> value, bool important, bool implicit)
{
- CSSPrimitiveValue* primitiveValue = value->isPrimitiveValue() ? toCSSPrimitiveValue(value.get()) : 0;
- // This property doesn't belong to a shorthand or is a CSS variable (which will be resolved later).
- if (!m_currentShorthand || (primitiveValue && primitiveValue->isVariableName())) {
+ // This property doesn't belong to a shorthand.
+ if (!m_currentShorthand) {
m_parsedProperties.append(CSSProperty(propId, value, important, false, CSSPropertyInvalid, m_implicitShorthand || implicit));
return;
}
@@ -1348,36 +175,19 @@ void CSSParser::addProperty(CSSPropertyID propId, PassRefPtr<CSSValue> value, bo
m_parsedProperties.append(CSSProperty(propId, value, important, true, indexOfShorthandForLonghand(m_currentShorthand, shorthands), m_implicitShorthand || implicit));
}
-void CSSParser::rollbackLastProperties(int num)
+void CSSPropertyParser::rollbackLastProperties(int num)
{
ASSERT(num >= 0);
ASSERT(m_parsedProperties.size() >= static_cast<unsigned>(num));
m_parsedProperties.shrink(m_parsedProperties.size() - num);
}
-void CSSParser::clearProperties()
-{
- m_parsedProperties.clear();
- m_numParsedPropertiesBeforeMarginBox = INVALID_NUM_PARSED_PROPERTIES;
- m_hasFontFaceOnlyValues = false;
-}
-
-// FIXME: Move to CSSParserContext?
-KURL CSSParser::completeURL(const CSSParserContext& context, const String& url)
-{
- if (url.isNull())
- return KURL();
- if (context.charset().isEmpty())
- return KURL(context.baseURL(), url);
- return KURL(context.baseURL(), url, context.charset());
-}
-
-KURL CSSParser::completeURL(const String& url) const
+KURL CSSPropertyParser::completeURL(const String& url) const
{
- return completeURL(m_context, url);
+ return m_context.completeURL(url);
}
-bool CSSParser::validCalculationUnit(CSSParserValue* value, Units unitflags, ReleaseParsedCalcValueCondition releaseCalc)
+bool CSSPropertyParser::validCalculationUnit(CSSParserValue* value, Units unitflags, ReleaseParsedCalcValueCondition releaseCalc)
{
bool mustBeNonNegative = unitflags & FNonNeg;
@@ -1407,9 +217,6 @@ bool CSSParser::validCalculationUnit(CSSParserValue* value, Units unitflags, Rel
case CalcPercentNumber:
b = (unitflags & FPercent) && (unitflags & FNumber);
break;
- case CalcVariable:
- b = true;
- break;
case CalcOther:
break;
}
@@ -1418,23 +225,19 @@ bool CSSParser::validCalculationUnit(CSSParserValue* value, Units unitflags, Rel
return b;
}
-inline bool CSSParser::shouldAcceptUnitLessValues(CSSParserValue* value, Units unitflags, CSSParserMode cssParserMode)
+inline bool CSSPropertyParser::shouldAcceptUnitLessValues(CSSParserValue* value, Units unitflags, CSSParserMode cssParserMode)
{
// Quirks mode and presentation attributes accept unit less values.
return (unitflags & (FLength | FAngle | FTime)) && (!value->fValue || isUnitLessLengthParsingEnabledForMode(cssParserMode));
}
-bool CSSParser::validUnit(CSSParserValue* value, Units unitflags, CSSParserMode cssParserMode, ReleaseParsedCalcValueCondition releaseCalc)
+bool CSSPropertyParser::validUnit(CSSParserValue* value, Units unitflags, CSSParserMode cssParserMode, ReleaseParsedCalcValueCondition releaseCalc)
{
if (isCalculation(value))
return validCalculationUnit(value, unitflags, releaseCalc);
bool b = false;
switch (value->unit) {
- case CSSPrimitiveValue::CSS_VARIABLE_NAME:
- // Variables are checked at the point they are dereferenced because unit type is not available here.
- b = true;
- break;
case CSSPrimitiveValue::CSS_NUMBER:
b = (unitflags & FNumber);
if (!b && shouldAcceptUnitLessValues(value, unitflags, cssParserMode)) {
@@ -1493,11 +296,8 @@ bool CSSParser::validUnit(CSSParserValue* value, Units unitflags, CSSParserMode
return b;
}
-inline PassRefPtr<CSSPrimitiveValue> CSSParser::createPrimitiveNumericValue(CSSParserValue* value)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::createPrimitiveNumericValue(CSSParserValue* value)
{
- if (value->unit == CSSPrimitiveValue::CSS_VARIABLE_NAME)
- return createPrimitiveVariableNameValue(value);
-
if (m_parsedCalculation) {
ASSERT(isCalculation(value));
return CSSPrimitiveValue::create(m_parsedCalculation.release());
@@ -1507,19 +307,20 @@ inline PassRefPtr<CSSPrimitiveValue> CSSParser::createPrimitiveNumericValue(CSSP
|| (value->unit >= CSSPrimitiveValue::CSS_TURN && value->unit <= CSSPrimitiveValue::CSS_CHS)
|| (value->unit >= CSSPrimitiveValue::CSS_VW && value->unit <= CSSPrimitiveValue::CSS_VMAX)
|| (value->unit >= CSSPrimitiveValue::CSS_DPPX && value->unit <= CSSPrimitiveValue::CSS_DPCM));
- return cssValuePool().createValue(value->fValue, static_cast<CSSPrimitiveValue::UnitTypes>(value->unit));
+ return cssValuePool().createValue(value->fValue, static_cast<CSSPrimitiveValue::UnitType>(value->unit));
}
-inline PassRefPtr<CSSPrimitiveValue> CSSParser::createPrimitiveStringValue(CSSParserValue* value)
+inline PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::createPrimitiveStringValue(CSSParserValue* value)
{
ASSERT(value->unit == CSSPrimitiveValue::CSS_STRING || value->unit == CSSPrimitiveValue::CSS_IDENT);
return cssValuePool().createValue(value->string, CSSPrimitiveValue::CSS_STRING);
}
-inline PassRefPtr<CSSPrimitiveValue> CSSParser::createPrimitiveVariableNameValue(CSSParserValue* value)
+inline PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::createCSSImageValueWithReferrer(const String& rawValue, const KURL& url)
{
- ASSERT(value->unit == CSSPrimitiveValue::CSS_VARIABLE_NAME);
- return CSSPrimitiveValue::create(value->string, CSSPrimitiveValue::CSS_VARIABLE_NAME);
+ RefPtrWillBeRawPtr<CSSValue> imageValue = CSSImageValue::create(rawValue, url);
+ toCSSImageValue(imageValue.get())->setReferrer(m_context.referrer());
+ return imageValue;
}
static inline bool isComma(CSSParserValue* value)
@@ -1551,7 +352,7 @@ static bool isGeneratedImageValue(CSSParserValue* val)
|| equalIgnoringCase(val->function->name, "-webkit-cross-fade(");
}
-bool CSSParser::validWidthOrHeight(CSSParserValue* value)
+bool CSSPropertyParser::validWidthOrHeight(CSSParserValue* value)
{
int id = value->id;
if (id == CSSValueIntrinsic || id == CSSValueMinIntrinsic || id == CSSValueWebkitMinContent || id == CSSValueWebkitMaxContent || id == CSSValueWebkitFillAvailable || id == CSSValueWebkitFitContent)
@@ -1559,7 +360,7 @@ bool CSSParser::validWidthOrHeight(CSSParserValue* value)
return !id && validUnit(value, FLength | FPercent | FNonNeg);
}
-inline PassRefPtr<CSSPrimitiveValue> CSSParser::parseValidPrimitive(CSSValueID identifier, CSSParserValue* value)
+inline PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::parseValidPrimitive(CSSValueID identifier, CSSParserValue* value)
{
if (identifier)
return cssValuePool().createIdentifierValue(identifier);
@@ -1573,45 +374,38 @@ inline PassRefPtr<CSSPrimitiveValue> CSSParser::parseValidPrimitive(CSSValueID i
return createPrimitiveNumericValue(value);
if (value->unit >= CSSPrimitiveValue::CSS_DPPX && value->unit <= CSSPrimitiveValue::CSS_DPCM)
return createPrimitiveNumericValue(value);
- if (value->unit == CSSPrimitiveValue::CSS_VARIABLE_NAME)
- return createPrimitiveVariableNameValue(value);
if (value->unit >= CSSParserValue::Q_EMS)
return CSSPrimitiveValue::createAllowingMarginQuirk(value->fValue, CSSPrimitiveValue::CSS_EMS);
if (isCalculation(value))
return CSSPrimitiveValue::create(m_parsedCalculation.release());
- return 0;
+ return nullptr;
}
-void CSSParser::addExpandedPropertyForValue(CSSPropertyID propId, PassRefPtr<CSSValue> prpValue, bool important)
+void CSSPropertyParser::addExpandedPropertyForValue(CSSPropertyID propId, PassRefPtrWillBeRawPtr<CSSValue> prpValue, bool important)
{
const StylePropertyShorthand& shorthand = shorthandForProperty(propId);
unsigned shorthandLength = shorthand.length();
if (!shorthandLength) {
- addProperty(propId, prpValue, important);
+ addPropertyWithPrefixingVariant(propId, prpValue, important);
return;
}
- RefPtr<CSSValue> value = prpValue;
+ RefPtrWillBeRawPtr<CSSValue> value = prpValue;
ShorthandScope scope(this, propId);
const CSSPropertyID* longhands = shorthand.properties();
for (unsigned i = 0; i < shorthandLength; ++i)
- addProperty(longhands[i], value, important);
-}
-
-void CSSParser::setCurrentProperty(CSSPropertyID propId)
-{
- m_id = propId;
+ addPropertyWithPrefixingVariant(longhands[i], value, important);
}
-bool CSSParser::parseValue(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseValue(CSSPropertyID propId, bool important)
{
if (!isInternalPropertyAndValueParsingEnabledForMode(m_context.mode()) && isInternalProperty(propId))
return false;
// We don't count the UA style sheet in our statistics.
- if (m_useCounter)
- m_useCounter->count(m_context, propId);
+ if (m_context.useCounter())
+ m_context.useCounter()->count(m_context, propId);
if (!m_valueList)
return false;
@@ -1650,13 +444,6 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
return true;
}
- if (!id && value->unit == CSSPrimitiveValue::CSS_VARIABLE_NAME && num == 1) {
- addProperty(propId, createPrimitiveVariableNameValue(value), important);
- m_valueList->next();
- return true;
- }
- ASSERT(propId != CSSPropertyVariable);
-
if (isKeywordPropertyID(propId)) {
if (!isValidKeywordPropertyAndValue(propId, id, m_context))
return false;
@@ -1667,7 +454,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
}
bool validPrimitive = false;
- RefPtr<CSSValue> parsedValue;
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = nullptr;
switch (propId) {
case CSSPropertySize: // <length>{1,2} | auto | [ <page-size> || [ portrait | landscape] ]
@@ -1708,7 +495,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
if (num != 1 || !parseValue(CSSPropertyOverflowY, important))
return false;
- RefPtr<CSSValue> overflowXValue;
+ RefPtrWillBeRawPtr<CSSValue> overflowXValue = nullptr;
// FIXME: -webkit-paged-x or -webkit-paged-y only apply to overflow-y. If this value has been
// set using the shorthand, then for now overflow-x will default to auto, but once we implement
@@ -1801,15 +588,15 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
// [ auto | crosshair | default | pointer | progress | move | e-resize | ne-resize |
// nw-resize | n-resize | se-resize | sw-resize | s-resize | w-resize | ew-resize |
// ns-resize | nesw-resize | nwse-resize | col-resize | row-resize | text | wait | help |
- // vertical-text | cell | context-menu | alias | copy | no-drop | not-allowed | -webkit-zoom-in
- // -webkit-zoom-out | all-scroll | -webkit-grab | -webkit-grabbing ] ] | inherit
- RefPtr<CSSValueList> list;
+ // vertical-text | cell | context-menu | alias | copy | no-drop | not-allowed | all-scroll |
+ // zoom-in | zoom-out | -webkit-grab | -webkit-grabbing | -webkit-zoom-in | -webkit-zoom-out ] ] | inherit
+ RefPtrWillBeRawPtr<CSSValueList> list = nullptr;
while (value) {
- RefPtr<CSSValue> image = 0;
+ RefPtrWillBeRawPtr<CSSValue> image = nullptr;
if (value->unit == CSSPrimitiveValue::CSS_URI) {
String uri = value->string;
if (!uri.isNull())
- image = CSSImageValue::create(completeURL(uri));
+ image = createCSSImageValueWithReferrer(uri, completeURL(uri));
} else if (value->unit == CSSParserValue::Function && equalIgnoringCase(value->function->name, "-webkit-image-set(")) {
image = parseImageSet(m_valueList.get());
if (!image)
@@ -1843,12 +630,18 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
return false;
value = m_valueList->next(); // comma
}
+ if (value && m_context.useCounter()) {
+ if (value->id == CSSValueWebkitZoomIn)
+ m_context.useCounter()->count(UseCounter::PrefixedCursorZoomIn);
+ else if (value->id == CSSValueWebkitZoomOut)
+ m_context.useCounter()->count(UseCounter::PrefixedCursorZoomOut);
+ }
if (list) {
if (!value)
return false;
if (inQuirksMode() && value->id == CSSValueHand) // MSIE 5 compatibility :/
list->append(cssValuePool().createIdentifierValue(CSSValuePointer));
- else if ((value->id >= CSSValueAuto && value->id <= CSSValueWebkitGrabbing) || value->id == CSSValueCopy || value->id == CSSValueNone)
+ else if ((value->id >= CSSValueAuto && value->id <= CSSValueWebkitZoomOut) || value->id == CSSValueCopy || value->id == CSSValueNone)
list->append(cssValuePool().createIdentifierValue(value->id));
m_valueList->next();
parsedValue = list.release();
@@ -1858,7 +651,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
if (inQuirksMode() && value->id == CSSValueHand) { // MSIE 5 compatibility :/
id = CSSValuePointer;
validPrimitive = true;
- } else if ((value->id >= CSSValueAuto && value->id <= CSSValueWebkitGrabbing) || value->id == CSSValueCopy || value->id == CSSValueNone)
+ } else if ((value->id >= CSSValueAuto && value->id <= CSSValueWebkitZoomOut) || value->id == CSSValueCopy || value->id == CSSValueNone)
validPrimitive = true;
} else {
ASSERT_NOT_REACHED();
@@ -1896,21 +689,24 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyWebkitMaskRepeatX:
case CSSPropertyWebkitMaskRepeatY:
{
- RefPtr<CSSValue> val1;
- RefPtr<CSSValue> val2;
+ RefPtrWillBeRawPtr<CSSValue> val1 = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> val2 = nullptr;
CSSPropertyID propId1, propId2;
bool result = false;
if (parseFillProperty(propId, propId1, propId2, val1, val2)) {
- OwnPtr<ShorthandScope> shorthandScope;
if (propId == CSSPropertyBackgroundPosition ||
propId == CSSPropertyBackgroundRepeat ||
propId == CSSPropertyWebkitMaskPosition ||
propId == CSSPropertyWebkitMaskRepeat) {
- shorthandScope = adoptPtr(new ShorthandScope(this, propId));
+ ShorthandScope scope(this, propId);
+ addProperty(propId1, val1.release(), important);
+ if (val2)
+ addProperty(propId2, val2.release(), important);
+ } else {
+ addProperty(propId1, val1.release(), important);
+ if (val2)
+ addProperty(propId2, val2.release(), important);
}
- addProperty(propId1, val1.release(), important);
- if (val2)
- addProperty(propId2, val2.release(), important);
result = true;
}
m_implicitShorthand = false;
@@ -1925,7 +721,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
parsedValue = cssValuePool().createIdentifierValue(CSSValueNone);
m_valueList->next();
} else if (value->unit == CSSPrimitiveValue::CSS_URI) {
- parsedValue = CSSImageValue::create(completeURL(value->string));
+ parsedValue = createCSSImageValueWithReferrer(value->string, completeURL(value->string));
m_valueList->next();
} else if (isGeneratedImageValue(value)) {
if (parseGeneratedImage(m_valueList.get(), parsedValue))
@@ -2036,17 +832,18 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
validPrimitive = (!id && validUnit(value, FLength | FPercent));
break;
- case CSSPropertyZIndex: // auto | <integer> | inherit
- if (id == CSSValueAuto) {
- validPrimitive = true;
- break;
- }
- /* nobreak */
case CSSPropertyOrphans: // <integer> | inherit | auto (We've added support for auto for backwards compatibility)
case CSSPropertyWidows: // <integer> | inherit | auto (Ditto)
if (id == CSSValueAuto)
validPrimitive = true;
else
+ validPrimitive = (!id && validUnit(value, FPositiveInteger, HTMLQuirksMode));
+ break;
+
+ case CSSPropertyZIndex: // auto | <integer> | inherit
+ if (id == CSSValueAuto)
+ validPrimitive = true;
+ else
validPrimitive = (!id && validUnit(value, FInteger, HTMLQuirksMode));
break;
@@ -2102,8 +899,6 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
break;
case CSSPropertySrc: // Only used within @font-face and @-webkit-filter, so cannot use inherit | initial or be !important. This is a list of urls or local references.
- if (m_inFilterRule)
- return parseFilterRuleSrc();
return parseFontFaceSrc();
case CSSPropertyUnicodeRange:
@@ -2115,7 +910,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyWebkitMaskBoxImage:
return parseBorderImageShorthand(propId, important);
case CSSPropertyWebkitBorderImage: {
- if (RefPtr<CSSValue> result = parseBorderImage(propId)) {
+ if (RefPtrWillBeRawPtr<CSSValue> result = parseBorderImage(propId)) {
addProperty(propId, result, important);
return true;
}
@@ -2124,7 +919,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyBorderImageOutset:
case CSSPropertyWebkitMaskBoxImageOutset: {
- RefPtr<CSSPrimitiveValue> result;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = nullptr;
if (parseBorderImageOutset(result)) {
addProperty(propId, result, important);
return true;
@@ -2133,7 +928,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
}
case CSSPropertyBorderImageRepeat:
case CSSPropertyWebkitMaskBoxImageRepeat: {
- RefPtr<CSSValue> result;
+ RefPtrWillBeRawPtr<CSSValue> result = nullptr;
if (parseBorderImageRepeat(result)) {
addProperty(propId, result, important);
return true;
@@ -2142,7 +937,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
}
case CSSPropertyBorderImageSlice:
case CSSPropertyWebkitMaskBoxImageSlice: {
- RefPtr<CSSBorderImageSliceValue> result;
+ RefPtrWillBeRawPtr<CSSBorderImageSliceValue> result = nullptr;
if (parseBorderImageSlice(propId, result)) {
addProperty(propId, result, important);
return true;
@@ -2151,7 +946,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
}
case CSSPropertyBorderImageWidth:
case CSSPropertyWebkitMaskBoxImageWidth: {
- RefPtr<CSSPrimitiveValue> result;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = nullptr;
if (parseBorderImageWidth(result)) {
addProperty(propId, result, important);
return true;
@@ -2167,8 +962,8 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
validPrimitive = validUnit(value, FLength | FPercent | FNonNeg);
if (!validPrimitive)
return false;
- RefPtr<CSSPrimitiveValue> parsedValue1 = createPrimitiveNumericValue(value);
- RefPtr<CSSPrimitiveValue> parsedValue2;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue1 = createPrimitiveNumericValue(value);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue2 = nullptr;
if (num == 2) {
value = m_valueList->next();
validPrimitive = validUnit(value, FLength | FPercent | FNonNeg);
@@ -2198,7 +993,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
if (id == CSSValueNone)
validPrimitive = true;
else {
- RefPtr<CSSValueList> shadowValueList = parseShadow(m_valueList.get(), propId);
+ RefPtrWillBeRawPtr<CSSValueList> shadowValueList = parseShadow(m_valueList.get(), propId);
if (shadowValueList) {
addProperty(propId, shadowValueList.release(), important);
m_valueList->next();
@@ -2229,7 +1024,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
if (id == CSSValueNone)
validPrimitive = true;
else {
- RefPtr<CSSValue> val = parseFilter();
+ RefPtrWillBeRawPtr<CSSValue> val = parseFilter();
if (val) {
addProperty(propId, val, important);
return true;
@@ -2259,16 +1054,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
validPrimitive = validUnit(value, FNumber | FNonNeg);
break;
case CSSPropertyOrder:
- if (validUnit(value, FInteger, HTMLStandardMode)) {
- if (value->unit != CSSPrimitiveValue::CSS_VARIABLE_NAME) {
- // We restrict the smallest value to int min + 2 because we use int min and int min + 1 as special values in a hash set.
- parsedValue = cssValuePool().createValue(max(static_cast<double>(std::numeric_limits<int>::min() + 2), value->fValue),
- static_cast<CSSPrimitiveValue::UnitTypes>(value->unit));
- m_valueList->next();
- } else {
- validPrimitive = true;
- }
- }
+ validPrimitive = validUnit(value, FInteger, HTMLStandardMode);
break;
case CSSPropertyInternalMarqueeIncrement:
if (id == CSSValueSmall || id == CSSValueLarge || id == CSSValueMedium)
@@ -2288,19 +1074,12 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
else
validPrimitive = validUnit(value, FTime | FInteger | FNonNeg);
break;
- case CSSPropertyWebkitFlowInto:
- if (!RuntimeEnabledFeatures::cssRegionsEnabled())
- return false;
- return parseFlowThread(propId, important);
- case CSSPropertyWebkitFlowFrom:
- if (!RuntimeEnabledFeatures::cssRegionsEnabled())
- return false;
- return parseRegionThread(propId, important);
+ case CSSPropertyTransform:
case CSSPropertyWebkitTransform:
if (id == CSSValueNone)
validPrimitive = true;
else {
- RefPtr<CSSValue> transformValue = parseTransform();
+ RefPtrWillBeRawPtr<CSSValue> transformValue = parseTransform(propId);
if (transformValue) {
addProperty(propId, transformValue.release(), important);
return true;
@@ -2308,15 +1087,27 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
return false;
}
break;
+ case CSSPropertyTransformOrigin: {
+ RefPtrWillBeRawPtr<CSSValueList> list = parseTransformOrigin();
+ if (!list)
+ return false;
+ // These values are added to match gecko serialization.
+ if (list->length() == 1)
+ list->append(cssValuePool().createValue(50, CSSPrimitiveValue::CSS_PERCENTAGE));
+ if (list->length() == 2)
+ list->append(cssValuePool().createValue(0, CSSPrimitiveValue::CSS_PX));
+ addProperty(propId, list.release(), important);
+ return true;
+ }
case CSSPropertyWebkitTransformOrigin:
case CSSPropertyWebkitTransformOriginX:
case CSSPropertyWebkitTransformOriginY:
case CSSPropertyWebkitTransformOriginZ: {
- RefPtr<CSSValue> val1;
- RefPtr<CSSValue> val2;
- RefPtr<CSSValue> val3;
+ RefPtrWillBeRawPtr<CSSValue> val1 = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> val2 = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> val3 = nullptr;
CSSPropertyID propId1, propId2, propId3;
- if (parseTransformOrigin(propId, propId1, propId2, propId3, val1, val2, val3)) {
+ if (parseWebkitTransformOrigin(propId, propId1, propId2, propId3, val1, val2, val3)) {
addProperty(propId1, val1.release(), important);
if (val2)
addProperty(propId2, val2.release(), important);
@@ -2326,28 +1117,40 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
}
return false;
}
+ case CSSPropertyPerspective:
+ if (id == CSSValueNone) {
+ validPrimitive = true;
+ } else if (validUnit(value, FLength | FNonNeg)) {
+ addProperty(propId, createPrimitiveNumericValue(value), important);
+ return true;
+ }
+ break;
case CSSPropertyWebkitPerspective:
- if (id == CSSValueNone)
+ if (id == CSSValueNone) {
validPrimitive = true;
- else {
+ } else if (validUnit(value, FNumber | FLength | FNonNeg)) {
// Accepting valueless numbers is a quirk of the -webkit prefixed version of the property.
- if (validUnit(value, FNumber | FLength | FNonNeg)) {
- RefPtr<CSSValue> val = createPrimitiveNumericValue(value);
- if (val) {
- addProperty(propId, val.release(), important);
- return true;
- }
- return false;
- }
+ addProperty(propId, createPrimitiveNumericValue(value), important);
+ return true;
}
break;
+ case CSSPropertyPerspectiveOrigin: {
+ RefPtrWillBeRawPtr<CSSValueList> list = parseTransformOrigin();
+ if (!list || list->length() == 3)
+ return false;
+ // This values are added to match gecko serialization.
+ if (list->length() == 1)
+ list->append(cssValuePool().createValue(50, CSSPrimitiveValue::CSS_PERCENTAGE));
+ addProperty(propId, list.release(), important);
+ return true;
+ }
case CSSPropertyWebkitPerspectiveOrigin:
case CSSPropertyWebkitPerspectiveOriginX:
case CSSPropertyWebkitPerspectiveOriginY: {
- RefPtr<CSSValue> val1;
- RefPtr<CSSValue> val2;
+ RefPtrWillBeRawPtr<CSSValue> val1 = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> val2 = nullptr;
CSSPropertyID propId1, propId2;
- if (parsePerspectiveOrigin(propId, propId1, propId2, val1, val2)) {
+ if (parseWebkitPerspectiveOrigin(propId, propId1, propId2, val1, val2)) {
addProperty(propId1, val1.release(), important);
if (val2)
addProperty(propId2, val2.release(), important);
@@ -2381,15 +1184,18 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyWebkitTransitionDuration:
case CSSPropertyWebkitTransitionTimingFunction:
case CSSPropertyWebkitTransitionProperty: {
- RefPtr<CSSValue> val;
- AnimationParseContext context;
- if (parseAnimationProperty(propId, val, context)) {
+ if (RefPtrWillBeRawPtr<CSSValueList> val = parseAnimationPropertyList(propId)) {
addPropertyWithPrefixingVariant(propId, val.release(), important);
return true;
}
return false;
}
+ case CSSPropertyJustifySelf:
+ if (!RuntimeEnabledFeatures::cssGridLayoutEnabled())
+ return false;
+
+ return parseItemPositionOverflowPosition(propId, important);
case CSSPropertyGridAutoColumns:
case CSSPropertyGridAutoRows:
if (!RuntimeEnabledFeatures::cssGridLayoutEnabled())
@@ -2397,11 +1203,12 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
parsedValue = parseGridTrackSize(*m_valueList);
break;
- case CSSPropertyGridDefinitionColumns:
- case CSSPropertyGridDefinitionRows:
+ case CSSPropertyGridTemplateColumns:
+ case CSSPropertyGridTemplateRows:
if (!RuntimeEnabledFeatures::cssGridLayoutEnabled())
return false;
- return parseGridTrackList(propId, important);
+ parsedValue = parseGridTrackList(important);
+ break;
case CSSPropertyGridColumnEnd:
case CSSPropertyGridColumnStart:
@@ -2423,12 +1230,22 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
return false;
return parseGridAreaShorthand(important);
- case CSSPropertyGridTemplate:
+ case CSSPropertyGridTemplateAreas:
if (!RuntimeEnabledFeatures::cssGridLayoutEnabled())
return false;
- parsedValue = parseGridTemplate();
+ parsedValue = parseGridTemplateAreas();
break;
+ case CSSPropertyGridTemplate:
+ if (!RuntimeEnabledFeatures::cssGridLayoutEnabled())
+ return false;
+ return parseGridTemplateShorthand(important);
+
+ case CSSPropertyGrid:
+ if (!RuntimeEnabledFeatures::cssGridLayoutEnabled())
+ return false;
+ return parseGridShorthand(important);
+
case CSSPropertyWebkitMarginCollapse: {
if (num == 1) {
ShorthandScope scope(this, CSSPropertyWebkitMarginCollapse);
@@ -2464,14 +1281,6 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
else
validPrimitive = validUnit(value, FLength | FNonNeg);
break;
- case CSSPropertyWebkitColumnAxis:
- if (id == CSSValueHorizontal || id == CSSValueVertical || id == CSSValueAuto)
- validPrimitive = true;
- break;
- case CSSPropertyWebkitColumnProgression:
- if (id == CSSValueNormal || id == CSSValueReverse)
- validPrimitive = true;
- break;
case CSSPropertyWebkitColumnSpan: // none | all | 1 (will be dropped in the unprefixed property)
if (id == CSSValueAll || id == CSSValueNone)
validPrimitive = true;
@@ -2481,6 +1290,10 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyWebkitColumnWidth: // auto | <length>
parsedValue = parseColumnWidth();
break;
+ case CSSPropertyWillChange:
+ if (!RuntimeEnabledFeatures::cssWillChangeEnabled())
+ return false;
+ return parseWillChange(important);
// End of CSS3 properties
// Apple specific properties. These will never be standardized and are purely to
@@ -2505,17 +1318,6 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
validPrimitive = true;
break;
- case CSSPropertyWebkitLineGrid:
- if (id == CSSValueNone)
- validPrimitive = true;
- else if (value->unit == CSSPrimitiveValue::CSS_IDENT) {
- String lineGridValue = String(value->string);
- if (!lineGridValue.isEmpty()) {
- addProperty(propId, cssValuePool().createValue(lineGridValue, CSSPrimitiveValue::CSS_STRING), important);
- return true;
- }
- }
- break;
case CSSPropertyWebkitLocale:
if (id == CSSValueAuto || value->unit == CSSPrimitiveValue::CSS_STRING)
validPrimitive = true;
@@ -2660,7 +1462,7 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
return parseFontFeatureSettings(important);
break;
- case CSSPropertyWebkitFontVariantLigatures:
+ case CSSPropertyFontVariantLigatures:
if (id == CSSValueNormal)
validPrimitive = true;
else
@@ -2670,42 +1472,35 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
if (id == CSSValueNone) {
validPrimitive = true;
} else if (value->unit == CSSParserValue::Function) {
- return parseBasicShape(propId, important);
+ parsedValue = parseBasicShape();
} else if (value->unit == CSSPrimitiveValue::CSS_URI) {
parsedValue = CSSPrimitiveValue::create(value->string, CSSPrimitiveValue::CSS_URI);
addProperty(propId, parsedValue.release(), important);
return true;
}
break;
- case CSSPropertyShapeInside:
case CSSPropertyShapeOutside:
- if (!RuntimeEnabledFeatures::cssShapesEnabled())
- return false;
- if (id == CSSValueAuto)
- validPrimitive = true;
- else if (id == CSSValueContentBox || id == CSSValuePaddingBox || id == CSSValueBorderBox || id == CSSValueMarginBox)
- validPrimitive = true;
- else if (propId == CSSPropertyShapeInside && id == CSSValueOutsideShape)
- validPrimitive = true;
- else if (value->unit == CSSParserValue::Function)
- return parseBasicShape(propId, important);
- else if (value->unit == CSSPrimitiveValue::CSS_URI) {
- parsedValue = CSSImageValue::create(completeURL(value->string));
- m_valueList->next();
- }
+ parsedValue = parseShapeProperty(propId);
break;
case CSSPropertyShapeMargin:
- case CSSPropertyShapePadding:
- validPrimitive = (RuntimeEnabledFeatures::cssShapesEnabled() && !id && validUnit(value, FLength | FNonNeg));
+ validPrimitive = (RuntimeEnabledFeatures::cssShapesEnabled() && !id && validUnit(value, FLength | FPercent | FNonNeg));
break;
case CSSPropertyShapeImageThreshold:
validPrimitive = (RuntimeEnabledFeatures::cssShapesEnabled() && !id && validUnit(value, FNumber));
break;
case CSSPropertyTouchAction:
- // auto | none | [pan-x || pan-y]
+ // auto | none | [pan-x || pan-y] | manipulation
return parseTouchAction(important);
+ case CSSPropertyAlignSelf:
+ ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
+ return parseItemPositionOverflowPosition(propId, important);
+
+ case CSSPropertyAlignItems:
+ ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
+ return parseItemPositionOverflowPosition(propId, important);
+
case CSSPropertyBorderBottomStyle:
case CSSPropertyBorderCollapse:
case CSSPropertyBorderLeftStyle:
@@ -2747,9 +1542,9 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyTextUnderlineMode:
case CSSPropertyTextUnderlineStyle:
case CSSPropertyTouchActionDelay:
- case CSSPropertyVariable:
case CSSPropertyVisibility:
case CSSPropertyWebkitAppearance:
+ case CSSPropertyBackfaceVisibility:
case CSSPropertyWebkitBackfaceVisibility:
case CSSPropertyWebkitBorderAfterStyle:
case CSSPropertyWebkitBorderBeforeStyle:
@@ -2769,17 +1564,13 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyColumnFill:
case CSSPropertyWebkitColumnRuleStyle:
case CSSPropertyAlignContent:
- case CSSPropertyAlignItems:
- case CSSPropertyAlignSelf:
case CSSPropertyFlexDirection:
case CSSPropertyFlexWrap:
case CSSPropertyJustifyContent:
case CSSPropertyFontKerning:
case CSSPropertyWebkitFontSmoothing:
case CSSPropertyGridAutoFlow:
- case CSSPropertyWebkitLineAlign:
case CSSPropertyWebkitLineBreak:
- case CSSPropertyWebkitLineSnap:
case CSSPropertyWebkitMarginAfterCollapse:
case CSSPropertyWebkitMarginBeforeCollapse:
case CSSPropertyWebkitMarginBottomCollapse:
@@ -2787,15 +1578,12 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyInternalMarqueeDirection:
case CSSPropertyInternalMarqueeStyle:
case CSSPropertyWebkitPrintColorAdjust:
- case CSSPropertyWebkitRegionBreakAfter:
- case CSSPropertyWebkitRegionBreakBefore:
- case CSSPropertyWebkitRegionBreakInside:
- case CSSPropertyWebkitRegionFragment:
case CSSPropertyWebkitRtlOrdering:
case CSSPropertyWebkitRubyPosition:
case CSSPropertyWebkitTextCombine:
case CSSPropertyWebkitTextEmphasisPosition:
case CSSPropertyWebkitTextSecurity:
+ case CSSPropertyTransformStyle:
case CSSPropertyWebkitTransformStyle:
case CSSPropertyWebkitUserDrag:
case CSSPropertyWebkitUserModify:
@@ -2820,6 +1608,14 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
case CSSPropertyUserZoom:
validPrimitive = false;
break;
+
+ case CSSPropertyAll:
+ if (id == CSSValueInitial || id == CSSValueInherit || id == CSSValueUnset) {
+ validPrimitive = true;
+ break;
+ }
+ return false;
+
default:
return parseSVGValue(propId, important);
}
@@ -2838,14 +1634,14 @@ bool CSSParser::parseValue(CSSPropertyID propId, bool important)
return false;
}
-void CSSParser::addFillValue(RefPtr<CSSValue>& lval, PassRefPtr<CSSValue> rval)
+void CSSPropertyParser::addFillValue(RefPtrWillBeRawPtr<CSSValue>& lval, PassRefPtrWillBeRawPtr<CSSValue> rval)
{
if (lval) {
if (lval->isBaseValueList())
toCSSValueList(lval.get())->append(rval);
else {
- PassRefPtr<CSSValue> oldlVal(lval.release());
- PassRefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ PassRefPtrWillBeRawPtr<CSSValue> oldlVal(lval.release());
+ PassRefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
list->append(oldlVal);
list->append(rval);
lval = list;
@@ -2855,7 +1651,7 @@ void CSSParser::addFillValue(RefPtr<CSSValue>& lval, PassRefPtr<CSSValue> rval)
lval = rval;
}
-static bool parseBackgroundClip(CSSParserValue* parserValue, RefPtr<CSSValue>& cssValue)
+static bool parseBackgroundClip(CSSParserValue* parserValue, RefPtrWillBeRawPtr<CSSValue>& cssValue)
{
if (parserValue->id == CSSValueBorderBox || parserValue->id == CSSValuePaddingBox
|| parserValue->id == CSSValueContentBox || parserValue->id == CSSValueWebkitText) {
@@ -2865,14 +1661,9 @@ static bool parseBackgroundClip(CSSParserValue* parserValue, RefPtr<CSSValue>& c
return false;
}
-bool CSSParser::useLegacyBackgroundSizeShorthandBehavior() const
-{
- return m_context.useLegacyBackgroundSizeShorthandBehavior();
-}
-
const int cMaxFillProperties = 9;
-bool CSSParser::parseFillShorthand(CSSPropertyID propId, const CSSPropertyID* properties, int numProperties, bool important)
+bool CSSPropertyParser::parseFillShorthand(CSSPropertyID propId, const CSSPropertyID* properties, int numProperties, bool important)
{
ASSERT(numProperties <= cMaxFillProperties);
if (numProperties > cMaxFillProperties)
@@ -2881,10 +1672,14 @@ bool CSSParser::parseFillShorthand(CSSPropertyID propId, const CSSPropertyID* pr
ShorthandScope scope(this, propId);
bool parsedProperty[cMaxFillProperties] = { false };
- RefPtr<CSSValue> values[cMaxFillProperties];
- RefPtr<CSSValue> clipValue;
- RefPtr<CSSValue> positionYValue;
- RefPtr<CSSValue> repeatYValue;
+ RefPtrWillBeRawPtr<CSSValue> values[cMaxFillProperties];
+#if ENABLE(OILPAN)
+ // Zero initialize the array of raw pointers.
+ memset(&values, 0, sizeof(values));
+#endif
+ RefPtrWillBeRawPtr<CSSValue> clipValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> positionYValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> repeatYValue = nullptr;
bool foundClip = false;
int i;
bool foundPositionCSSProperty = false;
@@ -2933,8 +1728,8 @@ bool CSSParser::parseFillShorthand(CSSPropertyID propId, const CSSPropertyID* pr
continue;
if (!parsedProperty[i]) {
- RefPtr<CSSValue> val1;
- RefPtr<CSSValue> val2;
+ RefPtrWillBeRawPtr<CSSValue> val1 = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> val2 = nullptr;
CSSPropertyID propId1, propId2;
CSSParserValue* parserValue = m_valueList->current();
// parseFillProperty() may modify m_implicitShorthand, so we MUST reset it
@@ -3005,7 +1800,7 @@ bool CSSParser::parseFillShorthand(CSSPropertyID propId, const CSSPropertyID* pr
} else if ((properties[i] == CSSPropertyBackgroundClip || properties[i] == CSSPropertyWebkitMaskClip) && !foundClip)
// Value is already set while updating origin
continue;
- else if (properties[i] == CSSPropertyBackgroundSize && !parsedProperty[i] && useLegacyBackgroundSizeShorthandBehavior())
+ else if (properties[i] == CSSPropertyBackgroundSize && !parsedProperty[i] && m_context.useLegacyBackgroundSizeShorthandBehavior())
continue;
else
addProperty(properties[i], values[i].release(), important);
@@ -3021,48 +1816,22 @@ bool CSSParser::parseFillShorthand(CSSPropertyID propId, const CSSPropertyID* pr
return true;
}
-void CSSParser::storeVariableDeclaration(const CSSParserString& name, PassOwnPtr<CSSParserValueList> value, bool important)
-{
- // When CSSGrammar.y encounters an invalid declaration it passes null for the CSSParserValueList, just bail.
- if (!value)
- return;
-
- static const unsigned prefixLength = sizeof("var-") - 1;
-
- ASSERT(name.length() > prefixLength);
- AtomicString variableName = name.atomicSubstring(prefixLength, name.length() - prefixLength);
-
- StringBuilder builder;
- for (unsigned i = 0, size = value->size(); i < size; i++) {
- if (i)
- builder.append(' ');
- RefPtr<CSSValue> cssValue = value->valueAt(i)->createCSSValue();
- if (!cssValue)
- return;
- builder.append(cssValue->cssText());
- }
-
- addProperty(CSSPropertyVariable, CSSVariableValue::create(variableName, builder.toString()), important, false);
-}
-
-void CSSParser::addAnimationValue(RefPtr<CSSValue>& lval, PassRefPtr<CSSValue> rval)
+static bool isValidTransitionPropertyList(CSSValueList* value)
{
- if (lval) {
- if (lval->isValueList())
- toCSSValueList(lval.get())->append(rval);
- else {
- PassRefPtr<CSSValue> oldVal(lval.release());
- PassRefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- list->append(oldVal);
- list->append(rval);
- lval = list;
- }
+ if (value->length() < 2)
+ return true;
+ for (CSSValueListIterator i = value; i.hasMore(); i.advance()) {
+ // FIXME: Shorthand parsing shouldn't add initial to the list since it won't round-trip
+ if (i.value()->isInitialValue())
+ continue;
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(i.value());
+ if (primitiveValue->isValueID() && primitiveValue->getValueID() == CSSValueNone)
+ return false;
}
- else
- lval = rval;
+ return true;
}
-bool CSSParser::parseAnimationShorthand(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseAnimationShorthand(CSSPropertyID propId, bool important)
{
const StylePropertyShorthand& animationProperties = parsingShorthandForProperty(propId);
const unsigned numProperties = 8;
@@ -3076,34 +1845,32 @@ bool CSSParser::parseAnimationShorthand(CSSPropertyID propId, bool important)
ShorthandScope scope(this, propId);
bool parsedProperty[numProperties] = { false };
- AnimationParseContext context;
- RefPtr<CSSValue> values[numProperties];
+ RefPtrWillBeRawPtr<CSSValueList> values[numProperties];
+ for (size_t i = 0; i < numProperties; ++i)
+ values[i] = CSSValueList::createCommaSeparated();
- unsigned i;
while (m_valueList->current()) {
CSSParserValue* val = m_valueList->current();
if (val->unit == CSSParserValue::Operator && val->iValue == ',') {
- // We hit the end. Fill in all remaining values with the initial value.
+ // We hit the end. Fill in all remaining values with the initial value.
m_valueList->next();
- for (i = 0; i < numProperties; ++i) {
+ for (size_t i = 0; i < numProperties; ++i) {
if (!parsedProperty[i])
- addAnimationValue(values[i], cssValuePool().createImplicitInitialValue());
+ values[i]->append(cssValuePool().createImplicitInitialValue());
parsedProperty[i] = false;
}
if (!m_valueList->current())
break;
- context.commitFirstAnimation();
}
bool found = false;
- for (i = 0; i < numProperties; ++i) {
- if (!parsedProperty[i]) {
- RefPtr<CSSValue> val;
- if (parseAnimationProperty(animationProperties.properties()[i], val, context)) {
- parsedProperty[i] = found = true;
- addAnimationValue(values[i], val.release());
- break;
- }
+ for (size_t i = 0; i < numProperties; ++i) {
+ if (parsedProperty[i])
+ continue;
+ if (RefPtrWillBeRawPtr<CSSValue> val = parseAnimationProperty(animationProperties.properties()[i])) {
+ parsedProperty[i] = found = true;
+ values[i]->append(val.release());
+ break;
}
}
@@ -3113,57 +1880,55 @@ bool CSSParser::parseAnimationShorthand(CSSPropertyID propId, bool important)
return false;
}
- for (i = 0; i < numProperties; ++i) {
+ for (size_t i = 0; i < numProperties; ++i) {
// If we didn't find the property, set an intial value.
if (!parsedProperty[i])
- addAnimationValue(values[i], cssValuePool().createImplicitInitialValue());
+ values[i]->append(cssValuePool().createImplicitInitialValue());
- addProperty(animationProperties.properties()[i], values[i].release(), important);
+ if (RuntimeEnabledFeatures::cssAnimationUnprefixedEnabled())
+ addPropertyWithPrefixingVariant(animationProperties.properties()[i], values[i].release(), important);
+ else
+ addProperty(animationProperties.properties()[i], values[i].release(), important);
}
return true;
}
-bool CSSParser::parseTransitionShorthand(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseTransitionShorthand(CSSPropertyID propId, bool important)
{
const unsigned numProperties = 4;
- const StylePropertyShorthand& shorthand = shorthandForProperty(propId);
+ const StylePropertyShorthand& shorthand = parsingShorthandForProperty(propId);
ASSERT(numProperties == shorthand.length());
ShorthandScope scope(this, propId);
bool parsedProperty[numProperties] = { false };
- AnimationParseContext context;
- RefPtr<CSSValue> values[numProperties];
+ RefPtrWillBeRawPtr<CSSValueList> values[numProperties];
+ for (size_t i = 0; i < numProperties; ++i)
+ values[i] = CSSValueList::createCommaSeparated();
- unsigned i;
while (m_valueList->current()) {
CSSParserValue* val = m_valueList->current();
if (val->unit == CSSParserValue::Operator && val->iValue == ',') {
// We hit the end. Fill in all remaining values with the initial value.
m_valueList->next();
- for (i = 0; i < numProperties; ++i) {
+ for (size_t i = 0; i < numProperties; ++i) {
if (!parsedProperty[i])
- addAnimationValue(values[i], cssValuePool().createImplicitInitialValue());
+ values[i]->append(cssValuePool().createImplicitInitialValue());
parsedProperty[i] = false;
}
if (!m_valueList->current())
break;
- context.commitFirstAnimation();
}
bool found = false;
- for (i = 0; !found && i < numProperties; ++i) {
- if (!parsedProperty[i]) {
- RefPtr<CSSValue> val;
- if (parseAnimationProperty(shorthand.properties()[i], val, context)) {
- parsedProperty[i] = found = true;
- addAnimationValue(values[i], val.release());
- }
-
- // There are more values to process but 'none' or 'all' were already defined as the animation property, the declaration becomes invalid.
- if (!context.animationPropertyKeywordAllowed() && context.hasCommittedFirstAnimation())
- return false;
+ for (size_t i = 0; i < numProperties; ++i) {
+ if (parsedProperty[i])
+ continue;
+ if (RefPtrWillBeRawPtr<CSSValue> val = parseAnimationProperty(shorthand.properties()[i])) {
+ parsedProperty[i] = found = true;
+ values[i]->append(val.release());
+ break;
}
}
@@ -3173,49 +1938,50 @@ bool CSSParser::parseTransitionShorthand(CSSPropertyID propId, bool important)
return false;
}
- // Fill in any remaining properties with the initial value.
- for (i = 0; i < numProperties; ++i) {
- if (!parsedProperty[i])
- addAnimationValue(values[i], cssValuePool().createImplicitInitialValue());
- }
+ ASSERT(shorthand.properties()[3] == CSSPropertyTransitionProperty || shorthand.properties()[3] == CSSPropertyWebkitTransitionProperty);
+ if (!isValidTransitionPropertyList(values[3].get()))
+ return false;
- // Now add all of the properties we found.
- for (i = 0; i < numProperties; i++)
+ // Fill in any remaining properties with the initial value and add
+ for (size_t i = 0; i < numProperties; ++i) {
+ if (!parsedProperty[i])
+ values[i]->append(cssValuePool().createImplicitInitialValue());
addPropertyWithPrefixingVariant(shorthand.properties()[i], values[i].release(), important);
+ }
return true;
}
-PassRefPtr<CSSValue> CSSParser::parseColumnWidth()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseColumnWidth()
{
CSSParserValue* value = m_valueList->current();
// Always parse lengths in strict mode here, since it would be ambiguous otherwise when used in
// the 'columns' shorthand property.
if (value->id == CSSValueAuto
|| (validUnit(value, FLength | FNonNeg, HTMLStandardMode) && value->fValue)) {
- RefPtr<CSSValue> parsedValue = parseValidPrimitive(value->id, value);
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = parseValidPrimitive(value->id, value);
m_valueList->next();
return parsedValue;
}
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseColumnCount()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseColumnCount()
{
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueAuto
|| (!value->id && validUnit(value, FPositiveInteger, HTMLQuirksMode))) {
- RefPtr<CSSValue> parsedValue = parseValidPrimitive(value->id, value);
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = parseValidPrimitive(value->id, value);
m_valueList->next();
return parsedValue;
}
- return 0;
+ return nullptr;
}
-bool CSSParser::parseColumnsShorthand(bool important)
+bool CSSPropertyParser::parseColumnsShorthand(bool important)
{
- RefPtr <CSSValue> columnWidth;
- RefPtr <CSSValue> columnCount;
+ RefPtrWillBeRawPtr<CSSValue> columnWidth = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> columnCount = nullptr;
bool hasPendingExplicitAuto = false;
for (unsigned propertiesParsed = 0; CSSParserValue* value = m_valueList->current(); propertiesParsed++) {
@@ -3267,7 +2033,7 @@ bool CSSParser::parseColumnsShorthand(bool important)
return true;
}
-bool CSSParser::parseShorthand(CSSPropertyID propId, const StylePropertyShorthand& shorthand, bool important)
+bool CSSPropertyParser::parseShorthand(CSSPropertyID propId, const StylePropertyShorthand& shorthand, bool important)
{
// We try to match as many properties as possible
// We set up an array of booleans to mark which property has been found,
@@ -3276,14 +2042,14 @@ bool CSSParser::parseShorthand(CSSPropertyID propId, const StylePropertyShorthan
bool found = false;
unsigned propertiesParsed = 0;
- bool propertyFound[6]= { false, false, false, false, false, false }; // 6 is enough size.
+ bool propertyFound[6] = { false, false, false, false, false, false }; // 6 is enough size.
while (m_valueList->current()) {
found = false;
for (unsigned propIndex = 0; !found && propIndex < shorthand.length(); ++propIndex) {
if (!propertyFound[propIndex] && parseValue(shorthand.properties()[propIndex], important)) {
- propertyFound[propIndex] = found = true;
- propertiesParsed++;
+ propertyFound[propIndex] = found = true;
+ propertiesParsed++;
}
}
@@ -3314,7 +2080,7 @@ bool CSSParser::parseShorthand(CSSPropertyID propId, const StylePropertyShorthan
return true;
}
-bool CSSParser::parse4Values(CSSPropertyID propId, const CSSPropertyID *properties, bool important)
+bool CSSPropertyParser::parse4Values(CSSPropertyID propId, const CSSPropertyID *properties, bool important)
{
/* From the CSS 2 specs, 8.3
* If there is only one value, it applies to all sides. If there are two values, the top and
@@ -3373,7 +2139,7 @@ bool CSSParser::parse4Values(CSSPropertyID propId, const CSSPropertyID *properti
}
// auto | <identifier>
-bool CSSParser::parsePage(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parsePage(CSSPropertyID propId, bool important)
{
ASSERT(propId == CSSPropertyPage);
@@ -3395,7 +2161,7 @@ bool CSSParser::parsePage(CSSPropertyID propId, bool important)
}
// <length>{1,2} | auto | [ <page-size> || [ portrait | landscape] ]
-bool CSSParser::parseSize(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseSize(CSSPropertyID propId, bool important)
{
ASSERT(propId == CSSPropertySize);
@@ -3406,7 +2172,7 @@ bool CSSParser::parseSize(CSSPropertyID propId, bool important)
if (!value)
return false;
- RefPtr<CSSValueList> parsedValues = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> parsedValues = CSSValueList::createSpaceSeparated();
// First parameter.
SizeParameterType paramType = parseSizeParameter(parsedValues.get(), value, None);
@@ -3425,7 +2191,7 @@ bool CSSParser::parseSize(CSSPropertyID propId, bool important)
return true;
}
-CSSParser::SizeParameterType CSSParser::parseSizeParameter(CSSValueList* parsedValues, CSSParserValue* value, SizeParameterType prevParamType)
+CSSPropertyParser::SizeParameterType CSSPropertyParser::parseSizeParameter(CSSValueList* parsedValues, CSSParserValue* value, SizeParameterType prevParamType)
{
switch (value->id) {
case CSSValueAuto:
@@ -3469,11 +2235,11 @@ CSSParser::SizeParameterType CSSParser::parseSizeParameter(CSSValueList* parsedV
// [ <string> <string> ]+ | inherit | none
// inherit and none are handled in parseValue.
-bool CSSParser::parseQuotes(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseQuotes(CSSPropertyID propId, bool important)
{
- RefPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
while (CSSParserValue* val = m_valueList->current()) {
- RefPtr<CSSValue> parsedValue;
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = nullptr;
if (val->unit == CSSPrimitiveValue::CSS_STRING)
parsedValue = CSSPrimitiveValue::create(val->string, CSSPrimitiveValue::CSS_STRING);
else
@@ -3492,15 +2258,15 @@ bool CSSParser::parseQuotes(CSSPropertyID propId, bool important)
// [ <string> | <uri> | <counter> | attr(X) | open-quote | close-quote | no-open-quote | no-close-quote ]+ | inherit
// in CSS 2.1 this got somewhat reduced:
// [ <string> | attr(X) | open-quote | close-quote | no-open-quote | no-close-quote ]+ | inherit
-bool CSSParser::parseContent(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseContent(CSSPropertyID propId, bool important)
{
- RefPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
while (CSSParserValue* val = m_valueList->current()) {
- RefPtr<CSSValue> parsedValue;
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = nullptr;
if (val->unit == CSSPrimitiveValue::CSS_URI) {
// url
- parsedValue = CSSImageValue::create(completeURL(val->string));
+ parsedValue = createCSSImageValueWithReferrer(val->string, completeURL(val->string));
} else if (val->unit == CSSParserValue::Function) {
// attr(X) | counter(X [,Y]) | counters(X, Y, [,Z]) | -webkit-gradient(...)
CSSParserValueList* args = val->function->args.get();
@@ -3565,22 +2331,22 @@ bool CSSParser::parseContent(CSSPropertyID propId, bool important)
return false;
}
-PassRefPtr<CSSValue> CSSParser::parseAttr(CSSParserValueList* args)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAttr(CSSParserValueList* args)
{
if (args->size() != 1)
- return 0;
+ return nullptr;
CSSParserValue* a = args->current();
if (a->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
+ return nullptr;
String attrName = a->string;
// CSS allows identifiers with "-" at the start, like "-webkit-mask-image".
// But HTML attribute names can't have those characters, and we should not
// even parse them inside attr().
if (attrName[0] == '-')
- return 0;
+ return nullptr;
if (m_context.isHTMLDocument())
attrName = attrName.lower();
@@ -3588,7 +2354,7 @@ PassRefPtr<CSSValue> CSSParser::parseAttr(CSSParserValueList* args)
return cssValuePool().createValue(attrName, CSSPrimitiveValue::CSS_ATTR);
}
-PassRefPtr<CSSValue> CSSParser::parseBackgroundColor()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseBackgroundColor()
{
CSSValueID id = m_valueList->current()->id;
if (id == CSSValueWebkitText || (id >= CSSValueAqua && id <= CSSValueWindowtext) || id == CSSValueMenu || id == CSSValueCurrentcolor ||
@@ -3597,14 +2363,14 @@ PassRefPtr<CSSValue> CSSParser::parseBackgroundColor()
return parseColor();
}
-bool CSSParser::parseFillImage(CSSParserValueList* valueList, RefPtr<CSSValue>& value)
+bool CSSPropertyParser::parseFillImage(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& value)
{
if (valueList->current()->id == CSSValueNone) {
value = cssValuePool().createIdentifierValue(CSSValueNone);
return true;
}
if (valueList->current()->unit == CSSPrimitiveValue::CSS_URI) {
- value = CSSImageValue::create(completeURL(valueList->current()->string));
+ value = createCSSImageValueWithReferrer(valueList->current()->string, completeURL(valueList->current()->string));
return true;
}
@@ -3620,7 +2386,7 @@ bool CSSParser::parseFillImage(CSSParserValueList* valueList, RefPtr<CSSValue>&
return false;
}
-PassRefPtr<CSSValue> CSSParser::parseFillPositionX(CSSParserValueList* valueList)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseFillPositionX(CSSParserValueList* valueList)
{
int id = valueList->current()->id;
if (id == CSSValueLeft || id == CSSValueRight || id == CSSValueCenter) {
@@ -3633,10 +2399,10 @@ PassRefPtr<CSSValue> CSSParser::parseFillPositionX(CSSParserValueList* valueList
}
if (validUnit(valueList->current(), FPercent | FLength))
return createPrimitiveNumericValue(valueList->current());
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseFillPositionY(CSSParserValueList* valueList)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseFillPositionY(CSSParserValueList* valueList)
{
int id = valueList->current()->id;
if (id == CSSValueTop || id == CSSValueBottom || id == CSSValueCenter) {
@@ -3649,17 +2415,17 @@ PassRefPtr<CSSValue> CSSParser::parseFillPositionY(CSSParserValueList* valueList
}
if (validUnit(valueList->current(), FPercent | FLength))
return createPrimitiveNumericValue(valueList->current());
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSPrimitiveValue> CSSParser::parseFillPositionComponent(CSSParserValueList* valueList, unsigned& cumulativeFlags, FillPositionFlag& individualFlag, FillPositionParsingMode parsingMode)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::parseFillPositionComponent(CSSParserValueList* valueList, unsigned& cumulativeFlags, FillPositionFlag& individualFlag, FillPositionParsingMode parsingMode)
{
CSSValueID id = valueList->current()->id;
if (id == CSSValueLeft || id == CSSValueTop || id == CSSValueRight || id == CSSValueBottom || id == CSSValueCenter) {
int percent = 0;
if (id == CSSValueLeft || id == CSSValueRight) {
if (cumulativeFlags & XFillPosition)
- return 0;
+ return nullptr;
cumulativeFlags |= XFillPosition;
individualFlag = XFillPosition;
if (id == CSSValueRight)
@@ -3667,7 +2433,7 @@ PassRefPtr<CSSPrimitiveValue> CSSParser::parseFillPositionComponent(CSSParserVal
}
else if (id == CSSValueTop || id == CSSValueBottom) {
if (cumulativeFlags & YFillPosition)
- return 0;
+ return nullptr;
cumulativeFlags |= YFillPosition;
individualFlag = YFillPosition;
if (id == CSSValueBottom)
@@ -3694,11 +2460,11 @@ PassRefPtr<CSSPrimitiveValue> CSSParser::parseFillPositionComponent(CSSParserVal
} else {
if (m_parsedCalculation)
m_parsedCalculation.release();
- return 0;
+ return nullptr;
}
return createPrimitiveNumericValue(valueList->current());
}
- return 0;
+ return nullptr;
}
static bool isValueConflictingWithCurrentEdge(int value1, int value2)
@@ -3717,7 +2483,7 @@ static bool isFillPositionKeyword(CSSValueID value)
return value == CSSValueLeft || value == CSSValueTop || value == CSSValueBottom || value == CSSValueRight || value == CSSValueCenter;
}
-void CSSParser::parse4ValuesFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue>& value1, RefPtr<CSSValue>& value2, PassRefPtr<CSSPrimitiveValue> parsedValue1, PassRefPtr<CSSPrimitiveValue> parsedValue2)
+void CSSPropertyParser::parse4ValuesFillPosition(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& value1, RefPtrWillBeRawPtr<CSSValue>& value2, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue1, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue2)
{
// [ left | right ] [ <percentage] | <length> ] && [ top | bottom ] [ <percentage> | <length> ]
// In the case of 4 values <position> requires the second value to be a length or a percentage.
@@ -3726,7 +2492,7 @@ void CSSParser::parse4ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
unsigned cumulativeFlags = 0;
FillPositionFlag value3Flag = InvalidFillPosition;
- RefPtr<CSSPrimitiveValue> value3 = parseFillPositionComponent(valueList, cumulativeFlags, value3Flag, ResolveValuesAsKeyword);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> value3 = parseFillPositionComponent(valueList, cumulativeFlags, value3Flag, ResolveValuesAsKeyword);
if (!value3)
return;
@@ -3749,7 +2515,7 @@ void CSSParser::parse4ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
cumulativeFlags = 0;
FillPositionFlag value4Flag = InvalidFillPosition;
- RefPtr<CSSPrimitiveValue> value4 = parseFillPositionComponent(valueList, cumulativeFlags, value4Flag, ResolveValuesAsKeyword);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> value4 = parseFillPositionComponent(valueList, cumulativeFlags, value4Flag, ResolveValuesAsKeyword);
if (!value4)
return;
@@ -3765,11 +2531,11 @@ void CSSParser::parse4ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
valueList->next();
}
-void CSSParser::parse3ValuesFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue>& value1, RefPtr<CSSValue>& value2, PassRefPtr<CSSPrimitiveValue> parsedValue1, PassRefPtr<CSSPrimitiveValue> parsedValue2)
+void CSSPropertyParser::parse3ValuesFillPosition(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& value1, RefPtrWillBeRawPtr<CSSValue>& value2, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue1, PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue2)
{
unsigned cumulativeFlags = 0;
FillPositionFlag value3Flag = InvalidFillPosition;
- RefPtr<CSSPrimitiveValue> value3 = parseFillPositionComponent(valueList, cumulativeFlags, value3Flag, ResolveValuesAsKeyword);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> value3 = parseFillPositionComponent(valueList, cumulativeFlags, value3Flag, ResolveValuesAsKeyword);
// value3 is not an expected value, we return.
if (!value3)
@@ -3813,8 +2579,8 @@ void CSSParser::parse3ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
value1 = createPrimitiveValuePair(parsedValue1, parsedValue2);
value2 = createPrimitiveValuePair(cssValuePool().createIdentifierValue(secondPositionKeyword), cssValuePool().createValue(50, CSSPrimitiveValue::CSS_PERCENTAGE));
} else {
- RefPtr<CSSPrimitiveValue> firstPositionValue;
- RefPtr<CSSPrimitiveValue> secondPositionValue;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> firstPositionValue = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> secondPositionValue = nullptr;
if (isFillPositionKeyword(ident2)) {
// To match CSS grammar, we should only accept: [ center | left | right | bottom | top ] [ left | right | top | bottom ] [ <percentage> | <length> ].
@@ -3856,12 +2622,12 @@ void CSSParser::parse3ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
#endif
}
-inline bool CSSParser::isPotentialPositionValue(CSSParserValue* value)
+inline bool CSSPropertyParser::isPotentialPositionValue(CSSParserValue* value)
{
return isFillPositionKeyword(value->id) || validUnit(value, FPercent | FLength, ReleaseParsedCalcValue);
}
-void CSSParser::parseFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue>& value1, RefPtr<CSSValue>& value2)
+void CSSPropertyParser::parseFillPosition(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& value1, RefPtrWillBeRawPtr<CSSValue>& value2)
{
unsigned numberOfValues = 0;
for (unsigned i = valueList->currentIndex(); i < valueList->size(); ++i, ++numberOfValues) {
@@ -3895,7 +2661,7 @@ void CSSParser::parseFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue
if (!value1)
return;
- value = valueList->next();
+ valueList->next();
// In case we are parsing more than two values, relax the check inside of parseFillPositionComponent. top 20px is
// a valid start for <position>.
@@ -3908,8 +2674,8 @@ void CSSParser::parseFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue
return;
}
- RefPtr<CSSPrimitiveValue> parsedValue1 = toCSSPrimitiveValue(value1.get());
- RefPtr<CSSPrimitiveValue> parsedValue2 = toCSSPrimitiveValue(value2.get());
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue1 = toCSSPrimitiveValue(value1.get());
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue2 = toCSSPrimitiveValue(value2.get());
value1.clear();
value2.clear();
@@ -3924,10 +2690,8 @@ void CSSParser::parseFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue
parse4ValuesFillPosition(valueList, value1, value2, parsedValue1.release(), parsedValue2.release());
}
-void CSSParser::parse2ValuesFillPosition(CSSParserValueList* valueList, RefPtr<CSSValue>& value1, RefPtr<CSSValue>& value2)
+void CSSPropertyParser::parse2ValuesFillPosition(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& value1, RefPtrWillBeRawPtr<CSSValue>& value2)
{
- CSSParserValue* value = valueList->current();
-
// Parse the first value. We're just making sure that it is one of the valid keywords or a percentage/length.
unsigned cumulativeFlags = 0;
FillPositionFlag value1Flag = InvalidFillPosition;
@@ -3939,7 +2703,7 @@ void CSSParser::parse2ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
// It only takes one value for background-position to be correctly parsed if it was specified in a shorthand (since we
// can assume that any other values belong to the rest of the shorthand). If we're not parsing a shorthand, though, the
// value was explicitly specified for our property.
- value = valueList->next();
+ CSSParserValue* value = valueList->next();
// First check for the comma. If so, we are finished parsing this value or value pair.
if (isComma(value))
@@ -3968,7 +2732,7 @@ void CSSParser::parse2ValuesFillPosition(CSSParserValueList* valueList, RefPtr<C
value1.swap(value2);
}
-void CSSParser::parseFillRepeat(RefPtr<CSSValue>& value1, RefPtr<CSSValue>& value2)
+void CSSPropertyParser::parseFillRepeat(RefPtrWillBeRawPtr<CSSValue>& value1, RefPtrWillBeRawPtr<CSSValue>& value2)
{
CSSValueID id = m_valueList->current()->id;
if (id == CSSValueRepeatX) {
@@ -3988,7 +2752,7 @@ void CSSParser::parseFillRepeat(RefPtr<CSSValue>& value1, RefPtr<CSSValue>& valu
if (id == CSSValueRepeat || id == CSSValueNoRepeat || id == CSSValueRound || id == CSSValueSpace)
value1 = cssValuePool().createIdentifierValue(id);
else {
- value1 = 0;
+ value1 = nullptr;
return;
}
@@ -4009,7 +2773,7 @@ void CSSParser::parseFillRepeat(RefPtr<CSSValue>& value1, RefPtr<CSSValue>& valu
value2 = cssValuePool().createIdentifierValue(toCSSPrimitiveValue(value1.get())->getValueID());
}
-PassRefPtr<CSSValue> CSSParser::parseFillSize(CSSPropertyID propId, bool& allowComma)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseFillSize(CSSPropertyID propId, bool& allowComma)
{
allowComma = true;
CSSParserValue* value = m_valueList->current();
@@ -4017,24 +2781,24 @@ PassRefPtr<CSSValue> CSSParser::parseFillSize(CSSPropertyID propId, bool& allowC
if (value->id == CSSValueContain || value->id == CSSValueCover)
return cssValuePool().createIdentifierValue(value->id);
- RefPtr<CSSPrimitiveValue> parsedValue1;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue1 = nullptr;
if (value->id == CSSValueAuto)
parsedValue1 = cssValuePool().createIdentifierValue(CSSValueAuto);
else {
if (!validUnit(value, FLength | FPercent))
- return 0;
+ return nullptr;
parsedValue1 = createPrimitiveNumericValue(value);
}
- RefPtr<CSSPrimitiveValue> parsedValue2;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue2 = nullptr;
if ((value = m_valueList->next())) {
if (value->unit == CSSParserValue::Operator && value->iValue == ',')
allowComma = false;
else if (value->id != CSSValueAuto) {
if (!validUnit(value, FLength | FPercent)) {
if (!inShorthand())
- return 0;
+ return nullptr;
// We need to rewind the value list, so that when it is advanced we'll end up back at this value.
m_valueList->previous();
} else
@@ -4049,21 +2813,25 @@ PassRefPtr<CSSValue> CSSParser::parseFillSize(CSSPropertyID propId, bool& allowC
if (!parsedValue2)
return parsedValue1;
- return createPrimitiveValuePair(parsedValue1.release(), parsedValue2.release());
+
+ Pair::IdenticalValuesPolicy policy = propId == CSSPropertyWebkitBackgroundSize ?
+ Pair::DropIdenticalValues : Pair::KeepIdenticalValues;
+
+ return createPrimitiveValuePair(parsedValue1.release(), parsedValue2.release(), policy);
}
-bool CSSParser::parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2,
- RefPtr<CSSValue>& retValue1, RefPtr<CSSValue>& retValue2)
+bool CSSPropertyParser::parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2,
+ RefPtrWillBeRawPtr<CSSValue>& retValue1, RefPtrWillBeRawPtr<CSSValue>& retValue2)
{
- RefPtr<CSSValueList> values;
- RefPtr<CSSValueList> values2;
+ RefPtrWillBeRawPtr<CSSValueList> values = nullptr;
+ RefPtrWillBeRawPtr<CSSValueList> values2 = nullptr;
CSSParserValue* val;
- RefPtr<CSSValue> value;
- RefPtr<CSSValue> value2;
+ RefPtrWillBeRawPtr<CSSValue> value = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> value2 = nullptr;
bool allowComma = false;
- retValue1 = retValue2 = 0;
+ retValue1 = retValue2 = nullptr;
propId1 = propId;
propId2 = propId;
if (propId == CSSPropertyBackgroundPosition) {
@@ -4081,8 +2849,8 @@ bool CSSParser::parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1,
}
while ((val = m_valueList->current())) {
- RefPtr<CSSValue> currValue;
- RefPtr<CSSValue> currValue2;
+ RefPtrWillBeRawPtr<CSSValue> currValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> currValue2 = nullptr;
if (allowComma) {
if (!isComma(val))
@@ -4159,12 +2927,12 @@ bool CSSParser::parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1,
}
break;
case CSSPropertyBackgroundBlendMode:
- if (RuntimeEnabledFeatures::cssCompositingEnabled() && (val->id == CSSValueNormal || val->id == CSSValueMultiply
+ if (val->id == CSSValueNormal || val->id == CSSValueMultiply
|| val->id == CSSValueScreen || val->id == CSSValueOverlay || val->id == CSSValueDarken
|| val->id == CSSValueLighten || val->id == CSSValueColorDodge || val->id == CSSValueColorBurn
|| val->id == CSSValueHardLight || val->id == CSSValueSoftLight || val->id == CSSValueDifference
|| val->id == CSSValueExclusion || val->id == CSSValueHue || val->id == CSSValueSaturation
- || val->id == CSSValueColor || val->id == CSSValueLuminosity)) {
+ || val->id == CSSValueColor || val->id == CSSValueLuminosity) {
currValue = cssValuePool().createIdentifierValue(val->id);
m_valueList->next();
}
@@ -4188,7 +2956,7 @@ bool CSSParser::parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1,
currValue = cssValuePool().createIdentifierValue(val->id);
m_valueList->next();
} else {
- currValue = 0;
+ currValue = nullptr;
}
}
break;
@@ -4241,49 +3009,49 @@ bool CSSParser::parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1,
return false;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationDelay()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationDelay()
{
CSSParserValue* value = m_valueList->current();
if (validUnit(value, FTime))
return createPrimitiveNumericValue(value);
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationDirection()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationDirection()
{
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueNormal || value->id == CSSValueAlternate || value->id == CSSValueReverse || value->id == CSSValueAlternateReverse)
return cssValuePool().createIdentifierValue(value->id);
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationDuration()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationDuration()
{
CSSParserValue* value = m_valueList->current();
if (validUnit(value, FTime | FNonNeg))
return createPrimitiveNumericValue(value);
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationFillMode()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationFillMode()
{
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueNone || value->id == CSSValueForwards || value->id == CSSValueBackwards || value->id == CSSValueBoth)
return cssValuePool().createIdentifierValue(value->id);
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationIterationCount()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationIterationCount()
{
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueInfinite)
return cssValuePool().createIdentifierValue(value->id);
if (validUnit(value, FNumber | FNonNeg))
return createPrimitiveNumericValue(value);
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationName()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationName()
{
CSSParserValue* value = m_valueList->current();
if (value->unit == CSSPrimitiveValue::CSS_STRING || value->unit == CSSPrimitiveValue::CSS_IDENT) {
@@ -4293,38 +3061,38 @@ PassRefPtr<CSSValue> CSSParser::parseAnimationName()
return createPrimitiveStringValue(value);
}
}
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationPlayState()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationPlayState()
{
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueRunning || value->id == CSSValuePaused)
return cssValuePool().createIdentifierValue(value->id);
- return 0;
+ return nullptr;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationProperty(AnimationParseContext& context)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationProperty()
{
CSSParserValue* value = m_valueList->current();
if (value->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
+ return nullptr;
+ // Since all is valid css property keyword, cssPropertyID for all
+ // returns non-null value. We need to check "all" before
+ // cssPropertyID check.
+ if (equalIgnoringCase(value, "all"))
+ return cssValuePool().createIdentifierValue(CSSValueAll);
CSSPropertyID result = cssPropertyID(value->string);
- if (result)
+ if (result && RuntimeCSSEnabled::isCSSPropertyEnabled(result))
return cssValuePool().createIdentifierValue(result);
- if (equalIgnoringCase(value, "all")) {
- context.sawAnimationPropertyKeyword();
- return cssValuePool().createIdentifierValue(CSSValueAll);
- }
- if (equalIgnoringCase(value, "none")) {
- context.commitAnimationPropertyKeyword();
- context.sawAnimationPropertyKeyword();
+ if (equalIgnoringCase(value, "none"))
return cssValuePool().createIdentifierValue(CSSValueNone);
- }
- return 0;
+ if (equalIgnoringCase(value, "inherit") || equalIgnoringCase(value, "initial"))
+ return nullptr;
+ return createPrimitiveStringValue(value);
}
-bool CSSParser::parseTransformOriginShorthand(RefPtr<CSSValue>& value1, RefPtr<CSSValue>& value2, RefPtr<CSSValue>& value3)
+bool CSSPropertyParser::parseWebkitTransformOriginShorthand(RefPtrWillBeRawPtr<CSSValue>& value1, RefPtrWillBeRawPtr<CSSValue>& value2, RefPtrWillBeRawPtr<CSSValue>& value3)
{
parse2ValuesFillPosition(m_valueList.get(), value1, value2);
@@ -4341,7 +3109,7 @@ bool CSSParser::parseTransformOriginShorthand(RefPtr<CSSValue>& value1, RefPtr<C
return true;
}
-bool CSSParser::parseCubicBezierTimingFunctionValue(CSSParserValueList*& args, double& result)
+bool CSSPropertyParser::parseCubicBezierTimingFunctionValue(CSSParserValueList*& args, double& result)
{
CSSParserValue* v = args->current();
if (!validUnit(v, FNumber))
@@ -4357,210 +3125,192 @@ bool CSSParser::parseCubicBezierTimingFunctionValue(CSSParserValueList*& args, d
return true;
}
-PassRefPtr<CSSValue> CSSParser::parseAnimationTimingFunction()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationTimingFunction()
{
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueEase || value->id == CSSValueLinear || value->id == CSSValueEaseIn || value->id == CSSValueEaseOut
- || value->id == CSSValueEaseInOut || value->id == CSSValueStepStart || value->id == CSSValueStepEnd)
+ || value->id == CSSValueEaseInOut || value->id == CSSValueStepStart || value->id == CSSValueStepEnd
+ || (value->id == CSSValueStepMiddle && RuntimeEnabledFeatures::webAnimationsElementAnimateEnabled()))
return cssValuePool().createIdentifierValue(value->id);
// We must be a function.
if (value->unit != CSSParserValue::Function)
- return 0;
+ return nullptr;
CSSParserValueList* args = value->function->args.get();
if (equalIgnoringCase(value->function->name, "steps(")) {
// For steps, 1 or 2 params must be specified (comma-separated)
if (!args || (args->size() != 1 && args->size() != 3))
- return 0;
+ return nullptr;
// There are two values.
int numSteps;
- bool stepAtStart = false;
+ StepsTimingFunction::StepAtPosition stepAtPosition = StepsTimingFunction::StepAtEnd;
CSSParserValue* v = args->current();
if (!validUnit(v, FInteger))
- return 0;
+ return nullptr;
numSteps = clampToInteger(v->fValue);
if (numSteps < 1)
- return 0;
+ return nullptr;
v = args->next();
if (v) {
// There is a comma so we need to parse the second value
if (!isComma(v))
- return 0;
+ return nullptr;
v = args->next();
- if (v->id != CSSValueStart && v->id != CSSValueEnd)
- return 0;
- stepAtStart = v->id == CSSValueStart;
+ switch (v->id) {
+ case CSSValueMiddle:
+ if (!RuntimeEnabledFeatures::webAnimationsAPIEnabled())
+ return nullptr;
+ stepAtPosition = StepsTimingFunction::StepAtMiddle;
+ break;
+ case CSSValueStart:
+ stepAtPosition = StepsTimingFunction::StepAtStart;
+ break;
+ case CSSValueEnd:
+ stepAtPosition = StepsTimingFunction::StepAtEnd;
+ break;
+ default:
+ return nullptr;
+ }
}
- return CSSStepsTimingFunctionValue::create(numSteps, stepAtStart);
+ return CSSStepsTimingFunctionValue::create(numSteps, stepAtPosition);
}
if (equalIgnoringCase(value->function->name, "cubic-bezier(")) {
// For cubic bezier, 4 values must be specified.
if (!args || args->size() != 7)
- return 0;
+ return nullptr;
// There are two points specified. The x values must be between 0 and 1 but the y values can exceed this range.
double x1, y1, x2, y2;
if (!parseCubicBezierTimingFunctionValue(args, x1))
- return 0;
+ return nullptr;
if (x1 < 0 || x1 > 1)
- return 0;
+ return nullptr;
if (!parseCubicBezierTimingFunctionValue(args, y1))
- return 0;
+ return nullptr;
if (!parseCubicBezierTimingFunctionValue(args, x2))
- return 0;
+ return nullptr;
if (x2 < 0 || x2 > 1)
- return 0;
+ return nullptr;
if (!parseCubicBezierTimingFunctionValue(args, y2))
- return 0;
+ return nullptr;
return CSSCubicBezierTimingFunctionValue::create(x1, y1, x2, y2);
}
- return 0;
+ return nullptr;
}
-bool CSSParser::parseAnimationProperty(CSSPropertyID propId, RefPtr<CSSValue>& result, AnimationParseContext& context)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseAnimationProperty(CSSPropertyID propId)
{
- RefPtr<CSSValueList> values;
- CSSParserValue* val;
- RefPtr<CSSValue> value;
- bool allowComma = false;
+ RefPtrWillBeRawPtr<CSSValue> value = nullptr;
+ switch (propId) {
+ case CSSPropertyAnimationDelay:
+ case CSSPropertyWebkitAnimationDelay:
+ case CSSPropertyTransitionDelay:
+ case CSSPropertyWebkitTransitionDelay:
+ value = parseAnimationDelay();
+ break;
+ case CSSPropertyAnimationDirection:
+ case CSSPropertyWebkitAnimationDirection:
+ value = parseAnimationDirection();
+ break;
+ case CSSPropertyAnimationDuration:
+ case CSSPropertyWebkitAnimationDuration:
+ case CSSPropertyTransitionDuration:
+ case CSSPropertyWebkitTransitionDuration:
+ value = parseAnimationDuration();
+ break;
+ case CSSPropertyAnimationFillMode:
+ case CSSPropertyWebkitAnimationFillMode:
+ value = parseAnimationFillMode();
+ break;
+ case CSSPropertyAnimationIterationCount:
+ case CSSPropertyWebkitAnimationIterationCount:
+ value = parseAnimationIterationCount();
+ break;
+ case CSSPropertyAnimationName:
+ case CSSPropertyWebkitAnimationName:
+ value = parseAnimationName();
+ break;
+ case CSSPropertyAnimationPlayState:
+ case CSSPropertyWebkitAnimationPlayState:
+ value = parseAnimationPlayState();
+ break;
+ case CSSPropertyTransitionProperty:
+ case CSSPropertyWebkitTransitionProperty:
+ value = parseAnimationProperty();
+ break;
+ case CSSPropertyAnimationTimingFunction:
+ case CSSPropertyWebkitAnimationTimingFunction:
+ case CSSPropertyTransitionTimingFunction:
+ case CSSPropertyWebkitTransitionTimingFunction:
+ value = parseAnimationTimingFunction();
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ return nullptr;
+ }
- result = 0;
+ if (value)
+ m_valueList->next();
+ return value.release();
+}
- while ((val = m_valueList->current())) {
- RefPtr<CSSValue> currValue;
- if (allowComma) {
- if (!isComma(val))
- return false;
+PassRefPtrWillBeRawPtr<CSSValueList> CSSPropertyParser::parseAnimationPropertyList(CSSPropertyID propId)
+{
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ while (m_valueList->current()) {
+ RefPtrWillBeRawPtr<CSSValue> value = parseAnimationProperty(propId);
+ if (!value)
+ return nullptr;
+ list->append(value.release());
+ if (CSSParserValue* parserValue = m_valueList->current()) {
+ if (!isComma(parserValue))
+ return nullptr;
m_valueList->next();
- allowComma = false;
- }
- else {
- switch (propId) {
- case CSSPropertyAnimationDelay:
- case CSSPropertyWebkitAnimationDelay:
- case CSSPropertyTransitionDelay:
- case CSSPropertyWebkitTransitionDelay:
- currValue = parseAnimationDelay();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationDirection:
- case CSSPropertyWebkitAnimationDirection:
- currValue = parseAnimationDirection();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationDuration:
- case CSSPropertyWebkitAnimationDuration:
- case CSSPropertyTransitionDuration:
- case CSSPropertyWebkitTransitionDuration:
- currValue = parseAnimationDuration();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationFillMode:
- case CSSPropertyWebkitAnimationFillMode:
- currValue = parseAnimationFillMode();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationIterationCount:
- case CSSPropertyWebkitAnimationIterationCount:
- currValue = parseAnimationIterationCount();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationName:
- case CSSPropertyWebkitAnimationName:
- currValue = parseAnimationName();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationPlayState:
- case CSSPropertyWebkitAnimationPlayState:
- currValue = parseAnimationPlayState();
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyTransitionProperty:
- case CSSPropertyWebkitTransitionProperty:
- currValue = parseAnimationProperty(context);
- if (value && !context.animationPropertyKeywordAllowed())
- return false;
- if (currValue)
- m_valueList->next();
- break;
- case CSSPropertyAnimationTimingFunction:
- case CSSPropertyWebkitAnimationTimingFunction:
- case CSSPropertyTransitionTimingFunction:
- case CSSPropertyWebkitTransitionTimingFunction:
- currValue = parseAnimationTimingFunction();
- if (currValue)
- m_valueList->next();
- break;
- default:
- ASSERT_NOT_REACHED();
- return false;
- }
-
- if (!currValue)
- return false;
-
- if (value && !values) {
- values = CSSValueList::createCommaSeparated();
- values->append(value.release());
- }
-
- if (values)
- values->append(currValue.release());
- else
- value = currValue.release();
-
- allowComma = true;
+ ASSERT(m_valueList->current());
}
-
- // When parsing the 'transition' shorthand property, we let it handle building up the lists for all
- // properties.
- if (inShorthand())
- break;
}
+ if ((propId == CSSPropertyTransitionProperty || propId == CSSPropertyWebkitTransitionProperty) && !isValidTransitionPropertyList(list.get()))
+ return nullptr;
+ ASSERT(list->length());
+ return list.release();
+}
- if (values && values->length()) {
- result = values.release();
- return true;
- }
- if (value) {
- result = value.release();
- return true;
- }
- return false;
+static inline bool isCSSWideKeyword(CSSParserValue& value)
+{
+ return value.id == CSSValueInitial || value.id == CSSValueInherit || value.id == CSSValueDefault;
+}
+
+static inline bool isValidCustomIdentForGridPositions(CSSParserValue& value)
+{
+ // FIXME: we need a more general solution for <custom-ident> in all properties.
+ return value.unit == CSSPrimitiveValue::CSS_IDENT && value.id != CSSValueSpan && value.id != CSSValueAuto && !isCSSWideKeyword(value);
}
-// The function parses [ <integer> || <string> ] in <grid-line> (which can be stand alone or with 'span').
-bool CSSParser::parseIntegerOrStringFromGridPosition(RefPtr<CSSPrimitiveValue>& numericValue, RefPtr<CSSPrimitiveValue>& gridLineName)
+// The function parses [ <integer> || <custom-ident> ] in <grid-line> (which can be stand alone or with 'span').
+bool CSSPropertyParser::parseIntegerOrCustomIdentFromGridPosition(RefPtrWillBeRawPtr<CSSPrimitiveValue>& numericValue, RefPtrWillBeRawPtr<CSSPrimitiveValue>& gridLineName)
{
CSSParserValue* value = m_valueList->current();
if (validUnit(value, FInteger) && value->fValue) {
numericValue = createPrimitiveNumericValue(value);
value = m_valueList->next();
- if (value && value->unit == CSSPrimitiveValue::CSS_STRING) {
+ if (value && isValidCustomIdentForGridPositions(*value)) {
gridLineName = createPrimitiveStringValue(m_valueList->current());
m_valueList->next();
}
return true;
}
- if (value->unit == CSSPrimitiveValue::CSS_STRING) {
+ if (isValidCustomIdentForGridPositions(*value)) {
gridLineName = createPrimitiveStringValue(m_valueList->current());
value = m_valueList->next();
if (value && validUnit(value, FInteger) && value->fValue) {
@@ -4573,7 +3323,7 @@ bool CSSParser::parseIntegerOrStringFromGridPosition(RefPtr<CSSPrimitiveValue>&
return false;
}
-PassRefPtr<CSSValue> CSSParser::parseGridPosition()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseGridPosition()
{
ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
@@ -4583,16 +3333,11 @@ PassRefPtr<CSSValue> CSSParser::parseGridPosition()
return cssValuePool().createIdentifierValue(CSSValueAuto);
}
- if (value->id != CSSValueSpan && value->unit == CSSPrimitiveValue::CSS_IDENT) {
- m_valueList->next();
- return cssValuePool().createValue(value->string, CSSPrimitiveValue::CSS_STRING);
- }
-
- RefPtr<CSSPrimitiveValue> numericValue;
- RefPtr<CSSPrimitiveValue> gridLineName;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> numericValue = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> gridLineName = nullptr;
bool hasSeenSpanKeyword = false;
- if (parseIntegerOrStringFromGridPosition(numericValue, gridLineName)) {
+ if (parseIntegerOrCustomIdentFromGridPosition(numericValue, gridLineName)) {
value = m_valueList->current();
if (value && value->id == CSSValueSpan) {
hasSeenSpanKeyword = true;
@@ -4600,24 +3345,30 @@ PassRefPtr<CSSValue> CSSParser::parseGridPosition()
}
} else if (value->id == CSSValueSpan) {
hasSeenSpanKeyword = true;
- if (m_valueList->next())
- parseIntegerOrStringFromGridPosition(numericValue, gridLineName);
+ if (CSSParserValue* nextValue = m_valueList->next()) {
+ if (!isForwardSlashOperator(nextValue) && !parseIntegerOrCustomIdentFromGridPosition(numericValue, gridLineName))
+ return nullptr;
+ }
}
// Check that we have consumed all the value list. For shorthands, the parser will pass
// the whole value list (including the opposite position).
if (m_valueList->current() && !isForwardSlashOperator(m_valueList->current()))
- return 0;
+ return nullptr;
// If we didn't parse anything, this is not a valid grid position.
if (!hasSeenSpanKeyword && !gridLineName && !numericValue)
- return 0;
+ return nullptr;
// Negative numbers are not allowed for span (but are for <integer>).
if (hasSeenSpanKeyword && numericValue && numericValue->getIntValue() < 0)
- return 0;
+ return nullptr;
- RefPtr<CSSValueList> values = CSSValueList::createSpaceSeparated();
+ // For the <custom-ident> case.
+ if (gridLineName && !numericValue && !hasSeenSpanKeyword)
+ return cssValuePool().createValue(gridLineName->getStringValue(), CSSPrimitiveValue::CSS_STRING);
+
+ RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createSpaceSeparated();
if (hasSeenSpanKeyword)
values->append(cssValuePool().createIdentifierValue(CSSValueSpan));
if (numericValue)
@@ -4628,7 +3379,7 @@ PassRefPtr<CSSValue> CSSParser::parseGridPosition()
return values.release();
}
-static PassRefPtr<CSSValue> gridMissingGridPositionValue(CSSValue* value)
+static PassRefPtrWillBeRawPtr<CSSValue> gridMissingGridPositionValue(CSSValue* value)
{
if (value->isPrimitiveValue() && toCSSPrimitiveValue(value)->isString())
return value;
@@ -4636,17 +3387,17 @@ static PassRefPtr<CSSValue> gridMissingGridPositionValue(CSSValue* value)
return cssValuePool().createIdentifierValue(CSSValueAuto);
}
-bool CSSParser::parseGridItemPositionShorthand(CSSPropertyID shorthandId, bool important)
+bool CSSPropertyParser::parseGridItemPositionShorthand(CSSPropertyID shorthandId, bool important)
{
ShorthandScope scope(this, shorthandId);
const StylePropertyShorthand& shorthand = shorthandForProperty(shorthandId);
ASSERT(shorthand.length() == 2);
- RefPtr<CSSValue> startValue = parseGridPosition();
+ RefPtrWillBeRawPtr<CSSValue> startValue = parseGridPosition();
if (!startValue)
return false;
- RefPtr<CSSValue> endValue;
+ RefPtrWillBeRawPtr<CSSValue> endValue = nullptr;
if (m_valueList->current()) {
if (!isForwardSlashOperator(m_valueList->current()))
return false;
@@ -4666,7 +3417,186 @@ bool CSSParser::parseGridItemPositionShorthand(CSSPropertyID shorthandId, bool i
return true;
}
-bool CSSParser::parseGridAreaShorthand(bool important)
+bool CSSPropertyParser::parseGridTemplateRowsAndAreas(PassRefPtrWillBeRawPtr<CSSValue> templateColumns, bool important)
+{
+ NamedGridAreaMap gridAreaMap;
+ size_t rowCount = 0;
+ size_t columnCount = 0;
+ bool trailingIdentWasAdded = false;
+ RefPtrWillBeRawPtr<CSSValueList> templateRows = CSSValueList::createSpaceSeparated();
+
+ // At least template-areas strings must be defined.
+ if (!m_valueList->current())
+ return false;
+
+ while (m_valueList->current()) {
+ // Handle leading <custom-ident>*.
+ if (m_valueList->current()->unit == CSSParserValue::ValueList) {
+ if (trailingIdentWasAdded) {
+ // A row's trailing ident must be concatenated with the next row's leading one.
+ parseGridLineNames(*m_valueList, *templateRows, static_cast<CSSGridLineNamesValue*>(templateRows->item(templateRows->length() - 1)));
+ } else {
+ parseGridLineNames(*m_valueList, *templateRows);
+ }
+ }
+
+ // Handle a template-area's row.
+ if (!parseGridTemplateAreasRow(gridAreaMap, rowCount, columnCount))
+ return false;
+ ++rowCount;
+
+ // Handle template-rows's track-size.
+ if (m_valueList->current() && m_valueList->current()->unit != CSSParserValue::ValueList && m_valueList->current()->unit != CSSPrimitiveValue::CSS_STRING) {
+ RefPtrWillBeRawPtr<CSSValue> value = parseGridTrackSize(*m_valueList);
+ if (!value)
+ return false;
+ templateRows->append(value);
+ } else {
+ templateRows->append(cssValuePool().createIdentifierValue(CSSValueAuto));
+ }
+
+ // This will handle the trailing/leading <custom-ident>* in the grammar.
+ trailingIdentWasAdded = false;
+ if (m_valueList->current() && m_valueList->current()->unit == CSSParserValue::ValueList) {
+ parseGridLineNames(*m_valueList, *templateRows);
+ trailingIdentWasAdded = true;
+ }
+ }
+
+ // [<track-list> /]?
+ if (templateColumns)
+ addProperty(CSSPropertyGridTemplateColumns, templateColumns, important);
+ else
+ addProperty(CSSPropertyGridTemplateColumns, cssValuePool().createIdentifierValue(CSSValueNone), important);
+
+ // [<line-names>? <string> [<track-size> <line-names>]? ]+
+ RefPtrWillBeRawPtr<CSSValue> templateAreas = CSSGridTemplateAreasValue::create(gridAreaMap, rowCount, columnCount);
+ addProperty(CSSPropertyGridTemplateAreas, templateAreas.release(), important);
+ addProperty(CSSPropertyGridTemplateRows, templateRows.release(), important);
+
+
+ return true;
+}
+
+
+bool CSSPropertyParser::parseGridTemplateShorthand(bool important)
+{
+ ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
+
+ ShorthandScope scope(this, CSSPropertyGridTemplate);
+ ASSERT(gridTemplateShorthand().length() == 3);
+
+ // At least "none" must be defined.
+ if (!m_valueList->current())
+ return false;
+
+ bool firstValueIsNone = m_valueList->current()->id == CSSValueNone;
+
+ // 1- 'none' case.
+ if (firstValueIsNone && !m_valueList->next()) {
+ addProperty(CSSPropertyGridTemplateColumns, cssValuePool().createIdentifierValue(CSSValueNone), important);
+ addProperty(CSSPropertyGridTemplateRows, cssValuePool().createIdentifierValue(CSSValueNone), important);
+ addProperty(CSSPropertyGridTemplateAreas, cssValuePool().createIdentifierValue(CSSValueNone), important);
+ return true;
+ }
+
+ unsigned index = 0;
+ RefPtrWillBeRawPtr<CSSValue> columnsValue = nullptr;
+ if (firstValueIsNone) {
+ columnsValue = cssValuePool().createIdentifierValue(CSSValueNone);
+ } else {
+ columnsValue = parseGridTrackList(important);
+ }
+
+ // 2- <grid-template-columns> / <grid-template-columns> syntax.
+ if (columnsValue) {
+ if (!(m_valueList->current() && isForwardSlashOperator(m_valueList->current()) && m_valueList->next()))
+ return false;
+ index = m_valueList->currentIndex();
+ if (RefPtrWillBeRawPtr<CSSValue> rowsValue = parseGridTrackList(important)) {
+ if (m_valueList->current())
+ return false;
+ addProperty(CSSPropertyGridTemplateColumns, columnsValue, important);
+ addProperty(CSSPropertyGridTemplateRows, rowsValue, important);
+ addProperty(CSSPropertyGridTemplateAreas, cssValuePool().createIdentifierValue(CSSValueNone), important);
+ return true;
+ }
+ }
+
+
+ // 3- [<track-list> /]? [<line-names>? <string> [<track-size> <line-names>]? ]+ syntax.
+ // The template-columns <track-list> can't be 'none'.
+ if (firstValueIsNone)
+ return false;
+ // It requires to rewind parsing due to previous syntax failures.
+ m_valueList->setCurrentIndex(index);
+ return parseGridTemplateRowsAndAreas(columnsValue, important);
+}
+
+bool CSSPropertyParser::parseGridShorthand(bool important)
+{
+ ShorthandScope scope(this, CSSPropertyGrid);
+ ASSERT(shorthandForProperty(CSSPropertyGrid).length() == 4);
+
+ // 1- <grid-template>
+ if (parseGridTemplateShorthand(important)) {
+ // It can only be specified the explicit or the implicit grid properties in a single grid declaration.
+ // The sub-properties not specified are set to their initial value, as normal for shorthands.
+ addProperty(CSSPropertyGridAutoFlow, cssValuePool().createImplicitInitialValue(), important);
+ addProperty(CSSPropertyGridAutoColumns, cssValuePool().createImplicitInitialValue(), important);
+ addProperty(CSSPropertyGridAutoRows, cssValuePool().createImplicitInitialValue(), important);
+ return true;
+ }
+
+ // Need to rewind parsing to explore the alternative syntax of this shorthand.
+ m_valueList->setCurrentIndex(0);
+
+ // 2- <grid-auto-flow> [ <grid-auto-columns> [ / <grid-auto-rows> ]? ]
+ CSSValueID id = m_valueList->current()->id;
+ if (id != CSSValueRow && id != CSSValueColumn && id != CSSValueNone)
+ return false;
+
+ RefPtrWillBeRawPtr<CSSValue> autoFlowValue = cssValuePool().createIdentifierValue(id);
+ RefPtrWillBeRawPtr<CSSValue> autoColumnsValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> autoRowsValue = nullptr;
+
+ if (m_valueList->next()) {
+ autoColumnsValue = parseGridTrackSize(*m_valueList);
+ if (!autoColumnsValue)
+ return false;
+ if (m_valueList->current()) {
+ if (!isForwardSlashOperator(m_valueList->current()) || !m_valueList->next())
+ return false;
+ autoRowsValue = parseGridTrackSize(*m_valueList);
+ if (!autoRowsValue)
+ return false;
+ }
+ if (m_valueList->current())
+ return false;
+ } else {
+ // Other omitted values are set to their initial values.
+ autoColumnsValue = cssValuePool().createImplicitInitialValue();
+ autoRowsValue = cssValuePool().createImplicitInitialValue();
+ }
+
+ // if <grid-auto-rows> value is omitted, it is set to the value specified for grid-auto-columns.
+ if (!autoRowsValue)
+ autoRowsValue = autoColumnsValue;
+
+ addProperty(CSSPropertyGridAutoFlow, autoFlowValue, important);
+ addProperty(CSSPropertyGridAutoColumns, autoColumnsValue, important);
+ addProperty(CSSPropertyGridAutoRows, autoRowsValue, important);
+
+ // It can only be specified the explicit or the implicit grid properties in a single grid declaration.
+ // The sub-properties not specified are set to their initial value, as normal for shorthands.
+ addProperty(CSSPropertyGridTemplateColumns, cssValuePool().createImplicitInitialValue(), important);
+ addProperty(CSSPropertyGridTemplateRows, cssValuePool().createImplicitInitialValue(), important);
+ addProperty(CSSPropertyGridTemplateAreas, cssValuePool().createImplicitInitialValue(), important);
+
+ return true;
+}
+
+bool CSSPropertyParser::parseGridAreaShorthand(bool important)
{
ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
@@ -4674,19 +3604,19 @@ bool CSSParser::parseGridAreaShorthand(bool important)
const StylePropertyShorthand& shorthand = gridAreaShorthand();
ASSERT_UNUSED(shorthand, shorthand.length() == 4);
- RefPtr<CSSValue> rowStartValue = parseGridPosition();
+ RefPtrWillBeRawPtr<CSSValue> rowStartValue = parseGridPosition();
if (!rowStartValue)
return false;
- RefPtr<CSSValue> columnStartValue;
+ RefPtrWillBeRawPtr<CSSValue> columnStartValue = nullptr;
if (!parseSingleGridAreaLonghand(columnStartValue))
return false;
- RefPtr<CSSValue> rowEndValue;
+ RefPtrWillBeRawPtr<CSSValue> rowEndValue = nullptr;
if (!parseSingleGridAreaLonghand(rowEndValue))
return false;
- RefPtr<CSSValue> columnEndValue;
+ RefPtrWillBeRawPtr<CSSValue> columnEndValue = nullptr;
if (!parseSingleGridAreaLonghand(columnEndValue))
return false;
@@ -4706,7 +3636,7 @@ bool CSSParser::parseGridAreaShorthand(bool important)
return true;
}
-bool CSSParser::parseSingleGridAreaLonghand(RefPtr<CSSValue>& property)
+bool CSSPropertyParser::parseSingleGridAreaLonghand(RefPtrWillBeRawPtr<CSSValue>& property)
{
if (!m_valueList->current())
return true;
@@ -4721,75 +3651,79 @@ bool CSSParser::parseSingleGridAreaLonghand(RefPtr<CSSValue>& property)
return true;
}
-void CSSParser::parseGridLineNames(CSSParserValueList* parserValueList, CSSValueList& valueList)
+void CSSPropertyParser::parseGridLineNames(CSSParserValueList& inputList, CSSValueList& valueList, CSSGridLineNamesValue* previousNamedAreaTrailingLineNames)
{
- ASSERT(parserValueList->current() && parserValueList->current()->unit == CSSParserValue::ValueList);
+ ASSERT(inputList.current() && inputList.current()->unit == CSSParserValue::ValueList);
- CSSParserValueList* identList = parserValueList->current()->valueList;
+ CSSParserValueList* identList = inputList.current()->valueList;
if (!identList->size()) {
- parserValueList->next();
+ inputList.next();
return;
}
- RefPtr<CSSGridLineNamesValue> lineNames = CSSGridLineNamesValue::create();
+ // Need to ensure the identList is at the heading index, since the parserList might have been rewound.
+ identList->setCurrentIndex(0);
+
+ RefPtrWillBeRawPtr<CSSGridLineNamesValue> lineNames = previousNamedAreaTrailingLineNames;
+ if (!lineNames)
+ lineNames = CSSGridLineNamesValue::create();
while (CSSParserValue* identValue = identList->current()) {
ASSERT(identValue->unit == CSSPrimitiveValue::CSS_IDENT);
- RefPtr<CSSPrimitiveValue> lineName = createPrimitiveStringValue(identValue);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> lineName = createPrimitiveStringValue(identValue);
lineNames->append(lineName.release());
identList->next();
}
- valueList.append(lineNames.release());
+ if (!previousNamedAreaTrailingLineNames)
+ valueList.append(lineNames.release());
- parserValueList->next();
+ inputList.next();
}
-bool CSSParser::parseGridTrackList(CSSPropertyID propId, bool important)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseGridTrackList(bool important)
{
ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
CSSParserValue* value = m_valueList->current();
if (value->id == CSSValueNone) {
- if (m_valueList->next())
- return false;
-
- addProperty(propId, cssValuePool().createIdentifierValue(value->id), important);
- return true;
+ m_valueList->next();
+ return cssValuePool().createIdentifierValue(CSSValueNone);
}
- RefPtr<CSSValueList> values = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createSpaceSeparated();
// Handle leading <ident>*.
value = m_valueList->current();
if (value && value->unit == CSSParserValue::ValueList)
- parseGridLineNames(m_valueList.get(), *values);
+ parseGridLineNames(*m_valueList, *values);
bool seenTrackSizeOrRepeatFunction = false;
while (CSSParserValue* currentValue = m_valueList->current()) {
+ if (isForwardSlashOperator(currentValue))
+ break;
if (currentValue->unit == CSSParserValue::Function && equalIgnoringCase(currentValue->function->name, "repeat(")) {
if (!parseGridTrackRepeatFunction(*values))
- return false;
+ return nullptr;
seenTrackSizeOrRepeatFunction = true;
} else {
- RefPtr<CSSValue> value = parseGridTrackSize(*m_valueList);
+ RefPtrWillBeRawPtr<CSSValue> value = parseGridTrackSize(*m_valueList);
if (!value)
- return false;
+ return nullptr;
values->append(value);
seenTrackSizeOrRepeatFunction = true;
}
// This will handle the trailing <ident>* in the grammar.
value = m_valueList->current();
if (value && value->unit == CSSParserValue::ValueList)
- parseGridLineNames(m_valueList.get(), *values);
+ parseGridLineNames(*m_valueList, *values);
}
// We should have found a <track-size> or else it is not a valid <track-list>
if (!seenTrackSizeOrRepeatFunction)
- return false;
+ return nullptr;
- addProperty(propId, values.release(), important);
- return true;
+ return values;
}
-bool CSSParser::parseGridTrackRepeatFunction(CSSValueList& list)
+bool CSSPropertyParser::parseGridTrackRepeatFunction(CSSValueList& list)
{
CSSParserValueList* arguments = m_valueList->current()->function->args.get();
if (!arguments || arguments->size() < 3 || !validUnit(arguments->valueAt(0), FPositiveInteger) || !isComma(arguments->valueAt(1)))
@@ -4797,17 +3731,21 @@ bool CSSParser::parseGridTrackRepeatFunction(CSSValueList& list)
ASSERT_WITH_SECURITY_IMPLICATION(arguments->valueAt(0)->fValue > 0);
size_t repetitions = arguments->valueAt(0)->fValue;
- RefPtr<CSSValueList> repeatedValues = CSSValueList::createSpaceSeparated();
+ // Clamp repetitions at minRepetitions.
+ // http://www.w3.org/TR/css-grid-1/#repeat-notation
+ if (repetitions > minRepetitions)
+ repetitions = minRepetitions;
+ RefPtrWillBeRawPtr<CSSValueList> repeatedValues = CSSValueList::createSpaceSeparated();
arguments->next(); // Skip the repetition count.
arguments->next(); // Skip the comma.
// Handle leading <ident>*.
CSSParserValue* currentValue = arguments->current();
if (currentValue && currentValue->unit == CSSParserValue::ValueList)
- parseGridLineNames(arguments, *repeatedValues);
+ parseGridLineNames(*arguments, *repeatedValues);
while (arguments->current()) {
- RefPtr<CSSValue> trackSize = parseGridTrackSize(*arguments);
+ RefPtrWillBeRawPtr<CSSValue> trackSize = parseGridTrackSize(*arguments);
if (!trackSize)
return false;
@@ -4816,7 +3754,7 @@ bool CSSParser::parseGridTrackRepeatFunction(CSSValueList& list)
// This takes care of any trailing <ident>* in the grammar.
currentValue = arguments->current();
if (currentValue && currentValue->unit == CSSParserValue::ValueList)
- parseGridLineNames(arguments, *repeatedValues);
+ parseGridLineNames(*arguments, *repeatedValues);
}
for (size_t i = 0; i < repetitions; ++i) {
@@ -4829,7 +3767,8 @@ bool CSSParser::parseGridTrackRepeatFunction(CSSValueList& list)
return true;
}
-PassRefPtr<CSSValue> CSSParser::parseGridTrackSize(CSSParserValueList& inputList)
+
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseGridTrackSize(CSSParserValueList& inputList)
{
ASSERT(RuntimeEnabledFeatures::cssGridLayoutEnabled());
@@ -4843,17 +3782,17 @@ PassRefPtr<CSSValue> CSSParser::parseGridTrackSize(CSSParserValueList& inputList
// The spec defines the following grammar: minmax( <track-breadth> , <track-breadth> )
CSSParserValueList* arguments = currentValue->function->args.get();
if (!arguments || arguments->size() != 3 || !isComma(arguments->valueAt(1)))
- return 0;
+ return nullptr;
- RefPtr<CSSPrimitiveValue> minTrackBreadth = parseGridBreadth(arguments->valueAt(0));
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> minTrackBreadth = parseGridBreadth(arguments->valueAt(0));
if (!minTrackBreadth)
- return 0;
+ return nullptr;
- RefPtr<CSSPrimitiveValue> maxTrackBreadth = parseGridBreadth(arguments->valueAt(2));
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> maxTrackBreadth = parseGridBreadth(arguments->valueAt(2));
if (!maxTrackBreadth)
- return 0;
+ return nullptr;
- RefPtr<CSSValueList> parsedArguments = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> parsedArguments = CSSValueList::createCommaSeparated();
parsedArguments->append(minTrackBreadth);
parsedArguments->append(maxTrackBreadth);
return CSSFunctionValue::create("minmax(", parsedArguments);
@@ -4862,7 +3801,7 @@ PassRefPtr<CSSValue> CSSParser::parseGridTrackSize(CSSParserValueList& inputList
return parseGridBreadth(currentValue);
}
-PassRefPtr<CSSPrimitiveValue> CSSParser::parseGridBreadth(CSSParserValue* currentValue)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::parseGridBreadth(CSSParserValue* currentValue)
{
if (currentValue->id == CSSValueMinContent || currentValue->id == CSSValueMaxContent)
return cssValuePool().createIdentifierValue(currentValue->id);
@@ -4872,135 +3811,143 @@ PassRefPtr<CSSPrimitiveValue> CSSParser::parseGridBreadth(CSSParserValue* curren
// Fractional unit is a non-negative dimension.
if (flexValue <= 0)
- return 0;
+ return nullptr;
return cssValuePool().createValue(flexValue, CSSPrimitiveValue::CSS_FR);
}
if (!validUnit(currentValue, FNonNeg | FLength | FPercent))
- return 0;
+ return nullptr;
return createPrimitiveNumericValue(currentValue);
}
-PassRefPtr<CSSValue> CSSParser::parseGridTemplate()
+bool CSSPropertyParser::parseGridTemplateAreasRow(NamedGridAreaMap& gridAreaMap, const size_t rowCount, size_t& columnCount)
{
- NamedGridAreaMap gridAreaMap;
- size_t rowCount = 0;
- size_t columnCount = 0;
-
- while (CSSParserValue* currentValue = m_valueList->current()) {
- if (currentValue->unit != CSSPrimitiveValue::CSS_STRING)
- return 0;
+ CSSParserValue* currentValue = m_valueList->current();
+ if (!currentValue || currentValue->unit != CSSPrimitiveValue::CSS_STRING)
+ return false;
- String gridRowNames = currentValue->string;
- if (!gridRowNames.length())
- return 0;
+ String gridRowNames = currentValue->string;
+ if (!gridRowNames.length())
+ return false;
- Vector<String> columnNames;
- gridRowNames.split(' ', columnNames);
+ Vector<String> columnNames;
+ gridRowNames.split(' ', columnNames);
- if (!columnCount) {
- columnCount = columnNames.size();
- ASSERT(columnCount);
- } else if (columnCount != columnNames.size()) {
- // The declaration is invalid is all the rows don't have the number of columns.
- return 0;
- }
+ if (!columnCount) {
+ columnCount = columnNames.size();
+ ASSERT(columnCount);
+ } else if (columnCount != columnNames.size()) {
+ // The declaration is invalid is all the rows don't have the number of columns.
+ return false;
+ }
- for (size_t currentCol = 0; currentCol < columnCount; ++currentCol) {
- const String& gridAreaName = columnNames[currentCol];
+ for (size_t currentCol = 0; currentCol < columnCount; ++currentCol) {
+ const String& gridAreaName = columnNames[currentCol];
- // Unamed areas are always valid (we consider them to be 1x1).
- if (gridAreaName == ".")
- continue;
+ // Unamed areas are always valid (we consider them to be 1x1).
+ if (gridAreaName == ".")
+ continue;
- // We handle several grid areas with the same name at once to simplify the validation code.
- size_t lookAheadCol;
- for (lookAheadCol = currentCol; lookAheadCol < (columnCount - 1); ++lookAheadCol) {
- if (columnNames[lookAheadCol + 1] != gridAreaName)
- break;
- }
+ // We handle several grid areas with the same name at once to simplify the validation code.
+ size_t lookAheadCol;
+ for (lookAheadCol = currentCol; lookAheadCol < (columnCount - 1); ++lookAheadCol) {
+ if (columnNames[lookAheadCol + 1] != gridAreaName)
+ break;
+ }
- NamedGridAreaMap::iterator gridAreaIt = gridAreaMap.find(gridAreaName);
- if (gridAreaIt == gridAreaMap.end()) {
- gridAreaMap.add(gridAreaName, GridCoordinate(GridSpan(rowCount, rowCount), GridSpan(currentCol, lookAheadCol)));
- } else {
- GridCoordinate& gridCoordinate = gridAreaIt->value;
+ NamedGridAreaMap::iterator gridAreaIt = gridAreaMap.find(gridAreaName);
+ if (gridAreaIt == gridAreaMap.end()) {
+ gridAreaMap.add(gridAreaName, GridCoordinate(GridSpan(rowCount, rowCount), GridSpan(currentCol, lookAheadCol)));
+ } else {
+ GridCoordinate& gridCoordinate = gridAreaIt->value;
- // The following checks test that the grid area is a single filled-in rectangle.
- // 1. The new row is adjacent to the previously parsed row.
- if (rowCount != gridCoordinate.rows.initialPositionIndex + 1)
- return 0;
+ // The following checks test that the grid area is a single filled-in rectangle.
+ // 1. The new row is adjacent to the previously parsed row.
+ if (rowCount != gridCoordinate.rows.resolvedFinalPosition.next().toInt())
+ return false;
- // 2. The new area starts at the same position as the previously parsed area.
- if (currentCol != gridCoordinate.columns.initialPositionIndex)
- return 0;
+ // 2. The new area starts at the same position as the previously parsed area.
+ if (currentCol != gridCoordinate.columns.resolvedInitialPosition.toInt())
+ return false;
- // 3. The new area ends at the same position as the previously parsed area.
- if (lookAheadCol != gridCoordinate.columns.finalPositionIndex)
- return 0;
+ // 3. The new area ends at the same position as the previously parsed area.
+ if (lookAheadCol != gridCoordinate.columns.resolvedFinalPosition.toInt())
+ return false;
- ++gridCoordinate.rows.finalPositionIndex;
- }
- currentCol = lookAheadCol;
+ ++gridCoordinate.rows.resolvedFinalPosition;
}
+ currentCol = lookAheadCol;
+ }
+
+ m_valueList->next();
+ return true;
+}
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseGridTemplateAreas()
+{
+ NamedGridAreaMap gridAreaMap;
+ size_t rowCount = 0;
+ size_t columnCount = 0;
+
+ while (m_valueList->current()) {
+ if (!parseGridTemplateAreasRow(gridAreaMap, rowCount, columnCount))
+ return nullptr;
++rowCount;
- m_valueList->next();
}
if (!rowCount || !columnCount)
- return 0;
+ return nullptr;
- return CSSGridTemplateValue::create(gridAreaMap, rowCount, columnCount);
+ return CSSGridTemplateAreasValue::create(gridAreaMap, rowCount, columnCount);
}
-PassRefPtr<CSSValue> CSSParser::parseCounterContent(CSSParserValueList* args, bool counters)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseCounterContent(CSSParserValueList* args, bool counters)
{
unsigned numArgs = args->size();
if (counters && numArgs != 3 && numArgs != 5)
- return 0;
+ return nullptr;
if (!counters && numArgs != 1 && numArgs != 3)
- return 0;
+ return nullptr;
CSSParserValue* i = args->current();
if (i->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
- RefPtr<CSSPrimitiveValue> identifier = createPrimitiveStringValue(i);
+ return nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> identifier = createPrimitiveStringValue(i);
- RefPtr<CSSPrimitiveValue> separator;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> separator = nullptr;
if (!counters)
separator = cssValuePool().createValue(String(), CSSPrimitiveValue::CSS_STRING);
else {
i = args->next();
if (i->unit != CSSParserValue::Operator || i->iValue != ',')
- return 0;
+ return nullptr;
i = args->next();
if (i->unit != CSSPrimitiveValue::CSS_STRING)
- return 0;
+ return nullptr;
separator = createPrimitiveStringValue(i);
}
- RefPtr<CSSPrimitiveValue> listStyle;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> listStyle = nullptr;
i = args->next();
if (!i) // Make the list style default decimal
listStyle = cssValuePool().createIdentifierValue(CSSValueDecimal);
else {
if (i->unit != CSSParserValue::Operator || i->iValue != ',')
- return 0;
+ return nullptr;
i = args->next();
if (i->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
+ return nullptr;
CSSValueID listStyleID = CSSValueInvalid;
if (i->id == CSSValueNone || (i->id >= CSSValueDisc && i->id <= CSSValueKatakanaIroha))
listStyleID = i->id;
else
- return 0;
+ return nullptr;
listStyle = cssValuePool().createIdentifierValue(listStyleID);
}
@@ -5008,7 +3955,7 @@ PassRefPtr<CSSValue> CSSParser::parseCounterContent(CSSParserValueList* args, bo
return cssValuePool().createValue(Counter::create(identifier.release(), listStyle.release(), separator.release()));
}
-bool CSSParser::parseClipShape(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseClipShape(CSSPropertyID propId, bool important)
{
CSSParserValue* value = m_valueList->current();
CSSParserValueList* args = value->function->args.get();
@@ -5019,7 +3966,7 @@ bool CSSParser::parseClipShape(CSSPropertyID propId, bool important)
// rect(t, r, b, l) || rect(t r b l)
if (args->size() != 4 && args->size() != 7)
return false;
- RefPtr<Rect> rect = Rect::create();
+ RefPtrWillBeRawPtr<Rect> rect = Rect::create();
bool valid = true;
int i = 0;
CSSParserValue* a = args->current();
@@ -5027,7 +3974,7 @@ bool CSSParser::parseClipShape(CSSPropertyID propId, bool important)
valid = a->id == CSSValueAuto || validUnit(a, FLength);
if (!valid)
break;
- RefPtr<CSSPrimitiveValue> length = a->id == CSSValueAuto ?
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> length = a->id == CSSValueAuto ?
cssValuePool().createIdentifierValue(CSSValueAuto) :
createPrimitiveNumericValue(a);
if (i == 0)
@@ -5057,235 +4004,316 @@ bool CSSParser::parseClipShape(CSSPropertyID propId, bool important)
return false;
}
-PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapeRectangle(CSSParserValueList* args)
+static void completeBorderRadii(RefPtrWillBeRawPtr<CSSPrimitiveValue> radii[4])
{
- ASSERT(args);
+ if (radii[3])
+ return;
+ if (!radii[2]) {
+ if (!radii[1])
+ radii[1] = radii[0];
+ radii[2] = radii[0];
+ }
+ radii[3] = radii[1];
+}
- // rect(x, y, width, height, [[rx], ry])
- if (args->size() != 7 && args->size() != 9 && args->size() != 11)
- return 0;
+// FIXME: This should be refactored with CSSParser::parseBorderRadius.
+// CSSParser::parseBorderRadius contains support for some legacy radius construction.
+PassRefPtrWillBeRawPtr<CSSBasicShape> CSSPropertyParser::parseInsetRoundedCorners(PassRefPtrWillBeRawPtr<CSSBasicShapeInset> shape, CSSParserValueList* args)
+{
+ CSSParserValue* argument = args->next();
- RefPtr<CSSBasicShapeRectangle> shape = CSSBasicShapeRectangle::create();
+ if (!argument)
+ return nullptr;
- unsigned argumentNumber = 0;
- CSSParserValue* argument = args->current();
+ Vector<CSSParserValue*> radiusArguments;
while (argument) {
- Units unitFlags = FLength | FPercent;
- if (argumentNumber > 1) {
- // Arguments width, height, rx, and ry cannot be negative.
- unitFlags = unitFlags | FNonNeg;
- }
- if (!validUnit(argument, unitFlags))
- return 0;
-
- RefPtr<CSSPrimitiveValue> length = createPrimitiveNumericValue(argument);
- ASSERT(argumentNumber < 6);
- switch (argumentNumber) {
- case 0:
- shape->setX(length);
- break;
- case 1:
- shape->setY(length);
- break;
- case 2:
- shape->setWidth(length);
- break;
- case 3:
- shape->setHeight(length);
- break;
- case 4:
- shape->setRadiusX(length);
- break;
- case 5:
- shape->setRadiusY(length);
- break;
- }
+ radiusArguments.append(argument);
argument = args->next();
- if (argument) {
- if (!isComma(argument))
- return 0;
+ }
- argument = args->next();
+ unsigned num = radiusArguments.size();
+ if (!num || num > 9)
+ return nullptr;
+
+ // FIXME: Refactor completeBorderRadii and the array
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> radii[2][4];
+#if ENABLE(OILPAN)
+ // Zero initialize the array of raw pointers.
+ memset(&radii, 0, sizeof(radii));
+#endif
+
+ unsigned indexAfterSlash = 0;
+ for (unsigned i = 0; i < num; ++i) {
+ CSSParserValue* value = radiusArguments.at(i);
+ if (value->unit == CSSParserValue::Operator) {
+ if (value->iValue != '/')
+ return nullptr;
+
+ if (!i || indexAfterSlash || i + 1 == num)
+ return nullptr;
+
+ indexAfterSlash = i + 1;
+ completeBorderRadii(radii[0]);
+ continue;
}
- argumentNumber++;
+
+ if (i - indexAfterSlash >= 4)
+ return nullptr;
+
+ if (!validUnit(value, FLength | FPercent | FNonNeg))
+ return nullptr;
+
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> radius = createPrimitiveNumericValue(value);
+
+ if (!indexAfterSlash)
+ radii[0][i] = radius;
+ else
+ radii[1][i - indexAfterSlash] = radius.release();
}
- if (argumentNumber < 4)
- return 0;
+ if (!indexAfterSlash) {
+ completeBorderRadii(radii[0]);
+ for (unsigned i = 0; i < 4; ++i)
+ radii[1][i] = radii[0][i];
+ } else {
+ completeBorderRadii(radii[1]);
+ }
+ shape->setTopLeftRadius(createPrimitiveValuePair(radii[0][0].release(), radii[1][0].release()));
+ shape->setTopRightRadius(createPrimitiveValuePair(radii[0][1].release(), radii[1][1].release()));
+ shape->setBottomRightRadius(createPrimitiveValuePair(radii[0][2].release(), radii[1][2].release()));
+ shape->setBottomLeftRadius(createPrimitiveValuePair(radii[0][3].release(), radii[1][3].release()));
+
return shape;
}
-PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapeInsetRectangle(CSSParserValueList* args)
+PassRefPtrWillBeRawPtr<CSSBasicShape> CSSPropertyParser::parseBasicShapeInset(CSSParserValueList* args)
{
ASSERT(args);
- // inset-rectangle(top, right, bottom, left, [[rx], ry])
- if (args->size() != 7 && args->size() != 9 && args->size() != 11)
- return 0;
-
- RefPtr<CSSBasicShapeInsetRectangle> shape = CSSBasicShapeInsetRectangle::create();
+ RefPtrWillBeRawPtr<CSSBasicShapeInset> shape = CSSBasicShapeInset::create();
- unsigned argumentNumber = 0;
CSSParserValue* argument = args->current();
+ WillBeHeapVector<RefPtrWillBeMember<CSSPrimitiveValue> > widthArguments;
+ bool hasRoundedInset = false;
+
while (argument) {
- Units unitFlags = FLength | FPercent | FNonNeg;
- if (!validUnit(argument, unitFlags))
- return 0;
-
- RefPtr<CSSPrimitiveValue> length = createPrimitiveNumericValue(argument);
- ASSERT(argumentNumber < 6);
- switch (argumentNumber) {
- case 0:
- shape->setTop(length);
- break;
- case 1:
- shape->setRight(length);
- break;
- case 2:
- shape->setBottom(length);
- break;
- case 3:
- shape->setLeft(length);
- break;
- case 4:
- shape->setRadiusX(length);
- break;
- case 5:
- shape->setRadiusY(length);
+ if (argument->unit == CSSPrimitiveValue::CSS_IDENT && equalIgnoringCase(argument->string, "round")) {
+ hasRoundedInset = true;
break;
}
+
+ Units unitFlags = FLength | FPercent;
+ if (!validUnit(argument, unitFlags) || widthArguments.size() > 4)
+ return nullptr;
+
+ widthArguments.append(createPrimitiveNumericValue(argument));
argument = args->next();
- if (argument) {
- if (!isComma(argument))
- return 0;
+ }
- argument = args->next();
+ switch (widthArguments.size()) {
+ case 1: {
+ shape->updateShapeSize1Value(widthArguments[0].get());
+ break;
+ }
+ case 2: {
+ shape->updateShapeSize2Values(widthArguments[0].get(), widthArguments[1].get());
+ break;
}
- argumentNumber++;
+ case 3: {
+ shape->updateShapeSize3Values(widthArguments[0].get(), widthArguments[1].get(), widthArguments[2].get());
+ break;
+ }
+ case 4: {
+ shape->updateShapeSize4Values(widthArguments[0].get(), widthArguments[1].get(), widthArguments[2].get(), widthArguments[3].get());
+ break;
+ }
+ default:
+ return nullptr;
}
- if (argumentNumber < 4)
- return 0;
+ if (hasRoundedInset)
+ return parseInsetRoundedCorners(shape, args);
return shape;
}
-PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapeCircle(CSSParserValueList* args)
+static bool isItemPositionKeyword(CSSValueID id)
{
- ASSERT(args);
+ return id == CSSValueStart || id == CSSValueEnd || id == CSSValueCenter
+ || id == CSSValueSelfStart || id == CSSValueSelfEnd || id == CSSValueFlexStart
+ || id == CSSValueFlexEnd || id == CSSValueLeft || id == CSSValueRight;
+}
- // circle(centerX, centerY, radius)
- if (args->size() != 5)
- return 0;
+bool CSSPropertyParser::parseItemPositionOverflowPosition(CSSPropertyID propId, bool important)
+{
+ // auto | baseline | stretch | [<item-position> && <overflow-position>? ]
+ // <item-position> = center | start | end | self-start | self-end | flex-start | flex-end | left | right;
+ // <overflow-position> = true | safe
- RefPtr<CSSBasicShapeCircle> shape = CSSBasicShapeCircle::create();
+ CSSParserValue* value = m_valueList->current();
- unsigned argumentNumber = 0;
- CSSParserValue* argument = args->current();
- while (argument) {
- Units unitFlags = FLength | FPercent;
- if (argumentNumber == 2) {
- // Argument radius cannot be negative.
- unitFlags = unitFlags | FNonNeg;
+ if (value->id == CSSValueAuto || value->id == CSSValueBaseline || value->id == CSSValueStretch) {
+ if (m_valueList->next())
+ return false;
+
+ addProperty(propId, cssValuePool().createIdentifierValue(value->id), important);
+ return true;
+ }
+
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> position = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> overflowAlignmentKeyword = nullptr;
+ if (isItemPositionKeyword(value->id)) {
+ position = cssValuePool().createIdentifierValue(value->id);
+ value = m_valueList->next();
+ if (value) {
+ if (value->id == CSSValueTrue || value->id == CSSValueSafe)
+ overflowAlignmentKeyword = cssValuePool().createIdentifierValue(value->id);
+ else
+ return false;
}
+ } else if (value->id == CSSValueTrue || value->id == CSSValueSafe) {
+ overflowAlignmentKeyword = cssValuePool().createIdentifierValue(value->id);
+ value = m_valueList->next();
+ if (value && isItemPositionKeyword(value->id))
+ position = cssValuePool().createIdentifierValue(value->id);
+ else
+ return false;
+ } else {
+ return false;
+ }
- if (!validUnit(argument, unitFlags))
- return 0;
+ if (m_valueList->next())
+ return false;
- RefPtr<CSSPrimitiveValue> length = createPrimitiveNumericValue(argument);
- ASSERT(argumentNumber < 3);
- switch (argumentNumber) {
- case 0:
- shape->setCenterX(length);
- break;
- case 1:
- shape->setCenterY(length);
- break;
- case 2:
- shape->setRadius(length);
- break;
+ ASSERT(position);
+ if (overflowAlignmentKeyword)
+ addProperty(propId, createPrimitiveValuePair(position, overflowAlignmentKeyword), important);
+ else
+ addProperty(propId, position.release(), important);
+
+ return true;
+}
+
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::parseShapeRadius(CSSParserValue* value)
+{
+ if (value->id == CSSValueClosestSide || value->id == CSSValueFarthestSide)
+ return cssValuePool().createIdentifierValue(value->id);
+
+ if (!validUnit(value, FLength | FPercent | FNonNeg))
+ return nullptr;
+
+ return createPrimitiveNumericValue(value);
+}
+
+PassRefPtrWillBeRawPtr<CSSBasicShape> CSSPropertyParser::parseBasicShapeCircle(CSSParserValueList* args)
+{
+ ASSERT(args);
+
+ // circle(radius)
+ // circle(radius at <position>)
+ // circle(at <position>)
+ // where position defines centerX and centerY using a CSS <position> data type.
+ RefPtrWillBeRawPtr<CSSBasicShapeCircle> shape = CSSBasicShapeCircle::create();
+
+ for (CSSParserValue* argument = args->current(); argument; argument = args->next()) {
+ // The call to parseFillPosition below should consume all of the
+ // arguments except the first two. Thus, and index greater than one
+ // indicates an invalid production.
+ if (args->currentIndex() > 1)
+ return nullptr;
+
+ if (!args->currentIndex() && argument->id != CSSValueAt) {
+ if (RefPtrWillBeRawPtr<CSSPrimitiveValue> radius = parseShapeRadius(argument)) {
+ shape->setRadius(radius);
+ continue;
+ }
+
+ return nullptr;
}
- argument = args->next();
- if (argument) {
- if (!isComma(argument))
- return 0;
- argument = args->next();
+ if (argument->id == CSSValueAt && args->next()) {
+ RefPtrWillBeRawPtr<CSSValue> centerX = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> centerY = nullptr;
+ parseFillPosition(args, centerX, centerY);
+ if (centerX && centerY && !args->current()) {
+ ASSERT(centerX->isPrimitiveValue());
+ ASSERT(centerY->isPrimitiveValue());
+ shape->setCenterX(toCSSPrimitiveValue(centerX.get()));
+ shape->setCenterY(toCSSPrimitiveValue(centerY.get()));
+ } else {
+ return nullptr;
+ }
+ } else {
+ return nullptr;
}
- argumentNumber++;
}
- if (argumentNumber < 3)
- return 0;
return shape;
}
-PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapeEllipse(CSSParserValueList* args)
+PassRefPtrWillBeRawPtr<CSSBasicShape> CSSPropertyParser::parseBasicShapeEllipse(CSSParserValueList* args)
{
ASSERT(args);
- // ellipse(centerX, centerY, radiusX, radiusY)
- if (args->size() != 7)
- return 0;
+ // ellipse(radiusX)
+ // ellipse(radiusX at <position>)
+ // ellipse(radiusX radiusY)
+ // ellipse(radiusX radiusY at <position>)
+ // ellipse(at <position>)
+ // where position defines centerX and centerY using a CSS <position> data type.
+ RefPtrWillBeRawPtr<CSSBasicShapeEllipse> shape = CSSBasicShapeEllipse::create();
+
+ for (CSSParserValue* argument = args->current(); argument; argument = args->next()) {
+ // The call to parseFillPosition below should consume all of the
+ // arguments except the first three. Thus, an index greater than two
+ // indicates an invalid production.
+ if (args->currentIndex() > 2)
+ return nullptr;
+
+ if (args->currentIndex() < 2 && argument->id != CSSValueAt) {
+ if (RefPtrWillBeRawPtr<CSSPrimitiveValue> radius = parseShapeRadius(argument)) {
+ if (!shape->radiusX())
+ shape->setRadiusX(radius);
+ else
+ shape->setRadiusY(radius);
+ continue;
+ }
- RefPtr<CSSBasicShapeEllipse> shape = CSSBasicShapeEllipse::create();
- unsigned argumentNumber = 0;
- CSSParserValue* argument = args->current();
- while (argument) {
- Units unitFlags = FLength | FPercent;
- if (argumentNumber > 1) {
- // Arguments radiusX and radiusY cannot be negative.
- unitFlags = unitFlags | FNonNeg;
- }
- if (!validUnit(argument, unitFlags))
- return 0;
-
- RefPtr<CSSPrimitiveValue> length = createPrimitiveNumericValue(argument);
- ASSERT(argumentNumber < 4);
- switch (argumentNumber) {
- case 0:
- shape->setCenterX(length);
- break;
- case 1:
- shape->setCenterY(length);
- break;
- case 2:
- shape->setRadiusX(length);
- break;
- case 3:
- shape->setRadiusY(length);
- break;
+ return nullptr;
}
- argument = args->next();
- if (argument) {
- if (!isComma(argument))
- return 0;
- argument = args->next();
- }
- argumentNumber++;
+ if (argument->id != CSSValueAt || !args->next()) // expecting ellipse(.. at <position>)
+ return nullptr;
+ RefPtrWillBeRawPtr<CSSValue> centerX = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> centerY = nullptr;
+ parseFillPosition(args, centerX, centerY);
+ if (!centerX || !centerY || args->current())
+ return nullptr;
+
+ ASSERT(centerX->isPrimitiveValue());
+ ASSERT(centerY->isPrimitiveValue());
+ shape->setCenterX(toCSSPrimitiveValue(centerX.get()));
+ shape->setCenterY(toCSSPrimitiveValue(centerY.get()));
}
- if (argumentNumber < 4)
- return 0;
return shape;
}
-PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapePolygon(CSSParserValueList* args)
+PassRefPtrWillBeRawPtr<CSSBasicShape> CSSPropertyParser::parseBasicShapePolygon(CSSParserValueList* args)
{
ASSERT(args);
unsigned size = args->size();
if (!size)
- return 0;
+ return nullptr;
- RefPtr<CSSBasicShapePolygon> shape = CSSBasicShapePolygon::create();
+ RefPtrWillBeRawPtr<CSSBasicShapePolygon> shape = CSSBasicShapePolygon::create();
CSSParserValue* argument = args->current();
if (argument->id == CSSValueEvenodd || argument->id == CSSValueNonzero) {
shape->setWindRule(argument->id == CSSValueEvenodd ? RULE_EVENODD : RULE_NONZERO);
if (!isComma(args->next()))
- return 0;
+ return nullptr;
argument = args->next();
size -= 2;
@@ -5293,19 +4321,20 @@ PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapePolygon(CSSParserValueList*
// <length> <length>, ... <length> <length> -> each pair has 3 elements except the last one
if (!size || (size % 3) - 2)
- return 0;
+ return nullptr;
CSSParserValue* argumentX = argument;
while (argumentX) {
+
if (!validUnit(argumentX, FLength | FPercent))
- return 0;
+ return nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> xLength = createPrimitiveNumericValue(argumentX);
CSSParserValue* argumentY = args->next();
if (!argumentY || !validUnit(argumentY, FLength | FPercent))
- return 0;
+ return nullptr;
- RefPtr<CSSPrimitiveValue> xLength = createPrimitiveNumericValue(argumentX);
- RefPtr<CSSPrimitiveValue> yLength = createPrimitiveNumericValue(argumentY);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> yLength = createPrimitiveNumericValue(argumentY);
shape->appendPoint(xLength.release(), yLength.release());
@@ -5313,7 +4342,7 @@ PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapePolygon(CSSParserValueList*
if (!commaOrNull)
argumentX = 0;
else if (!isComma(commaOrNull))
- return 0;
+ return nullptr;
else
argumentX = args->next();
}
@@ -5321,37 +4350,109 @@ PassRefPtr<CSSBasicShape> CSSParser::parseBasicShapePolygon(CSSParserValueList*
return shape;
}
-bool CSSParser::parseBasicShape(CSSPropertyID propId, bool important)
+static bool isBoxValue(CSSValueID valueId)
+{
+ switch (valueId) {
+ case CSSValueContentBox:
+ case CSSValuePaddingBox:
+ case CSSValueBorderBox:
+ case CSSValueMarginBox:
+ return true;
+ default:
+ break;
+ }
+
+ return false;
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseShapeProperty(CSSPropertyID propId)
+{
+ if (!RuntimeEnabledFeatures::cssShapesEnabled())
+ return nullptr;
+
+ CSSParserValue* value = m_valueList->current();
+ CSSValueID valueId = value->id;
+
+ if (valueId == CSSValueNone) {
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> keywordValue = parseValidPrimitive(valueId, value);
+ m_valueList->next();
+ return keywordValue.release();
+ }
+
+ RefPtrWillBeRawPtr<CSSValue> imageValue = nullptr;
+ if (valueId != CSSValueNone && parseFillImage(m_valueList.get(), imageValue)) {
+ m_valueList->next();
+ return imageValue.release();
+ }
+
+ return parseBasicShapeAndOrBox();
+}
+
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseBasicShapeAndOrBox()
+{
+ CSSParserValue* value = m_valueList->current();
+
+ bool shapeFound = false;
+ bool boxFound = false;
+ CSSValueID valueId;
+
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ for (unsigned i = 0; i < 2; ++i) {
+ if (!value)
+ break;
+ valueId = value->id;
+ if (value->unit == CSSParserValue::Function && !shapeFound) {
+ // parseBasicShape already asks for the next value list item.
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> shapeValue = parseBasicShape();
+ if (!shapeValue)
+ return nullptr;
+ list->append(shapeValue.release());
+ shapeFound = true;
+ } else if (isBoxValue(valueId) && !boxFound) {
+ list->append(parseValidPrimitive(valueId, value));
+ boxFound = true;
+ m_valueList->next();
+ } else {
+ return nullptr;
+ }
+
+ value = m_valueList->current();
+ }
+
+ if (m_valueList->current())
+ return nullptr;
+ return list.release();
+}
+
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::parseBasicShape()
{
CSSParserValue* value = m_valueList->current();
ASSERT(value->unit == CSSParserValue::Function);
CSSParserValueList* args = value->function->args.get();
if (!args)
- return false;
+ return nullptr;
- RefPtr<CSSBasicShape> shape;
- if (equalIgnoringCase(value->function->name, "rectangle("))
- shape = parseBasicShapeRectangle(args);
- else if (equalIgnoringCase(value->function->name, "circle("))
+ RefPtrWillBeRawPtr<CSSBasicShape> shape = nullptr;
+ if (equalIgnoringCase(value->function->name, "circle("))
shape = parseBasicShapeCircle(args);
else if (equalIgnoringCase(value->function->name, "ellipse("))
shape = parseBasicShapeEllipse(args);
else if (equalIgnoringCase(value->function->name, "polygon("))
shape = parseBasicShapePolygon(args);
- else if (equalIgnoringCase(value->function->name, "inset-rectangle("))
- shape = parseBasicShapeInsetRectangle(args);
+ else if (equalIgnoringCase(value->function->name, "inset("))
+ shape = parseBasicShapeInset(args);
if (!shape)
- return false;
+ return nullptr;
- addProperty(propId, cssValuePool().createValue(shape.release()), important);
m_valueList->next();
- return true;
+
+ return cssValuePool().createValue(shape.release());
}
// [ 'font-style' || 'font-variant' || 'font-weight' ]? 'font-size' [ / 'line-height' ]? 'font-family'
-bool CSSParser::parseFont(bool important)
+bool CSSPropertyParser::parseFont(bool important)
{
// Let's check if there is an inherit or initial somewhere in the shorthand.
for (unsigned i = 0; i < m_valueList->size(); ++i) {
@@ -5410,7 +4511,7 @@ bool CSSParser::parseFont(bool important)
addProperty(CSSPropertyLineHeight, cssValuePool().createIdentifierValue(CSSValueNormal), important, true);
// Font family must come now.
- RefPtr<CSSValue> parsedFamilyValue = parseFontFamily();
+ RefPtrWillBeRawPtr<CSSValue> parsedFamilyValue = parseFontFamily();
if (!parsedFamilyValue)
return false;
@@ -5426,6 +4527,7 @@ bool CSSParser::parseFont(bool important)
}
class FontFamilyValueBuilder {
+ DISALLOW_ALLOCATION();
public:
FontFamilyValueBuilder(CSSValueList* list)
: m_list(list)
@@ -5458,9 +4560,9 @@ private:
CSSValueList* m_list;
};
-PassRefPtr<CSSValueList> CSSParser::parseFontFamily()
+PassRefPtrWillBeRawPtr<CSSValueList> CSSPropertyParser::parseFontFamily()
{
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
CSSParserValue* value = m_valueList->current();
FontFamilyValueBuilder familyBuilder(list.get());
@@ -5474,8 +4576,7 @@ PassRefPtr<CSSValueList> CSSParser::parseFontFamily()
((nextValue->id >= CSSValueSerif && nextValue->id <= CSSValueWebkitBody) ||
(nextValue->unit == CSSPrimitiveValue::CSS_STRING || nextValue->unit == CSSPrimitiveValue::CSS_IDENT));
- bool valueIsKeyword = value->id == CSSValueInitial || value->id == CSSValueInherit || value->id == CSSValueDefault;
- if (valueIsKeyword && !inFamily) {
+ if (isCSSWideKeyword(*value) && !inFamily) {
if (nextValBreaksFont)
value = m_valueList->next();
else if (nextValIsFontName)
@@ -5528,11 +4629,11 @@ PassRefPtr<CSSValueList> CSSParser::parseFontFamily()
familyBuilder.commit();
if (!list->length())
- list = 0;
+ list = nullptr;
return list.release();
}
-bool CSSParser::parseLineHeight(bool important)
+bool CSSPropertyParser::parseLineHeight(bool important)
{
CSSParserValue* value = m_valueList->current();
CSSValueID id = value->id;
@@ -5547,7 +4648,7 @@ bool CSSParser::parseLineHeight(bool important)
return validPrimitive;
}
-bool CSSParser::parseFontSize(bool important)
+bool CSSPropertyParser::parseFontSize(bool important)
{
CSSParserValue* value = m_valueList->current();
CSSValueID id = value->id;
@@ -5562,20 +4663,23 @@ bool CSSParser::parseFontSize(bool important)
return validPrimitive;
}
-bool CSSParser::parseFontVariant(bool important)
+bool CSSPropertyParser::parseFontVariant(bool important)
{
- RefPtr<CSSValueList> values;
+ RefPtrWillBeRawPtr<CSSValueList> values = nullptr;
if (m_valueList->size() > 1)
values = CSSValueList::createCommaSeparated();
CSSParserValue* val;
bool expectComma = false;
while ((val = m_valueList->current())) {
- RefPtr<CSSPrimitiveValue> parsedValue;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedValue = nullptr;
if (!expectComma) {
expectComma = true;
if (val->id == CSSValueNormal || val->id == CSSValueSmallCaps)
parsedValue = cssValuePool().createIdentifierValue(val->id);
else if (val->id == CSSValueAll && !values) {
+ // FIXME: CSSPropertyParser::parseFontVariant() implements
+ // the old css3 draft:
+ // http://www.w3.org/TR/2002/WD-css3-webfonts-20020802/#font-variant
// 'all' is only allowed in @font-face and with no other values. Make a value list to
// indicate that we are in the @font-face case.
values = CSSValueList::createCommaSeparated();
@@ -5601,7 +4705,8 @@ bool CSSParser::parseFontVariant(bool important)
}
if (values && values->length()) {
- m_hasFontFaceOnlyValues = true;
+ if (m_ruleType != CSSRuleSourceData::FONT_FACE_RULE)
+ return false;
addProperty(CSSPropertyFontVariant, values.release(), important);
return true;
}
@@ -5609,7 +4714,7 @@ bool CSSParser::parseFontVariant(bool important)
return false;
}
-bool CSSParser::parseFontWeight(bool important)
+bool CSSPropertyParser::parseFontWeight(bool important)
{
CSSParserValue* value = m_valueList->current();
if ((value->id >= CSSValueNormal) && (value->id <= CSSValue900)) {
@@ -5626,9 +4731,10 @@ bool CSSParser::parseFontWeight(bool important)
return false;
}
-bool CSSParser::parseFontFaceSrcURI(CSSValueList* valueList)
+bool CSSPropertyParser::parseFontFaceSrcURI(CSSValueList* valueList)
{
- RefPtr<CSSFontFaceSrcValue> uriValue(CSSFontFaceSrcValue::create(completeURL(m_valueList->current()->string)));
+ RefPtrWillBeRawPtr<CSSFontFaceSrcValue> uriValue(CSSFontFaceSrcValue::create(completeURL(m_valueList->current()->string)));
+ uriValue->setReferrer(m_context.referrer());
CSSParserValue* value = m_valueList->next();
if (!value) {
@@ -5657,7 +4763,7 @@ bool CSSParser::parseFontFaceSrcURI(CSSValueList* valueList)
return true;
}
-bool CSSParser::parseFontFaceSrcLocal(CSSValueList* valueList)
+bool CSSPropertyParser::parseFontFaceSrcLocal(CSSValueList* valueList)
{
CSSParserValueList* args = m_valueList->current()->function->args.get();
if (!args || !args->size())
@@ -5685,9 +4791,9 @@ bool CSSParser::parseFontFaceSrcLocal(CSSValueList* valueList)
return true;
}
-bool CSSParser::parseFontFaceSrc()
+bool CSSPropertyParser::parseFontFaceSrc()
{
- RefPtr<CSSValueList> values(CSSValueList::createCommaSeparated());
+ RefPtrWillBeRawPtr<CSSValueList> values(CSSValueList::createCommaSeparated());
while (CSSParserValue* value = m_valueList->current()) {
if (value->unit == CSSPrimitiveValue::CSS_URI) {
@@ -5707,9 +4813,9 @@ bool CSSParser::parseFontFaceSrc()
return true;
}
-bool CSSParser::parseFontFaceUnicodeRange()
+bool CSSPropertyParser::parseFontFaceUnicodeRange()
{
- RefPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
bool failed = false;
bool operatorExpected = false;
for (; m_valueList->current(); m_valueList->next(), operatorExpected = !operatorExpected) {
@@ -5869,7 +4975,7 @@ static int parseDouble(const CharacterType* string, const CharacterType* end, co
}
template <typename CharacterType>
-static bool parseColorIntOrPercentage(const CharacterType*& string, const CharacterType* end, const char terminator, CSSPrimitiveValue::UnitTypes& expect, int& value)
+static bool parseColorIntOrPercentage(const CharacterType*& string, const CharacterType* end, const char terminator, CSSPrimitiveValue::UnitType& expect, int& value)
{
const CharacterType* current = string;
double localValue = 0;
@@ -6028,16 +5134,14 @@ static inline bool mightBeRGB(const CharacterType* characters, unsigned length)
template <typename CharacterType>
static inline bool fastParseColorInternal(RGBA32& rgb, const CharacterType* characters, unsigned length , bool strict)
{
- CSSPrimitiveValue::UnitTypes expect = CSSPrimitiveValue::CSS_UNKNOWN;
+ CSSPrimitiveValue::UnitType expect = CSSPrimitiveValue::CSS_UNKNOWN;
+
+ if (length >= 4 && characters[0] == '#')
+ return Color::parseHexColor(characters + 1, length - 1, rgb);
if (!strict && length >= 3) {
- if (characters[0] == '#') {
- if (Color::parseHexColor(characters + 1, length - 1, rgb))
- return true;
- } else {
- if (Color::parseHexColor(characters, length, rgb))
- return true;
- }
+ if (Color::parseHexColor(characters, length, rgb))
+ return true;
}
// Try rgba() syntax.
@@ -6086,7 +5190,7 @@ static inline bool fastParseColorInternal(RGBA32& rgb, const CharacterType* char
}
template<typename StringType>
-bool CSSParser::fastParseColor(RGBA32& rgb, const StringType& name, bool strict)
+bool CSSPropertyParser::fastParseColor(RGBA32& rgb, const StringType& name, bool strict)
{
unsigned length = name.length();
bool parseResult;
@@ -6104,15 +5208,15 @@ bool CSSParser::fastParseColor(RGBA32& rgb, const StringType& name, bool strict)
// Try named colors.
Color tc;
- tc.setNamedColor(name);
- if (tc.isValid()) {
- rgb = tc.rgb();
- return true;
- }
- return false;
+ if (!tc.setNamedColor(name))
+ return false;
+ rgb = tc.rgb();
+ return true;
}
-inline double CSSParser::parsedDouble(CSSParserValue *v, ReleaseParsedCalcValueCondition releaseCalc)
+template bool CSSPropertyParser::fastParseColor(RGBA32&, const String&, bool strict);
+
+inline double CSSPropertyParser::parsedDouble(CSSParserValue *v, ReleaseParsedCalcValueCondition releaseCalc)
{
const double result = m_parsedCalculation ? m_parsedCalculation->doubleValue() : v->fValue;
if (releaseCalc == ReleaseParsedCalcValue)
@@ -6120,7 +5224,7 @@ inline double CSSParser::parsedDouble(CSSParserValue *v, ReleaseParsedCalcValueC
return result;
}
-bool CSSParser::isCalculation(CSSParserValue* value)
+bool CSSPropertyParser::isCalculation(CSSParserValue* value)
{
return (value->unit == CSSParserValue::Function)
&& (equalIgnoringCase(value->function->name, "calc(")
@@ -6129,7 +5233,7 @@ bool CSSParser::isCalculation(CSSParserValue* value)
|| equalIgnoringCase(value->function->name, "-webkit-max("));
}
-inline int CSSParser::colorIntFromValue(CSSParserValue* v)
+inline int CSSPropertyParser::colorIntFromValue(CSSParserValue* v)
{
bool isPercent;
@@ -6155,7 +5259,7 @@ inline int CSSParser::colorIntFromValue(CSSParserValue* v)
return static_cast<int>(value);
}
-bool CSSParser::parseColorParameters(CSSParserValue* value, int* colorArray, bool parseAlpha)
+bool CSSPropertyParser::parseColorParameters(CSSParserValue* value, int* colorArray, bool parseAlpha)
{
CSSParserValueList* args = value->function->args.get();
CSSParserValue* v = args->current();
@@ -6188,7 +5292,7 @@ bool CSSParser::parseColorParameters(CSSParserValue* value, int* colorArray, boo
const double value = parsedDouble(v, ReleaseParsedCalcValue);
// Convert the floating pointer number of alpha to an integer in the range [0, 256),
// with an equal distribution across all 256 values.
- colorArray[3] = static_cast<int>(max(0.0, min(1.0, value)) * nextafter(256.0, 0.0));
+ colorArray[3] = static_cast<int>(std::max(0.0, std::min(1.0, value)) * nextafter(256.0, 0.0));
}
return true;
}
@@ -6198,7 +5302,7 @@ bool CSSParser::parseColorParameters(CSSParserValue* value, int* colorArray, boo
// and with alpha, the format is
// hsla(<number>, <percent>, <percent>, <number>)
// The first value, HUE, is in an angle with a value between 0 and 360
-bool CSSParser::parseHSLParameters(CSSParserValue* value, double* colorArray, bool parseAlpha)
+bool CSSPropertyParser::parseHSLParameters(CSSParserValue* value, double* colorArray, bool parseAlpha)
{
CSSParserValueList* args = value->function->args.get();
CSSParserValue* v = args->current();
@@ -6214,7 +5318,7 @@ bool CSSParser::parseHSLParameters(CSSParserValue* value, double* colorArray, bo
v = args->next();
if (!validUnit(v, FPercent, HTMLStandardMode))
return false;
- colorArray[i] = max(0.0, min(100.0, parsedDouble(v, ReleaseParsedCalcValue))) / 100.0; // needs to be value between 0 and 1.0
+ colorArray[i] = std::max(0.0, std::min(100.0, parsedDouble(v, ReleaseParsedCalcValue))) / 100.0; // needs to be value between 0 and 1.0
}
if (parseAlpha) {
v = args->next();
@@ -6223,20 +5327,20 @@ bool CSSParser::parseHSLParameters(CSSParserValue* value, double* colorArray, bo
v = args->next();
if (!validUnit(v, FNumber, HTMLStandardMode))
return false;
- colorArray[3] = max(0.0, min(1.0, parsedDouble(v, ReleaseParsedCalcValue)));
+ colorArray[3] = std::max(0.0, std::min(1.0, parsedDouble(v, ReleaseParsedCalcValue)));
}
return true;
}
-PassRefPtr<CSSPrimitiveValue> CSSParser::parseColor(CSSParserValue* value)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> CSSPropertyParser::parseColor(CSSParserValue* value)
{
RGBA32 c = Color::transparent;
if (!parseColorFromValue(value ? value : m_valueList->current(), c))
- return 0;
+ return nullptr;
return cssValuePool().createColorValue(c);
}
-bool CSSParser::parseColorFromValue(CSSParserValue* value, RGBA32& c)
+bool CSSPropertyParser::parseColorFromValue(CSSParserValue* value, RGBA32& c)
{
if (inQuirksMode() && value->unit == CSSPrimitiveValue::CSS_NUMBER
&& value->fValue >= 0. && value->fValue < 1000000.) {
@@ -6291,8 +5395,10 @@ bool CSSParser::parseColorFromValue(CSSParserValue* value, RGBA32& c)
// This class tracks parsing state for shadow values. If it goes out of scope (e.g., due to an early return)
// without the allowBreak bit being set, then it will clean up all of the objects and destroy them.
-struct ShadowParseContext {
- ShadowParseContext(CSSPropertyID prop, CSSParser* parser)
+class ShadowParseContext {
+ STACK_ALLOCATED();
+public:
+ ShadowParseContext(CSSPropertyID prop, CSSPropertyParser* parser)
: property(prop)
, m_parser(parser)
, allowX(true)
@@ -6319,12 +5425,12 @@ struct ShadowParseContext {
}
// Now reset for the next shadow value.
- x = 0;
- y = 0;
- blur = 0;
- spread = 0;
- style = 0;
- color = 0;
+ x = nullptr;
+ y = nullptr;
+ blur = nullptr;
+ spread = nullptr;
+ style = nullptr;
+ color = nullptr;
allowX = true;
allowColor = true;
@@ -6337,7 +5443,7 @@ struct ShadowParseContext {
void commitLength(CSSParserValue* v)
{
- RefPtr<CSSPrimitiveValue> val = m_parser->createPrimitiveNumericValue(v);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> val = m_parser->createPrimitiveNumericValue(v);
if (allowX) {
x = val.release();
@@ -6363,7 +5469,7 @@ struct ShadowParseContext {
}
}
- void commitColor(PassRefPtr<CSSPrimitiveValue> val)
+ void commitColor(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val)
{
color = val;
allowColor = false;
@@ -6391,15 +5497,15 @@ struct ShadowParseContext {
}
CSSPropertyID property;
- CSSParser* m_parser;
+ CSSPropertyParser* m_parser;
- RefPtr<CSSValueList> values;
- RefPtr<CSSPrimitiveValue> x;
- RefPtr<CSSPrimitiveValue> y;
- RefPtr<CSSPrimitiveValue> blur;
- RefPtr<CSSPrimitiveValue> spread;
- RefPtr<CSSPrimitiveValue> style;
- RefPtr<CSSPrimitiveValue> color;
+ RefPtrWillBeMember<CSSValueList> values;
+ RefPtrWillBeMember<CSSPrimitiveValue> x;
+ RefPtrWillBeMember<CSSPrimitiveValue> y;
+ RefPtrWillBeMember<CSSPrimitiveValue> blur;
+ RefPtrWillBeMember<CSSPrimitiveValue> spread;
+ RefPtrWillBeMember<CSSPrimitiveValue> style;
+ RefPtrWillBeMember<CSSPrimitiveValue> color;
bool allowX;
bool allowY;
@@ -6410,44 +5516,45 @@ struct ShadowParseContext {
bool allowBreak;
};
-PassRefPtr<CSSValueList> CSSParser::parseShadow(CSSParserValueList* valueList, CSSPropertyID propId)
+PassRefPtrWillBeRawPtr<CSSValueList> CSSPropertyParser::parseShadow(CSSParserValueList* valueList, CSSPropertyID propId)
{
ShadowParseContext context(propId, this);
CSSParserValue* val;
while ((val = valueList->current())) {
// Check for a comma break first.
if (val->unit == CSSParserValue::Operator) {
- if (val->iValue != ',' || !context.allowBreak)
+ if (val->iValue != ',' || !context.allowBreak) {
// Other operators aren't legal or we aren't done with the current shadow
// value. Treat as invalid.
- return 0;
+ return nullptr;
+ }
// The value is good. Commit it.
context.commitValue();
} else if (validUnit(val, FLength, HTMLStandardMode)) {
// We required a length and didn't get one. Invalid.
if (!context.allowLength())
- return 0;
+ return nullptr;
// Blur radius must be non-negative.
if (context.allowBlur && !validUnit(val, FLength | FNonNeg, HTMLStandardMode))
- return 0;
+ return nullptr;
// A length is allowed here. Construct the value and add it.
context.commitLength(val);
} else if (val->id == CSSValueInset) {
if (!context.allowStyle)
- return 0;
+ return nullptr;
context.commitStyle(val);
} else {
// The only other type of value that's ok is a color value.
- RefPtr<CSSPrimitiveValue> parsedColor;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> parsedColor = nullptr;
bool isColor = ((val->id >= CSSValueAqua && val->id <= CSSValueWindowtext) || val->id == CSSValueMenu
|| (val->id >= CSSValueWebkitFocusRingColor && val->id <= CSSValueWebkitText && inQuirksMode())
|| val->id == CSSValueCurrentcolor);
if (isColor) {
if (!context.allowColor)
- return 0;
+ return nullptr;
parsedColor = cssValuePool().createIdentifierValue(val->id);
}
@@ -6456,7 +5563,7 @@ PassRefPtr<CSSValueList> CSSParser::parseShadow(CSSParserValueList* valueList, C
parsedColor = parseColor(val);
if (!parsedColor || !context.allowColor)
- return 0; // This value is not a color or length and is invalid or
+ return nullptr; // This value is not a color or length and is invalid or
// it is a color, but a color isn't allowed at this point.
context.commitColor(parsedColor.release());
@@ -6471,33 +5578,30 @@ PassRefPtr<CSSValueList> CSSParser::parseShadow(CSSParserValueList* valueList, C
return context.values.release();
}
- return 0;
+ return nullptr;
}
-bool CSSParser::parseReflect(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseReflect(CSSPropertyID propId, bool important)
{
// box-reflect: <direction> <offset> <mask>
// Direction comes first.
CSSParserValue* val = m_valueList->current();
- RefPtr<CSSPrimitiveValue> direction;
- if (val->unit == CSSPrimitiveValue::CSS_VARIABLE_NAME)
- direction = createPrimitiveVariableNameValue(val);
- else
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> direction = nullptr;
switch (val->id) {
- case CSSValueAbove:
- case CSSValueBelow:
- case CSSValueLeft:
- case CSSValueRight:
- direction = cssValuePool().createIdentifierValue(val->id);
- break;
- default:
- return false;
+ case CSSValueAbove:
+ case CSSValueBelow:
+ case CSSValueLeft:
+ case CSSValueRight:
+ direction = cssValuePool().createIdentifierValue(val->id);
+ break;
+ default:
+ return false;
}
// The offset comes next.
val = m_valueList->next();
- RefPtr<CSSPrimitiveValue> offset;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> offset = nullptr;
if (!val)
offset = cssValuePool().createValue(0, CSSPrimitiveValue::CSS_PX);
else {
@@ -6507,7 +5611,7 @@ bool CSSParser::parseReflect(CSSPropertyID propId, bool important)
}
// Now for the mask.
- RefPtr<CSSValue> mask;
+ RefPtrWillBeRawPtr<CSSValue> mask = nullptr;
val = m_valueList->next();
if (val) {
mask = parseBorderImage(propId);
@@ -6515,20 +5619,20 @@ bool CSSParser::parseReflect(CSSPropertyID propId, bool important)
return false;
}
- RefPtr<CSSReflectValue> reflectValue = CSSReflectValue::create(direction.release(), offset.release(), mask.release());
+ RefPtrWillBeRawPtr<CSSReflectValue> reflectValue = CSSReflectValue::create(direction.release(), offset.release(), mask.release());
addProperty(propId, reflectValue.release(), important);
m_valueList->next();
return true;
}
-bool CSSParser::parseFlex(CSSParserValueList* args, bool important)
+bool CSSPropertyParser::parseFlex(CSSParserValueList* args, bool important)
{
if (!args || !args->size() || args->size() > 3)
return false;
static const double unsetValue = -1;
double flexGrow = unsetValue;
double flexShrink = unsetValue;
- RefPtr<CSSPrimitiveValue> flexBasis;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> flexBasis = nullptr;
while (CSSParserValue* arg = args->current()) {
if (validUnit(arg, FNumber | FNonNeg)) {
@@ -6565,10 +5669,10 @@ bool CSSParser::parseFlex(CSSParserValueList* args, bool important)
return true;
}
-bool CSSParser::parseObjectPosition(bool important)
+bool CSSPropertyParser::parseObjectPosition(bool important)
{
- RefPtr<CSSValue> xValue;
- RefPtr<CSSValue> yValue;
+ RefPtrWillBeRawPtr<CSSValue> xValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> yValue = nullptr;
parseFillPosition(m_valueList.get(), xValue, yValue);
if (!xValue || !yValue)
return false;
@@ -6579,7 +5683,9 @@ bool CSSParser::parseObjectPosition(bool important)
return true;
}
-struct BorderImageParseContext {
+class BorderImageParseContext {
+ STACK_ALLOCATED();
+public:
BorderImageParseContext()
: m_canAdvance(false)
, m_allowCommit(true)
@@ -6603,7 +5709,7 @@ struct BorderImageParseContext {
bool requireWidth() const { return m_requireWidth; }
bool requireOutset() const { return m_requireOutset; }
- void commitImage(PassRefPtr<CSSValue> image)
+ void commitImage(PassRefPtrWillBeRawPtr<CSSValue> image)
{
m_image = image;
m_canAdvance = true;
@@ -6612,7 +5718,7 @@ struct BorderImageParseContext {
m_allowImageSlice = !m_imageSlice;
m_allowRepeat = !m_repeat;
}
- void commitImageSlice(PassRefPtr<CSSBorderImageSliceValue> slice)
+ void commitImageSlice(PassRefPtrWillBeRawPtr<CSSBorderImageSliceValue> slice)
{
m_imageSlice = slice;
m_canAdvance = true;
@@ -6633,7 +5739,7 @@ struct BorderImageParseContext {
m_requireWidth = false;
}
}
- void commitBorderWidth(PassRefPtr<CSSPrimitiveValue> slice)
+ void commitBorderWidth(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> slice)
{
m_borderSlice = slice;
m_canAdvance = true;
@@ -6642,7 +5748,7 @@ struct BorderImageParseContext {
m_allowImage = !m_image;
m_allowRepeat = !m_repeat;
}
- void commitBorderOutset(PassRefPtr<CSSPrimitiveValue> outset)
+ void commitBorderOutset(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> outset)
{
m_outset = outset;
m_canAdvance = true;
@@ -6651,7 +5757,7 @@ struct BorderImageParseContext {
m_allowImage = !m_image;
m_allowRepeat = !m_repeat;
}
- void commitRepeat(PassRefPtr<CSSValue> repeat)
+ void commitRepeat(PassRefPtrWillBeRawPtr<CSSValue> repeat)
{
m_repeat = repeat;
m_canAdvance = true;
@@ -6661,30 +5767,30 @@ struct BorderImageParseContext {
m_allowImage = !m_image;
}
- PassRefPtr<CSSValue> commitCSSValue()
+ PassRefPtrWillBeRawPtr<CSSValue> commitCSSValue()
{
- return createBorderImageValue(m_image, m_imageSlice, m_borderSlice, m_outset, m_repeat);
+ return createBorderImageValue(m_image, m_imageSlice.get(), m_borderSlice.get(), m_outset.get(), m_repeat.get());
}
- void commitMaskBoxImage(CSSParser* parser, bool important)
+ void commitMaskBoxImage(CSSPropertyParser* parser, bool important)
{
commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageSource, parser, m_image, important);
- commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageSlice, parser, m_imageSlice, important);
- commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageWidth, parser, m_borderSlice, important);
- commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageOutset, parser, m_outset, important);
- commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageRepeat, parser, m_repeat, important);
+ commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageSlice, parser, m_imageSlice.get(), important);
+ commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageWidth, parser, m_borderSlice.get(), important);
+ commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageOutset, parser, m_outset.get(), important);
+ commitBorderImageProperty(CSSPropertyWebkitMaskBoxImageRepeat, parser, m_repeat.get(), important);
}
- void commitBorderImage(CSSParser* parser, bool important)
+ void commitBorderImage(CSSPropertyParser* parser, bool important)
{
commitBorderImageProperty(CSSPropertyBorderImageSource, parser, m_image, important);
- commitBorderImageProperty(CSSPropertyBorderImageSlice, parser, m_imageSlice, important);
- commitBorderImageProperty(CSSPropertyBorderImageWidth, parser, m_borderSlice, important);
- commitBorderImageProperty(CSSPropertyBorderImageOutset, parser, m_outset, important);
+ commitBorderImageProperty(CSSPropertyBorderImageSlice, parser, m_imageSlice.get(), important);
+ commitBorderImageProperty(CSSPropertyBorderImageWidth, parser, m_borderSlice.get(), important);
+ commitBorderImageProperty(CSSPropertyBorderImageOutset, parser, m_outset.get(), important);
commitBorderImageProperty(CSSPropertyBorderImageRepeat, parser, m_repeat, important);
}
- void commitBorderImageProperty(CSSPropertyID propId, CSSParser* parser, PassRefPtr<CSSValue> value, bool important)
+ void commitBorderImageProperty(CSSPropertyID propId, CSSPropertyParser* parser, PassRefPtrWillBeRawPtr<CSSValue> value, bool important)
{
if (value)
parser->addProperty(propId, value, important);
@@ -6692,6 +5798,8 @@ struct BorderImageParseContext {
parser->addProperty(propId, cssValuePool().createImplicitInitialValue(), important, true);
}
+ static bool buildFromParser(CSSPropertyParser&, CSSPropertyID, BorderImageParseContext&);
+
bool m_canAdvance;
bool m_allowCommit;
@@ -6703,17 +5811,17 @@ struct BorderImageParseContext {
bool m_requireWidth;
bool m_requireOutset;
- RefPtr<CSSValue> m_image;
- RefPtr<CSSBorderImageSliceValue> m_imageSlice;
- RefPtr<CSSPrimitiveValue> m_borderSlice;
- RefPtr<CSSPrimitiveValue> m_outset;
+ RefPtrWillBeMember<CSSValue> m_image;
+ RefPtrWillBeMember<CSSBorderImageSliceValue> m_imageSlice;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_borderSlice;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_outset;
- RefPtr<CSSValue> m_repeat;
+ RefPtrWillBeMember<CSSValue> m_repeat;
};
-static bool buildBorderImageParseContext(CSSParser& parser, CSSPropertyID propId, BorderImageParseContext& context)
+bool BorderImageParseContext::buildFromParser(CSSPropertyParser& parser, CSSPropertyID propId, BorderImageParseContext& context)
{
- ShorthandScope scope(&parser, propId);
+ CSSPropertyParser::ShorthandScope scope(&parser, propId);
while (CSSParserValue* val = parser.m_valueList->current()) {
context.setCanAdvance(false);
@@ -6722,15 +5830,15 @@ static bool buildBorderImageParseContext(CSSParser& parser, CSSPropertyID propId
if (!context.canAdvance() && context.allowImage()) {
if (val->unit == CSSPrimitiveValue::CSS_URI) {
- context.commitImage(CSSImageValue::create(parser.completeURL(parser.m_context, val->string)));
+ context.commitImage(parser.createCSSImageValueWithReferrer(val->string, parser.m_context.completeURL(val->string)));
} else if (isGeneratedImageValue(val)) {
- RefPtr<CSSValue> value;
+ RefPtrWillBeRawPtr<CSSValue> value = nullptr;
if (parser.parseGeneratedImage(parser.m_valueList.get(), value))
context.commitImage(value.release());
else
return false;
} else if (val->unit == CSSParserValue::Function && equalIgnoringCase(val->function->name, "-webkit-image-set(")) {
- RefPtr<CSSValue> value = parser.parseImageSet(parser.m_valueList.get());
+ RefPtrWillBeRawPtr<CSSValue> value = parser.parseImageSet(parser.m_valueList.get());
if (value)
context.commitImage(value.release());
else
@@ -6740,25 +5848,25 @@ static bool buildBorderImageParseContext(CSSParser& parser, CSSPropertyID propId
}
if (!context.canAdvance() && context.allowImageSlice()) {
- RefPtr<CSSBorderImageSliceValue> imageSlice;
+ RefPtrWillBeRawPtr<CSSBorderImageSliceValue> imageSlice = nullptr;
if (parser.parseBorderImageSlice(propId, imageSlice))
context.commitImageSlice(imageSlice.release());
}
if (!context.canAdvance() && context.allowRepeat()) {
- RefPtr<CSSValue> repeat;
+ RefPtrWillBeRawPtr<CSSValue> repeat = nullptr;
if (parser.parseBorderImageRepeat(repeat))
context.commitRepeat(repeat.release());
}
if (!context.canAdvance() && context.requireWidth()) {
- RefPtr<CSSPrimitiveValue> borderSlice;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> borderSlice = nullptr;
if (parser.parseBorderImageWidth(borderSlice))
context.commitBorderWidth(borderSlice.release());
}
if (!context.canAdvance() && context.requireOutset()) {
- RefPtr<CSSPrimitiveValue> borderOutset;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> borderOutset = nullptr;
if (parser.parseBorderImageOutset(borderOutset))
context.commitBorderOutset(borderOutset.release());
}
@@ -6772,10 +5880,10 @@ static bool buildBorderImageParseContext(CSSParser& parser, CSSPropertyID propId
return context.allowCommit();
}
-bool CSSParser::parseBorderImageShorthand(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseBorderImageShorthand(CSSPropertyID propId, bool important)
{
BorderImageParseContext context;
- if (buildBorderImageParseContext(*this, propId, context)) {
+ if (BorderImageParseContext::buildFromParser(*this, propId, context)) {
switch (propId) {
case CSSPropertyWebkitMaskBoxImage:
context.commitMaskBoxImage(this, important);
@@ -6791,13 +5899,13 @@ bool CSSParser::parseBorderImageShorthand(CSSPropertyID propId, bool important)
return false;
}
-PassRefPtr<CSSValue> CSSParser::parseBorderImage(CSSPropertyID propId)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseBorderImage(CSSPropertyID propId)
{
BorderImageParseContext context;
- if (buildBorderImageParseContext(*this, propId, context)) {
+ if (BorderImageParseContext::buildFromParser(*this, propId, context)) {
return context.commitCSSValue();
}
- return 0;
+ return nullptr;
}
static bool isBorderImageRepeatKeyword(int id)
@@ -6805,10 +5913,10 @@ static bool isBorderImageRepeatKeyword(int id)
return id == CSSValueStretch || id == CSSValueRepeat || id == CSSValueSpace || id == CSSValueRound;
}
-bool CSSParser::parseBorderImageRepeat(RefPtr<CSSValue>& result)
+bool CSSPropertyParser::parseBorderImageRepeat(RefPtrWillBeRawPtr<CSSValue>& result)
{
- RefPtr<CSSPrimitiveValue> firstValue;
- RefPtr<CSSPrimitiveValue> secondValue;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> firstValue = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> secondValue = nullptr;
CSSParserValue* val = m_valueList->current();
if (!val)
return false;
@@ -6838,8 +5946,9 @@ bool CSSParser::parseBorderImageRepeat(RefPtr<CSSValue>& result)
}
class BorderImageSliceParseContext {
+ STACK_ALLOCATED();
public:
- BorderImageSliceParseContext(CSSParser* parser)
+ BorderImageSliceParseContext(CSSPropertyParser* parser)
: m_parser(parser)
, m_allowNumber(true)
, m_allowFill(true)
@@ -6854,7 +5963,7 @@ public:
void commitNumber(CSSParserValue* v)
{
- RefPtr<CSSPrimitiveValue> val = m_parser->createPrimitiveNumericValue(v);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> val = m_parser->createPrimitiveNumericValue(v);
if (!m_top)
m_top = val;
else if (!m_right)
@@ -6872,7 +5981,7 @@ public:
void commitFill() { m_fill = true; m_allowFill = false; m_allowNumber = !m_top; }
- PassRefPtr<CSSBorderImageSliceValue> commitBorderImageSlice()
+ PassRefPtrWillBeRawPtr<CSSBorderImageSliceValue> commitBorderImageSlice()
{
// We need to clone and repeat values for any omissions.
ASSERT(m_top);
@@ -6889,7 +5998,7 @@ public:
m_left = m_right;
// Now build a rect value to hold all four of our primitive values.
- RefPtr<Quad> quad = Quad::create();
+ RefPtrWillBeRawPtr<Quad> quad = Quad::create();
quad->setTop(m_top);
quad->setRight(m_right);
quad->setBottom(m_bottom);
@@ -6900,21 +6009,21 @@ public:
}
private:
- CSSParser* m_parser;
+ CSSPropertyParser* m_parser;
bool m_allowNumber;
bool m_allowFill;
bool m_allowFinalCommit;
- RefPtr<CSSPrimitiveValue> m_top;
- RefPtr<CSSPrimitiveValue> m_right;
- RefPtr<CSSPrimitiveValue> m_bottom;
- RefPtr<CSSPrimitiveValue> m_left;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_top;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_right;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_bottom;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_left;
bool m_fill;
};
-bool CSSParser::parseBorderImageSlice(CSSPropertyID propId, RefPtr<CSSBorderImageSliceValue>& result)
+bool CSSPropertyParser::parseBorderImageSlice(CSSPropertyID propId, RefPtrWillBeRawPtr<CSSBorderImageSliceValue>& result)
{
BorderImageSliceParseContext context(this);
CSSParserValue* val;
@@ -6952,8 +6061,9 @@ bool CSSParser::parseBorderImageSlice(CSSPropertyID propId, RefPtr<CSSBorderImag
}
class BorderImageQuadParseContext {
+ STACK_ALLOCATED();
public:
- BorderImageQuadParseContext(CSSParser* parser)
+ BorderImageQuadParseContext(CSSPropertyParser* parser)
: m_parser(parser)
, m_allowNumber(true)
, m_allowFinalCommit(false)
@@ -6965,7 +6075,7 @@ public:
void commitNumber(CSSParserValue* v)
{
- RefPtr<CSSPrimitiveValue> val;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> val = nullptr;
if (v->id == CSSValueAuto)
val = cssValuePool().createIdentifierValue(v->id);
else
@@ -6986,10 +6096,9 @@ public:
m_allowFinalCommit = true;
}
- void setAllowFinalCommit() { m_allowFinalCommit = true; }
- void setTop(PassRefPtr<CSSPrimitiveValue> val) { m_top = val; }
+ void setTop(PassRefPtrWillBeRawPtr<CSSPrimitiveValue> val) { m_top = val; }
- PassRefPtr<CSSPrimitiveValue> commitBorderImageQuad()
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> commitBorderImageQuad()
{
// We need to clone and repeat values for any omissions.
ASSERT(m_top);
@@ -7006,7 +6115,7 @@ public:
m_left = m_right;
// Now build a quad value to hold all four of our primitive values.
- RefPtr<Quad> quad = Quad::create();
+ RefPtrWillBeRawPtr<Quad> quad = Quad::create();
quad->setTop(m_top);
quad->setRight(m_right);
quad->setBottom(m_bottom);
@@ -7017,18 +6126,18 @@ public:
}
private:
- CSSParser* m_parser;
+ CSSPropertyParser* m_parser;
bool m_allowNumber;
bool m_allowFinalCommit;
- RefPtr<CSSPrimitiveValue> m_top;
- RefPtr<CSSPrimitiveValue> m_right;
- RefPtr<CSSPrimitiveValue> m_bottom;
- RefPtr<CSSPrimitiveValue> m_left;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_top;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_right;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_bottom;
+ RefPtrWillBeMember<CSSPrimitiveValue> m_left;
};
-bool CSSParser::parseBorderImageQuad(Units validUnits, RefPtr<CSSPrimitiveValue>& result)
+bool CSSPropertyParser::parseBorderImageQuad(Units validUnits, RefPtrWillBeRawPtr<CSSPrimitiveValue>& result)
{
BorderImageQuadParseContext context(this);
CSSParserValue* val;
@@ -7054,36 +6163,28 @@ bool CSSParser::parseBorderImageQuad(Units validUnits, RefPtr<CSSPrimitiveValue>
return false;
}
-bool CSSParser::parseBorderImageWidth(RefPtr<CSSPrimitiveValue>& result)
+bool CSSPropertyParser::parseBorderImageWidth(RefPtrWillBeRawPtr<CSSPrimitiveValue>& result)
{
return parseBorderImageQuad(FLength | FNumber | FNonNeg | FPercent, result);
}
-bool CSSParser::parseBorderImageOutset(RefPtr<CSSPrimitiveValue>& result)
+bool CSSPropertyParser::parseBorderImageOutset(RefPtrWillBeRawPtr<CSSPrimitiveValue>& result)
{
return parseBorderImageQuad(FLength | FNumber | FNonNeg, result);
}
-static void completeBorderRadii(RefPtr<CSSPrimitiveValue> radii[4])
-{
- if (radii[3])
- return;
- if (!radii[2]) {
- if (!radii[1])
- radii[1] = radii[0];
- radii[2] = radii[0];
- }
- radii[3] = radii[1];
-}
-
-bool CSSParser::parseBorderRadius(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseBorderRadius(CSSPropertyID propId, bool important)
{
unsigned num = m_valueList->size();
if (num > 9)
return false;
ShorthandScope scope(this, propId);
- RefPtr<CSSPrimitiveValue> radii[2][4];
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> radii[2][4];
+#if ENABLE(OILPAN)
+ // Zero initialize the array of raw pointers.
+ memset(&radii, 0, sizeof(radii));
+#endif
unsigned indexAfterSlash = 0;
for (unsigned i = 0; i < num; ++i) {
@@ -7106,7 +6207,7 @@ bool CSSParser::parseBorderRadius(CSSPropertyID propId, bool important)
if (!validUnit(value, FLength | FPercent | FNonNeg))
return false;
- RefPtr<CSSPrimitiveValue> radius = createPrimitiveNumericValue(value);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> radius = createPrimitiveNumericValue(value);
if (!indexAfterSlash) {
radii[0][i] = radius;
@@ -7135,7 +6236,7 @@ bool CSSParser::parseBorderRadius(CSSPropertyID propId, bool important)
return true;
}
-bool CSSParser::parseAspectRatio(bool important)
+bool CSSPropertyParser::parseAspectRatio(bool important)
{
unsigned num = m_valueList->size();
if (num == 1 && m_valueList->valueAt(0)->id == CSSValueNone) {
@@ -7164,12 +6265,12 @@ bool CSSParser::parseAspectRatio(bool important)
return true;
}
-bool CSSParser::parseCounter(CSSPropertyID propId, int defaultValue, bool important)
+bool CSSPropertyParser::parseCounter(CSSPropertyID propId, int defaultValue, bool important)
{
enum { ID, VAL } state = ID;
- RefPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
- RefPtr<CSSPrimitiveValue> counterName;
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> counterName = nullptr;
while (true) {
CSSParserValue* val = m_valueList->current();
@@ -7207,9 +6308,9 @@ bool CSSParser::parseCounter(CSSPropertyID propId, int defaultValue, bool import
}
// This should go away once we drop support for -webkit-gradient
-static PassRefPtr<CSSPrimitiveValue> parseDeprecatedGradientPoint(CSSParserValue* a, bool horizontal)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseDeprecatedGradientPoint(CSSParserValue* a, bool horizontal)
{
- RefPtr<CSSPrimitiveValue> result;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> result = nullptr;
if (a->unit == CSSPrimitiveValue::CSS_IDENT) {
if ((equalIgnoringCase(a, "left") && horizontal)
|| (equalIgnoringCase(a, "top") && !horizontal))
@@ -7219,12 +6320,13 @@ static PassRefPtr<CSSPrimitiveValue> parseDeprecatedGradientPoint(CSSParserValue
result = cssValuePool().createValue(100., CSSPrimitiveValue::CSS_PERCENTAGE);
else if (equalIgnoringCase(a, "center"))
result = cssValuePool().createValue(50., CSSPrimitiveValue::CSS_PERCENTAGE);
- } else if (a->unit == CSSPrimitiveValue::CSS_NUMBER || a->unit == CSSPrimitiveValue::CSS_PERCENTAGE)
- result = cssValuePool().createValue(a->fValue, static_cast<CSSPrimitiveValue::UnitTypes>(a->unit));
+ } else if (a->unit == CSSPrimitiveValue::CSS_NUMBER || a->unit == CSSPrimitiveValue::CSS_PERCENTAGE) {
+ result = cssValuePool().createValue(a->fValue, static_cast<CSSPrimitiveValue::UnitType>(a->unit));
+ }
return result;
}
-static bool parseDeprecatedGradientColorStop(CSSParser* p, CSSParserValue* a, CSSGradientColorStop& stop)
+bool parseDeprecatedGradientColorStop(CSSPropertyParser* p, CSSParserValue* a, CSSGradientColorStop& stop)
{
if (a->unit != CSSParserValue::Function)
return false;
@@ -7288,7 +6390,7 @@ static bool parseDeprecatedGradientColorStop(CSSParser* p, CSSParserValue* a, CS
return true;
}
-bool CSSParser::parseDeprecatedGradient(CSSParserValueList* valueList, RefPtr<CSSValue>& gradient)
+bool CSSPropertyParser::parseDeprecatedGradient(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& gradient)
{
// Walk the arguments.
CSSParserValueList* args = valueList->current()->function->args.get();
@@ -7307,7 +6409,7 @@ bool CSSParser::parseDeprecatedGradient(CSSParserValueList* valueList, RefPtr<CS
else
return false;
- RefPtr<CSSGradientValue> result;
+ RefPtrWillBeRawPtr<CSSGradientValue> result = nullptr;
switch (gradientType) {
case CSSDeprecatedLinearGradient:
result = CSSLinearGradientValue::create(NonRepeating, gradientType);
@@ -7331,7 +6433,7 @@ bool CSSParser::parseDeprecatedGradient(CSSParserValueList* valueList, RefPtr<CS
a = args->next();
if (!a)
return false;
- RefPtr<CSSPrimitiveValue> point = parseDeprecatedGradientPoint(a, true);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> point = parseDeprecatedGradientPoint(a, true);
if (!point)
return false;
result->setFirstX(point.release());
@@ -7421,10 +6523,10 @@ bool CSSParser::parseDeprecatedGradient(CSSParserValueList* valueList, RefPtr<CS
return true;
}
-static PassRefPtr<CSSPrimitiveValue> valueFromSideKeyword(CSSParserValue* a, bool& isHorizontal)
+static PassRefPtrWillBeRawPtr<CSSPrimitiveValue> valueFromSideKeyword(CSSParserValue* a, bool& isHorizontal)
{
if (a->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
+ return nullptr;
switch (a->id) {
case CSSValueLeft:
@@ -7436,12 +6538,12 @@ static PassRefPtr<CSSPrimitiveValue> valueFromSideKeyword(CSSParserValue* a, boo
isHorizontal = false;
break;
default:
- return 0;
+ return nullptr;
}
return cssValuePool().createIdentifierValue(a->id);
}
-static PassRefPtr<CSSPrimitiveValue> parseGradientColorOrKeyword(CSSParser* p, CSSParserValue* value)
+PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseGradientColorOrKeyword(CSSPropertyParser* p, CSSParserValue* value)
{
CSSValueID id = value->id;
if (id == CSSValueWebkitText || (id >= CSSValueAqua && id <= CSSValueWindowtext) || id == CSSValueMenu || id == CSSValueCurrentcolor)
@@ -7450,9 +6552,9 @@ static PassRefPtr<CSSPrimitiveValue> parseGradientColorOrKeyword(CSSParser* p, C
return p->parseColor(value);
}
-bool CSSParser::parseDeprecatedLinearGradient(CSSParserValueList* valueList, RefPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
+bool CSSPropertyParser::parseDeprecatedLinearGradient(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
{
- RefPtr<CSSLinearGradientValue> result = CSSLinearGradientValue::create(repeating, CSSPrefixedLinearGradient);
+ RefPtrWillBeRawPtr<CSSLinearGradientValue> result = CSSLinearGradientValue::create(repeating, CSSPrefixedLinearGradient);
// Walk the arguments.
CSSParserValueList* args = valueList->current()->function->args.get();
@@ -7472,9 +6574,10 @@ bool CSSParser::parseDeprecatedLinearGradient(CSSParserValueList* valueList, Ref
expectComma = true;
} else {
// Look one or two optional keywords that indicate a side or corner.
- RefPtr<CSSPrimitiveValue> startX, startY;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> startX = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> startY = nullptr;
- RefPtr<CSSPrimitiveValue> location;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> location = nullptr;
bool isHorizontal = false;
if ((location = valueFromSideKeyword(a, isHorizontal))) {
if (isHorizontal)
@@ -7518,9 +6621,9 @@ bool CSSParser::parseDeprecatedLinearGradient(CSSParserValueList* valueList, Ref
return true;
}
-bool CSSParser::parseDeprecatedRadialGradient(CSSParserValueList* valueList, RefPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
+bool CSSPropertyParser::parseDeprecatedRadialGradient(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
{
- RefPtr<CSSRadialGradientValue> result = CSSRadialGradientValue::create(repeating, CSSPrefixedRadialGradient);
+ RefPtrWillBeRawPtr<CSSRadialGradientValue> result = CSSRadialGradientValue::create(repeating, CSSPrefixedRadialGradient);
// Walk the arguments.
CSSParserValueList* args = valueList->current()->function->args.get();
@@ -7534,8 +6637,8 @@ bool CSSParser::parseDeprecatedRadialGradient(CSSParserValueList* valueList, Ref
bool expectComma = false;
// Optional background-position
- RefPtr<CSSValue> centerX;
- RefPtr<CSSValue> centerY;
+ RefPtrWillBeRawPtr<CSSValue> centerX = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> centerY = nullptr;
// parse2ValuesFillPosition advances the args next pointer.
parse2ValuesFillPosition(args, centerX, centerY);
a = args->current();
@@ -7558,8 +6661,8 @@ bool CSSParser::parseDeprecatedRadialGradient(CSSParserValueList* valueList, Ref
result->setFirstY(toCSSPrimitiveValue(centerY.get()));
result->setSecondY(toCSSPrimitiveValue(centerY.get()));
- RefPtr<CSSPrimitiveValue> shapeValue;
- RefPtr<CSSPrimitiveValue> sizeValue;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> shapeValue = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> sizeValue = nullptr;
// Optional shape and/or size in any order.
for (int i = 0; i < 2; ++i) {
@@ -7599,8 +6702,8 @@ bool CSSParser::parseDeprecatedRadialGradient(CSSParserValueList* valueList, Ref
result->setSizingBehavior(sizeValue);
// Or, two lengths or percentages
- RefPtr<CSSPrimitiveValue> horizontalSize;
- RefPtr<CSSPrimitiveValue> verticalSize;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> horizontalSize = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> verticalSize = nullptr;
if (!shapeValue && !sizeValue) {
if (validUnit(a, FLength | FPercent)) {
@@ -7636,9 +6739,9 @@ bool CSSParser::parseDeprecatedRadialGradient(CSSParserValueList* valueList, Ref
return true;
}
-bool CSSParser::parseLinearGradient(CSSParserValueList* valueList, RefPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
+bool CSSPropertyParser::parseLinearGradient(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
{
- RefPtr<CSSLinearGradientValue> result = CSSLinearGradientValue::create(repeating, CSSLinearGradient);
+ RefPtrWillBeRawPtr<CSSLinearGradientValue> result = CSSLinearGradientValue::create(repeating, CSSLinearGradient);
CSSParserValueList* args = valueList->current()->function->args.get();
if (!args || !args->size())
@@ -7661,8 +6764,9 @@ bool CSSParser::parseLinearGradient(CSSParserValueList* valueList, RefPtr<CSSVal
if (!a)
return false;
- RefPtr<CSSPrimitiveValue> endX, endY;
- RefPtr<CSSPrimitiveValue> location;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> endX = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> endY = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> location = nullptr;
bool isHorizontal = false;
location = valueFromSideKeyword(a, isHorizontal);
@@ -7708,9 +6812,9 @@ bool CSSParser::parseLinearGradient(CSSParserValueList* valueList, RefPtr<CSSVal
return true;
}
-bool CSSParser::parseRadialGradient(CSSParserValueList* valueList, RefPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
+bool CSSPropertyParser::parseRadialGradient(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& gradient, CSSGradientRepeat repeating)
{
- RefPtr<CSSRadialGradientValue> result = CSSRadialGradientValue::create(repeating, CSSRadialGradient);
+ RefPtrWillBeRawPtr<CSSRadialGradientValue> result = CSSRadialGradientValue::create(repeating, CSSRadialGradient);
CSSParserValueList* args = valueList->current()->function->args.get();
if (!args || !args->size())
@@ -7722,10 +6826,10 @@ bool CSSParser::parseRadialGradient(CSSParserValueList* valueList, RefPtr<CSSVal
bool expectComma = false;
- RefPtr<CSSPrimitiveValue> shapeValue;
- RefPtr<CSSPrimitiveValue> sizeValue;
- RefPtr<CSSPrimitiveValue> horizontalSize;
- RefPtr<CSSPrimitiveValue> verticalSize;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> shapeValue = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> sizeValue = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> horizontalSize = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> verticalSize = nullptr;
// First part of grammar, the size/shape clause:
// [ circle || <length> ] |
@@ -7800,8 +6904,8 @@ bool CSSParser::parseRadialGradient(CSSParserValueList* valueList, RefPtr<CSSVal
// Second part of grammar, the center-position clause:
// at <position>
- RefPtr<CSSValue> centerX;
- RefPtr<CSSValue> centerY;
+ RefPtrWillBeRawPtr<CSSValue> centerX = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> centerY = nullptr;
if (a->unit == CSSPrimitiveValue::CSS_IDENT && equalIgnoringCase(a, "at")) {
a = args->next();
if (!a)
@@ -7831,7 +6935,7 @@ bool CSSParser::parseRadialGradient(CSSParserValueList* valueList, RefPtr<CSSVal
return true;
}
-bool CSSParser::parseGradientColorStops(CSSParserValueList* valueList, CSSGradientValue* gradient, bool expectComma)
+bool CSSPropertyParser::parseGradientColorStops(CSSParserValueList* valueList, CSSGradientValue* gradient, bool expectComma)
{
CSSParserValue* a = valueList->current();
@@ -7869,36 +6973,55 @@ bool CSSParser::parseGradientColorStops(CSSParserValueList* valueList, CSSGradie
return gradient->stopCount() >= 2;
}
-bool CSSParser::parseGeneratedImage(CSSParserValueList* valueList, RefPtr<CSSValue>& value)
+bool CSSPropertyParser::parseGeneratedImage(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& value)
{
CSSParserValue* val = valueList->current();
if (val->unit != CSSParserValue::Function)
return false;
- if (equalIgnoringCase(val->function->name, "-webkit-gradient("))
+ if (equalIgnoringCase(val->function->name, "-webkit-gradient(")) {
+ // FIXME: This should send a deprecation message.
+ if (m_context.useCounter())
+ m_context.useCounter()->count(UseCounter::DeprecatedWebKitGradient);
return parseDeprecatedGradient(valueList, value);
+ }
- if (equalIgnoringCase(val->function->name, "-webkit-linear-gradient("))
+ if (equalIgnoringCase(val->function->name, "-webkit-linear-gradient(")) {
+ // FIXME: This should send a deprecation message.
+ if (m_context.useCounter())
+ m_context.useCounter()->count(UseCounter::DeprecatedWebKitLinearGradient);
return parseDeprecatedLinearGradient(valueList, value, NonRepeating);
+ }
if (equalIgnoringCase(val->function->name, "linear-gradient("))
return parseLinearGradient(valueList, value, NonRepeating);
- if (equalIgnoringCase(val->function->name, "-webkit-repeating-linear-gradient("))
+ if (equalIgnoringCase(val->function->name, "-webkit-repeating-linear-gradient(")) {
+ // FIXME: This should send a deprecation message.
+ if (m_context.useCounter())
+ m_context.useCounter()->count(UseCounter::DeprecatedWebKitRepeatingLinearGradient);
return parseDeprecatedLinearGradient(valueList, value, Repeating);
+ }
if (equalIgnoringCase(val->function->name, "repeating-linear-gradient("))
return parseLinearGradient(valueList, value, Repeating);
- if (equalIgnoringCase(val->function->name, "-webkit-radial-gradient("))
+ if (equalIgnoringCase(val->function->name, "-webkit-radial-gradient(")) {
+ // FIXME: This should send a deprecation message.
+ if (m_context.useCounter())
+ m_context.useCounter()->count(UseCounter::DeprecatedWebKitRadialGradient);
return parseDeprecatedRadialGradient(valueList, value, NonRepeating);
+ }
if (equalIgnoringCase(val->function->name, "radial-gradient("))
return parseRadialGradient(valueList, value, NonRepeating);
- if (equalIgnoringCase(val->function->name, "-webkit-repeating-radial-gradient("))
+ if (equalIgnoringCase(val->function->name, "-webkit-repeating-radial-gradient(")) {
+ if (m_context.useCounter())
+ m_context.useCounter()->count(UseCounter::DeprecatedWebKitRepeatingRadialGradient);
return parseDeprecatedRadialGradient(valueList, value, Repeating);
+ }
if (equalIgnoringCase(val->function->name, "repeating-radial-gradient("))
return parseRadialGradient(valueList, value, Repeating);
@@ -7912,17 +7035,15 @@ bool CSSParser::parseGeneratedImage(CSSParserValueList* valueList, RefPtr<CSSVal
return false;
}
-bool CSSParser::parseCrossfade(CSSParserValueList* valueList, RefPtr<CSSValue>& crossfade)
+bool CSSPropertyParser::parseCrossfade(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& crossfade)
{
- RefPtr<CSSCrossfadeValue> result;
-
// Walk the arguments.
CSSParserValueList* args = valueList->current()->function->args.get();
if (!args || args->size() != 5)
return false;
CSSParserValue* a = args->current();
- RefPtr<CSSValue> fromImageValue;
- RefPtr<CSSValue> toImageValue;
+ RefPtrWillBeRawPtr<CSSValue> fromImageValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> toImageValue = nullptr;
// The first argument is the "from" image. It is a fill image.
if (!a || !parseFillImage(args, fromImageValue))
@@ -7945,7 +7066,7 @@ bool CSSParser::parseCrossfade(CSSParserValueList* valueList, RefPtr<CSSValue>&
a = args->next();
// The third argument is the crossfade value. It is a percentage or a fractional number.
- RefPtr<CSSPrimitiveValue> percentage;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> percentage = nullptr;
if (!a)
return false;
@@ -7956,7 +7077,7 @@ bool CSSParser::parseCrossfade(CSSParserValueList* valueList, RefPtr<CSSValue>&
else
return false;
- result = CSSCrossfadeValue::create(fromImageValue, toImageValue);
+ RefPtrWillBeRawPtr<CSSCrossfadeValue> result = CSSCrossfadeValue::create(fromImageValue, toImageValue);
result->setPercentage(percentage);
crossfade = result;
@@ -7964,7 +7085,7 @@ bool CSSParser::parseCrossfade(CSSParserValueList* valueList, RefPtr<CSSValue>&
return true;
}
-bool CSSParser::parseCanvas(CSSParserValueList* valueList, RefPtr<CSSValue>& canvas)
+bool CSSPropertyParser::parseCanvas(CSSParserValueList* valueList, RefPtrWillBeRawPtr<CSSValue>& canvas)
{
// Walk the arguments.
CSSParserValueList* args = valueList->current()->function->args.get();
@@ -7980,36 +7101,36 @@ bool CSSParser::parseCanvas(CSSParserValueList* valueList, RefPtr<CSSValue>& can
return true;
}
-PassRefPtr<CSSValue> CSSParser::parseImageSet(CSSParserValueList* valueList)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseImageSet(CSSParserValueList* valueList)
{
CSSParserValue* function = valueList->current();
if (function->unit != CSSParserValue::Function)
- return 0;
+ return nullptr;
CSSParserValueList* functionArgs = valueList->current()->function->args.get();
if (!functionArgs || !functionArgs->size() || !functionArgs->current())
- return 0;
+ return nullptr;
- RefPtr<CSSImageSetValue> imageSet = CSSImageSetValue::create();
+ RefPtrWillBeRawPtr<CSSImageSetValue> imageSet = CSSImageSetValue::create();
CSSParserValue* arg = functionArgs->current();
while (arg) {
if (arg->unit != CSSPrimitiveValue::CSS_URI)
- return 0;
+ return nullptr;
- RefPtr<CSSImageValue> image = CSSImageValue::create(completeURL(arg->string));
+ RefPtrWillBeRawPtr<CSSValue> image = createCSSImageValueWithReferrer(arg->string, completeURL(arg->string));
imageSet->append(image);
arg = functionArgs->next();
if (!arg || arg->unit != CSSPrimitiveValue::CSS_DIMENSION)
- return 0;
+ return nullptr;
double imageScaleFactor = 0;
const String& string = arg->string;
unsigned length = string.length();
if (!length)
- return 0;
+ return nullptr;
if (string.is8Bit()) {
const LChar* start = string.characters8();
parseDouble(start, start + length, 'x', imageScaleFactor);
@@ -8018,7 +7139,7 @@ PassRefPtr<CSSValue> CSSParser::parseImageSet(CSSParserValueList* valueList)
parseDouble(start, start + length, 'x', imageScaleFactor);
}
if (imageScaleFactor <= 0)
- return 0;
+ return nullptr;
imageSet->append(cssValuePool().createValue(imageScaleFactor, CSSPrimitiveValue::CSS_NUMBER));
// If there are no more arguments, we're done.
@@ -8028,7 +7149,7 @@ PassRefPtr<CSSValue> CSSParser::parseImageSet(CSSParserValueList* valueList)
// If there are more arguments, they should be after a comma.
if (!isComma(arg))
- return 0;
+ return nullptr;
// Skip the comma and move on to the next argument.
arg = functionArgs->next();
@@ -8037,234 +7158,63 @@ PassRefPtr<CSSValue> CSSParser::parseImageSet(CSSParserValueList* valueList)
return imageSet.release();
}
-class TransformOperationInfo {
-public:
- TransformOperationInfo(const CSSParserString& name)
- : m_type(CSSTransformValue::UnknownTransformOperation)
- , m_argCount(1)
- , m_allowSingleArgument(false)
- , m_unit(CSSParser::FUnknown)
- {
- const UChar* characters;
- unsigned nameLength = name.length();
-
- const unsigned longestNameLength = 12;
- UChar characterBuffer[longestNameLength];
- if (name.is8Bit()) {
- unsigned length = std::min(longestNameLength, nameLength);
- const LChar* characters8 = name.characters8();
- for (unsigned i = 0; i < length; ++i)
- characterBuffer[i] = characters8[i];
- characters = characterBuffer;
- } else
- characters = name.characters16();
-
- SWITCH(characters, nameLength) {
- CASE("skew(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::SkewTransformOperation;
- m_allowSingleArgument = true;
- m_argCount = 3;
- }
- CASE("scale(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::ScaleTransformOperation;
- m_allowSingleArgument = true;
- m_argCount = 3;
- }
- CASE("skewx(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::SkewXTransformOperation;
- }
- CASE("skewy(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::SkewYTransformOperation;
- }
- CASE("matrix(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::MatrixTransformOperation;
- m_argCount = 11;
- }
- CASE("rotate(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::RotateTransformOperation;
- }
- CASE("scalex(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::ScaleXTransformOperation;
- }
- CASE("scaley(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::ScaleYTransformOperation;
- }
- CASE("scalez(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::ScaleZTransformOperation;
- }
- CASE("scale3d(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::Scale3DTransformOperation;
- m_argCount = 5;
- }
- CASE("rotatex(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::RotateXTransformOperation;
- }
- CASE("rotatey(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::RotateYTransformOperation;
- }
- CASE("rotatez(") {
- m_unit = CSSParser::FAngle;
- m_type = CSSTransformValue::RotateZTransformOperation;
- }
- CASE("matrix3d(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::Matrix3DTransformOperation;
- m_argCount = 31;
- }
- CASE("rotate3d(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::Rotate3DTransformOperation;
- m_argCount = 7;
- }
- CASE("translate(") {
- m_unit = CSSParser::FLength | CSSParser::FPercent;
- m_type = CSSTransformValue::TranslateTransformOperation;
- m_allowSingleArgument = true;
- m_argCount = 3;
- }
- CASE("translatex(") {
- m_unit = CSSParser::FLength | CSSParser::FPercent;
- m_type = CSSTransformValue::TranslateXTransformOperation;
- }
- CASE("translatey(") {
- m_unit = CSSParser::FLength | CSSParser::FPercent;
- m_type = CSSTransformValue::TranslateYTransformOperation;
- }
- CASE("translatez(") {
- m_unit = CSSParser::FLength | CSSParser::FPercent;
- m_type = CSSTransformValue::TranslateZTransformOperation;
- }
- CASE("perspective(") {
- m_unit = CSSParser::FNumber;
- m_type = CSSTransformValue::PerspectiveTransformOperation;
- }
- CASE("translate3d(") {
- m_unit = CSSParser::FLength | CSSParser::FPercent;
- m_type = CSSTransformValue::Translate3DTransformOperation;
- m_argCount = 5;
- }
- }
- }
-
- CSSTransformValue::TransformOperationType type() const { return m_type; }
- unsigned argCount() const { return m_argCount; }
- CSSParser::Units unit() const { return m_unit; }
-
- bool unknown() const { return m_type == CSSTransformValue::UnknownTransformOperation; }
- bool hasCorrectArgCount(unsigned argCount) { return m_argCount == argCount || (m_allowSingleArgument && argCount == 1); }
-
-private:
- CSSTransformValue::TransformOperationType m_type;
- unsigned m_argCount;
- bool m_allowSingleArgument;
- CSSParser::Units m_unit;
-};
-
-PassRefPtr<CSSValueList> CSSParser::parseTransform()
+bool CSSPropertyParser::parseWillChange(bool important)
{
- if (!m_valueList)
- return 0;
+ ASSERT(RuntimeEnabledFeatures::cssWillChangeEnabled());
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
- RefPtr<CSSValue> parsedTransformValue = parseTransformValue(value);
- if (!parsedTransformValue)
- return 0;
-
- list->append(parsedTransformValue.release());
+ RefPtrWillBeRawPtr<CSSValueList> values = CSSValueList::createCommaSeparated();
+ if (m_valueList->current()->id == CSSValueAuto) {
+ if (m_valueList->next())
+ return false;
}
- return list.release();
-}
-
-PassRefPtr<CSSValue> CSSParser::parseTransformValue(CSSParserValue *value)
-{
- if (value->unit != CSSParserValue::Function || !value->function)
- return 0;
-
- // Every primitive requires at least one argument.
- CSSParserValueList* args = value->function->args.get();
- if (!args)
- return 0;
-
- // See if the specified primitive is one we understand.
- TransformOperationInfo info(value->function->name);
- if (info.unknown())
- return 0;
-
- if (!info.hasCorrectArgCount(args->size()))
- return 0;
-
- // The transform is a list of functional primitives that specify transform operations.
- // We collect a list of CSSTransformValues, where each value specifies a single operation.
-
- // Create the new CSSTransformValue for this operation and add it to our list.
- RefPtr<CSSTransformValue> transformValue = CSSTransformValue::create(info.type());
-
- // Snag our values.
- CSSParserValue* a = args->current();
- unsigned argNumber = 0;
- while (a) {
- CSSParser::Units unit = info.unit();
-
- if (info.type() == CSSTransformValue::Rotate3DTransformOperation && argNumber == 3) {
- // 4th param of rotate3d() is an angle rather than a bare number, validate it as such
- if (!validUnit(a, FAngle, HTMLStandardMode))
- return 0;
- } else if (info.type() == CSSTransformValue::Translate3DTransformOperation && argNumber == 2) {
- // 3rd param of translate3d() cannot be a percentage
- if (!validUnit(a, FLength, HTMLStandardMode))
- return 0;
- } else if (info.type() == CSSTransformValue::TranslateZTransformOperation && !argNumber) {
- // 1st param of translateZ() cannot be a percentage
- if (!validUnit(a, FLength, HTMLStandardMode))
- return 0;
- } else if (info.type() == CSSTransformValue::PerspectiveTransformOperation && !argNumber) {
- // 1st param of perspective() must be a non-negative number (deprecated) or length.
- if (!validUnit(a, FNumber | FLength | FNonNeg, HTMLStandardMode))
- return 0;
- } else if (!validUnit(a, unit, HTMLStandardMode))
- return 0;
+ CSSParserValue* currentValue;
+ bool expectComma = false;
- // Add the value to the current transform operation.
- transformValue->append(createPrimitiveNumericValue(a));
+ // Every comma-separated list of CSS_IDENTs is a valid will-change value,
+ // unless the list includes an explicitly disallowed CSS_IDENT.
+ while ((currentValue = m_valueList->current())) {
+ if (expectComma) {
+ if (!isComma(currentValue))
+ return false;
+ expectComma = false;
+ m_valueList->next();
+ continue;
+ }
- a = args->next();
- if (!a)
- break;
- if (a->unit != CSSParserValue::Operator || a->iValue != ',')
- return 0;
- a = args->next();
+ if (currentValue->unit != CSSPrimitiveValue::CSS_IDENT)
+ return false;
- argNumber++;
+ CSSPropertyID property = cssPropertyID(currentValue->string);
+ if (property && RuntimeCSSEnabled::isCSSPropertyEnabled(property)) {
+ // Now "all" is used by both CSSValue and CSSPropertyValue.
+ // Need to return false when currentValue is CSSPropertyAll.
+ if (property == CSSPropertyWillChange || property == CSSPropertyAll)
+ return false;
+ values->append(cssValuePool().createIdentifierValue(property));
+ } else {
+ switch (currentValue->id) {
+ case CSSValueNone:
+ case CSSValueAll:
+ case CSSValueAuto:
+ case CSSValueDefault:
+ case CSSValueInitial:
+ case CSSValueInherit:
+ return false;
+ case CSSValueContents:
+ case CSSValueScrollPosition:
+ values->append(cssValuePool().createIdentifierValue(currentValue->id));
+ break;
+ default:
+ break;
+ }
+ }
+ expectComma = true;
+ m_valueList->next();
}
- return transformValue.release();
-}
-
-bool CSSParser::isBlendMode(CSSValueID valueID)
-{
- return (valueID >= CSSValueMultiply && valueID <= CSSValueLuminosity)
- || valueID == CSSValueNormal
- || valueID == CSSValueOverlay;
-}
-
-bool CSSParser::isCompositeOperator(CSSValueID valueID)
-{
- // FIXME: Add CSSValueDestination and CSSValueLighter when the Compositing spec updates.
- return valueID >= CSSValueClear && valueID <= CSSValueXor;
+ addProperty(CSSPropertyWillChange, values.release(), important);
+ return true;
}
static void filterInfoForName(const CSSParserString& name, CSSFilterValue::FilterOperationType& filterType, unsigned& maximumArgumentCount)
@@ -8291,425 +7241,11 @@ static void filterInfoForName(const CSSParserString& name, CSSFilterValue::Filte
filterType = CSSFilterValue::DropShadowFilterOperation;
maximumArgumentCount = 4; // x-offset, y-offset, blur-radius, color -- spread and inset style not allowed.
}
- else if (equalIgnoringCase(name, "custom("))
- filterType = CSSFilterValue::CustomFilterOperation;
-}
-
-static bool acceptCommaOperator(CSSParserValueList* argsList)
-{
- if (CSSParserValue* arg = argsList->current()) {
- if (!isComma(arg))
- return false;
- argsList->next();
- }
- return true;
-}
-
-PassRefPtr<CSSArrayFunctionValue> CSSParser::parseCustomFilterArrayFunction(CSSParserValue* value)
-{
- ASSERT(value->unit == CSSParserValue::Function && value->function);
-
- if (!equalIgnoringCase(value->function->name, "array("))
- return 0;
-
- CSSParserValueList* arrayArgsParserValueList = value->function->args.get();
- if (!arrayArgsParserValueList || !arrayArgsParserValueList->size())
- return 0;
-
- // array() values are comma separated.
- RefPtr<CSSArrayFunctionValue> arrayFunction = CSSArrayFunctionValue::create();
- while (true) {
- // We parse pairs <Value, Comma> at each step.
- CSSParserValue* currentParserValue = arrayArgsParserValueList->current();
- if (!currentParserValue || !validUnit(currentParserValue, FNumber, HTMLStandardMode))
- return 0;
-
- RefPtr<CSSValue> arrayValue = cssValuePool().createValue(currentParserValue->fValue, CSSPrimitiveValue::CSS_NUMBER);
- arrayFunction->append(arrayValue.release());
-
- CSSParserValue* nextParserValue = arrayArgsParserValueList->next();
- if (!nextParserValue)
- break;
-
- if (!isComma(nextParserValue))
- return 0;
-
- arrayArgsParserValueList->next();
- }
-
- return arrayFunction;
-}
-
-PassRefPtr<CSSMixFunctionValue> CSSParser::parseMixFunction(CSSParserValue* value)
-{
- ASSERT(value->unit == CSSParserValue::Function && value->function);
-
- if (!equalIgnoringCase(value->function->name, "mix("))
- return 0;
-
- CSSParserValueList* argsList = value->function->args.get();
- if (!argsList)
- return 0;
-
- unsigned numArgs = argsList->size();
- if (numArgs < 1 || numArgs > 3)
- return 0;
-
- RefPtr<CSSMixFunctionValue> mixFunction = CSSMixFunctionValue::create();
-
- bool hasBlendMode = false;
- bool hasAlphaCompositing = false;
-
- for (CSSParserValue* arg = argsList->current(); arg; arg = argsList->next()) {
- RefPtr<CSSValue> value;
-
- unsigned argNumber = argsList->currentIndex();
- if (!argNumber) {
- if (arg->unit == CSSPrimitiveValue::CSS_URI) {
- KURL shaderURL = completeURL(arg->string);
- value = CSSShaderValue::create(shaderURL.string());
- }
- } else if (argNumber == 1 || argNumber == 2) {
- if (!hasBlendMode && isBlendMode(arg->id)) {
- hasBlendMode = true;
- value = cssValuePool().createIdentifierValue(arg->id);
- } else if (!hasAlphaCompositing && isCompositeOperator(arg->id)) {
- hasAlphaCompositing = true;
- value = cssValuePool().createIdentifierValue(arg->id);
- }
- }
-
- if (!value)
- return 0;
-
- mixFunction->append(value.release());
- }
-
- return mixFunction;
-}
-
-PassRefPtr<CSSValueList> CSSParser::parseCustomFilterParameters(CSSParserValueList* argsList)
-{
- //
- // params: [<param-def>[,<param-def>*]]
- // param-def: <param-name>wsp<param-value>
- // param-name: <ident>
- // param-value: true|false[wsp+true|false]{0-3} |
- // <number>[wsp+<number>]{0-3} |
- // <array> |
- // <transform> |
- // <texture(<uri>)>
- // array: 'array('<number>[wsp<number>]*')'
- // css-3d-transform: <transform-function>;[<transform-function>]*
- // transform: <css-3d-transform> | <mat>
- // mat: 'mat2('<number>(,<number>){3}')' |
- // 'mat3('<number>(,<number>){8}')' |
- // 'mat4('<number>(,<number>){15}')' )
- //
-
- RefPtr<CSSValueList> paramList = CSSValueList::createCommaSeparated();
-
- while (CSSParserValue* arg = argsList->current()) {
- if (arg->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
-
- RefPtr<CSSValueList> parameter = CSSValueList::createSpaceSeparated();
- parameter->append(createPrimitiveStringValue(arg));
-
- arg = argsList->next();
- if (!arg)
- return 0;
-
- RefPtr<CSSValue> parameterValue;
-
- if (arg->unit == CSSParserValue::Function && arg->function) {
- // FIXME: Implement parsing for the other parameter types.
- // textures: https://bugs.webkit.org/show_bug.cgi?id=71442
- // mat2, mat3, mat4: https://bugs.webkit.org/show_bug.cgi?id=71444
- if (equalIgnoringCase(arg->function->name, "array(")) {
- parameterValue = parseCustomFilterArrayFunction(arg);
- // This parsing step only consumes function arguments,
- // argsList is therefore moved forward explicitely.
- argsList->next();
- } else
- parameterValue = parseCustomFilterTransform(argsList);
- } else {
- RefPtr<CSSValueList> paramValueList = CSSValueList::createSpaceSeparated();
- arg = argsList->current();
- while (arg) {
- // If we hit a comma, it means that we finished this parameter's values.
- if (isComma(arg))
- break;
- if (!validUnit(arg, FNumber, HTMLStandardMode))
- return 0;
- paramValueList->append(cssValuePool().createValue(arg->fValue, CSSPrimitiveValue::CSS_NUMBER));
- arg = argsList->next();
- }
- if (!paramValueList->length() || paramValueList->length() > 4)
- return 0;
- parameterValue = paramValueList.release();
- }
-
- if (!parameterValue || !acceptCommaOperator(argsList))
- return 0;
-
- parameter->append(parameterValue.release());
- paramList->append(parameter.release());
- }
-
- return paramList;
-}
-
-PassRefPtr<CSSFilterValue> CSSParser::parseCustomFilterFunctionWithAtRuleReferenceSyntax(CSSParserValue* value)
-{
- //
- // Custom filter function "at-rule reference" syntax:
- //
- // custom(<filter-name>wsp[,wsp<params>])
- //
- // filter-name: <filter-name>
- // params: See the comment in CSSParser::parseCustomFilterParameters.
- //
-
- ASSERT(value->function);
-
- CSSParserValueList* argsList = value->function->args.get();
- if (!argsList || !argsList->size())
- return 0;
-
- // 1. Parse the filter name.
- CSSParserValue* arg = argsList->current();
- if (arg->unit != CSSPrimitiveValue::CSS_IDENT)
- return 0;
-
- RefPtr<CSSFilterValue> filterValue = CSSFilterValue::create(CSSFilterValue::CustomFilterOperation);
-
- RefPtr<CSSValue> filterName = createPrimitiveStringValue(arg);
- filterValue->append(filterName);
- argsList->next();
-
- if (!acceptCommaOperator(argsList))
- return 0;
-
- // 2. Parse the parameters.
- RefPtr<CSSValueList> paramList = parseCustomFilterParameters(argsList);
- if (!paramList)
- return 0;
-
- if (paramList->length())
- filterValue->append(paramList.release());
-
- return filterValue;
-}
-
-// FIXME: The custom filters "inline" syntax is deprecated. We will remove it eventually.
-PassRefPtr<CSSFilterValue> CSSParser::parseCustomFilterFunctionWithInlineSyntax(CSSParserValue* value)
-{
- //
- // Custom filter function "inline" syntax:
- //
- // custom(<vertex-shader>[wsp<fragment-shader>][,<vertex-mesh>][,<params>])
- //
- // vertexShader: <uri> | none
- // fragmentShader: <uri> | none | mix(<uri> [ <blend-mode> || <alpha-compositing> ]?)
- //
- // blend-mode: normal | multiply | screen | overlay | darken | lighten | color-dodge |
- // color-burn | hard-light | soft-light | difference | exclusion | hue |
- // saturation | color | luminosity
- // alpha-compositing: clear | src | dst | src-over | dst-over | src-in | dst-in |
- // src-out | dst-out | src-atop | dst-atop | xor | plus
- //
- // vertexMesh: +<integer>{1,2}[wsp<box>][wsp'detached']
- // box: filter-box | border-box | padding-box | content-box
- //
- // params: See the comment in CSSParser::parseCustomFilterParameters.
- //
-
- ASSERT(value->function);
-
- CSSParserValueList* argsList = value->function->args.get();
- if (!argsList)
- return 0;
-
- RefPtr<CSSFilterValue> filterValue = CSSFilterValue::create(CSSFilterValue::CustomFilterOperation);
-
- // 1. Parse the shader URLs: <vertex-shader>[wsp<fragment-shader>]
- RefPtr<CSSValueList> shadersList = CSSValueList::createSpaceSeparated();
- bool hadAtLeastOneCustomShader = false;
- CSSParserValue* arg;
- for (arg = argsList->current(); arg; arg = argsList->next()) {
- RefPtr<CSSValue> value;
- if (arg->id == CSSValueNone)
- value = cssValuePool().createIdentifierValue(CSSValueNone);
- else if (arg->unit == CSSPrimitiveValue::CSS_URI) {
- KURL shaderURL = completeURL(arg->string);
- value = CSSShaderValue::create(shaderURL.string());
- hadAtLeastOneCustomShader = true;
- } else if (argsList->currentIndex() == 1 && arg->unit == CSSParserValue::Function) {
- if (!(value = parseMixFunction(arg)))
- return 0;
- hadAtLeastOneCustomShader = true;
- }
-
- if (!value)
- break;
- shadersList->append(value.release());
- }
-
- if (!shadersList->length() || !hadAtLeastOneCustomShader || shadersList->length() > 2 || !acceptCommaOperator(argsList))
- return 0;
-
- filterValue->append(shadersList.release());
-
- // 2. Parse the mesh size <vertex-mesh>
- RefPtr<CSSValueList> meshSizeList = CSSValueList::createSpaceSeparated();
-
- for (arg = argsList->current(); arg; arg = argsList->next()) {
- if (!validUnit(arg, FInteger | FNonNeg, HTMLStandardMode))
- break;
- int integerValue = clampToInteger(arg->fValue);
- // According to the specification we can only accept positive non-zero values.
- if (integerValue < 1)
- return 0;
- meshSizeList->append(cssValuePool().createValue(integerValue, CSSPrimitiveValue::CSS_NUMBER));
- }
-
- if (meshSizeList->length() > 2)
- return 0;
-
- // FIXME: For legacy content, we accept the mesh box types. We don't do anything else with them.
- // Eventually, we'll remove them completely.
- // https://bugs.webkit.org/show_bug.cgi?id=103778
- if ((arg = argsList->current()) && (arg->id == CSSValueBorderBox || arg->id == CSSValuePaddingBox
- || arg->id == CSSValueContentBox || arg->id == CSSValueFilterBox))
- argsList->next();
-
- if ((arg = argsList->current()) && arg->id == CSSValueDetached) {
- meshSizeList->append(cssValuePool().createIdentifierValue(arg->id));
- argsList->next();
- }
-
- if (meshSizeList->length()) {
- if (!acceptCommaOperator(argsList))
- return 0;
- filterValue->append(meshSizeList.release());
- }
-
- // 3. Parse the parameters.
- RefPtr<CSSValueList> paramList = parseCustomFilterParameters(argsList);
- if (!paramList)
- return 0;
-
- if (paramList->length())
- filterValue->append(paramList.release());
-
- return filterValue;
-}
-
-PassRefPtr<CSSFilterValue> CSSParser::parseCustomFilterFunction(CSSParserValue* value)
-{
- ASSERT(value->function);
-
- // Look ahead to determine which syntax the custom function is using.
- // Both the at-rule reference syntax and the inline syntax require at least one argument.
- CSSParserValueList* argsList = value->function->args.get();
- if (!argsList || !argsList->size())
- return 0;
-
- // The at-rule reference syntax expects a single ident or an ident followed by a comma.
- // e.g. custom(my-filter) or custom(my-filter, ...)
- // In contrast, when the inline syntax starts with an ident like "none", it expects a uri or a mix function next.
- // e.g. custom(none url(...)) or custom(none mix(...)
- bool isAtRuleReferenceSyntax = argsList->valueAt(0)->unit == CSSPrimitiveValue::CSS_IDENT
- && (argsList->size() == 1 || isComma(argsList->valueAt(1)));
- return isAtRuleReferenceSyntax ? parseCustomFilterFunctionWithAtRuleReferenceSyntax(value) : parseCustomFilterFunctionWithInlineSyntax(value);
-}
-
-PassRefPtr<CSSValueList> CSSParser::parseCustomFilterTransform(CSSParserValueList* valueList)
-{
- if (!valueList)
- return 0;
-
- // CSS Shaders' custom() transforms are space separated and comma terminated.
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- for (CSSParserValue* value = valueList->current(); value; value = valueList->next()) {
- if (isComma(value))
- break;
-
- RefPtr<CSSValue> parsedTransformValue = parseTransformValue(value);
- if (!parsedTransformValue)
- return 0;
-
- list->append(parsedTransformValue.release());
- }
-
- return list.release();
-}
-
-PassRefPtr<CSSShaderValue> CSSParser::parseFilterRuleSrcUriAndFormat(CSSParserValueList* valueList)
-{
- CSSParserValue* value = valueList->current();
- ASSERT(value && value->unit == CSSPrimitiveValue::CSS_URI);
- RefPtr<CSSShaderValue> shaderValue = CSSShaderValue::create(completeURL(value->string));
-
- value = valueList->next();
- if (value && value->unit == CSSParserValue::Function && equalIgnoringCase(value->function->name, "format(")) {
- CSSParserValueList* args = value->function->args.get();
- if (!args || args->size() != 1)
- return 0;
-
- CSSParserValue* arg = args->current();
- if (arg->unit != CSSPrimitiveValue::CSS_STRING)
- return 0;
-
- shaderValue->setFormat(arg->string);
- valueList->next();
- }
-
- return shaderValue.release();
-}
-
-bool CSSParser::parseFilterRuleSrc()
-{
- RefPtr<CSSValueList> srcList = CSSValueList::createCommaSeparated();
-
- CSSParserValue* value = m_valueList->current();
- while (value) {
- if (value->unit != CSSPrimitiveValue::CSS_URI)
- return false;
-
- RefPtr<CSSShaderValue> shaderValue = parseFilterRuleSrcUriAndFormat(m_valueList.get());
- if (!shaderValue)
- return false;
- srcList->append(shaderValue.release());
-
- if (!acceptCommaOperator(m_valueList.get()))
- return false;
-
- value = m_valueList->current();
- }
-
- if (!srcList->length())
- return false;
-
- addProperty(CSSPropertySrc, srcList.release(), m_important);
- return true;
-}
-
-StyleRuleBase* CSSParser::createFilterRule(const CSSParserString& filterName)
-{
- RefPtr<StyleRuleFilter> rule = StyleRuleFilter::create(filterName);
- rule->setProperties(createStylePropertySet());
- clearProperties();
- StyleRuleFilter* result = rule.get();
- m_parsedRules.append(rule.release());
- return result;
}
-
-PassRefPtr<CSSFilterValue> CSSParser::parseBuiltinFilterArguments(CSSParserValueList* args, CSSFilterValue::FilterOperationType filterType)
+PassRefPtrWillBeRawPtr<CSSFilterValue> CSSPropertyParser::parseBuiltinFilterArguments(CSSParserValueList* args, CSSFilterValue::FilterOperationType filterType)
{
- RefPtr<CSSFilterValue> filterValue = CSSFilterValue::create(filterType);
+ RefPtrWillBeRawPtr<CSSFilterValue> filterValue = CSSFilterValue::create(filterType);
ASSERT(args);
switch (filterType) {
@@ -8721,12 +7257,12 @@ PassRefPtr<CSSFilterValue> CSSParser::parseBuiltinFilterArguments(CSSParserValue
case CSSFilterValue::ContrastFilterOperation: {
// One optional argument, 0-1 or 0%-100%, if missing use 100%.
if (args->size() > 1)
- return 0;
+ return nullptr;
if (args->size()) {
CSSParserValue* value = args->current();
if (!validUnit(value, FNumber | FPercent | FNonNeg, HTMLStandardMode))
- return 0;
+ return nullptr;
double amount = value->fValue;
@@ -8735,36 +7271,36 @@ PassRefPtr<CSSFilterValue> CSSParser::parseBuiltinFilterArguments(CSSParserValue
&& filterType != CSSFilterValue::ContrastFilterOperation) {
double maxAllowed = value->unit == CSSPrimitiveValue::CSS_PERCENTAGE ? 100.0 : 1.0;
if (amount > maxAllowed)
- return 0;
+ return nullptr;
}
- filterValue->append(cssValuePool().createValue(amount, static_cast<CSSPrimitiveValue::UnitTypes>(value->unit)));
+ filterValue->append(cssValuePool().createValue(amount, static_cast<CSSPrimitiveValue::UnitType>(value->unit)));
}
break;
}
case CSSFilterValue::BrightnessFilterOperation: {
// One optional argument, if missing use 100%.
if (args->size() > 1)
- return 0;
+ return nullptr;
if (args->size()) {
CSSParserValue* value = args->current();
if (!validUnit(value, FNumber | FPercent, HTMLStandardMode))
- return 0;
+ return nullptr;
- filterValue->append(cssValuePool().createValue(value->fValue, static_cast<CSSPrimitiveValue::UnitTypes>(value->unit)));
+ filterValue->append(cssValuePool().createValue(value->fValue, static_cast<CSSPrimitiveValue::UnitType>(value->unit)));
}
break;
}
case CSSFilterValue::HueRotateFilterOperation: {
// hue-rotate() takes one optional angle.
if (args->size() > 1)
- return 0;
+ return nullptr;
if (args->size()) {
CSSParserValue* argument = args->current();
if (!validUnit(argument, FAngle, HTMLStandardMode))
- return 0;
+ return nullptr;
filterValue->append(createPrimitiveNumericValue(argument));
}
@@ -8773,12 +7309,12 @@ PassRefPtr<CSSFilterValue> CSSParser::parseBuiltinFilterArguments(CSSParserValue
case CSSFilterValue::BlurFilterOperation: {
// Blur takes a single length. Zero parameters are allowed.
if (args->size() > 1)
- return 0;
+ return nullptr;
if (args->size()) {
CSSParserValue* argument = args->current();
if (!validUnit(argument, FLength | FNonNeg, HTMLStandardMode))
- return 0;
+ return nullptr;
filterValue->append(createPrimitiveNumericValue(argument));
}
@@ -8786,9 +7322,9 @@ PassRefPtr<CSSFilterValue> CSSParser::parseBuiltinFilterArguments(CSSParserValue
}
case CSSFilterValue::DropShadowFilterOperation: {
// drop-shadow() takes a single shadow.
- RefPtr<CSSValueList> shadowValueList = parseShadow(args, CSSPropertyWebkitFilter);
+ RefPtrWillBeRawPtr<CSSValueList> shadowValueList = parseShadow(args, CSSPropertyWebkitFilter);
if (!shadowValueList || shadowValueList->length() != 1)
- return 0;
+ return nullptr;
filterValue->append((shadowValueList.release())->itemWithoutBoundsCheck(0));
break;
@@ -8799,22 +7335,22 @@ PassRefPtr<CSSFilterValue> CSSParser::parseBuiltinFilterArguments(CSSParserValue
return filterValue.release();
}
-PassRefPtr<CSSValueList> CSSParser::parseFilter()
+PassRefPtrWillBeRawPtr<CSSValueList> CSSPropertyParser::parseFilter()
{
if (!m_valueList)
- return 0;
+ return nullptr;
// The filter is a list of functional primitives that specify individual operations.
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
if (value->unit != CSSPrimitiveValue::CSS_URI && (value->unit != CSSParserValue::Function || !value->function))
- return 0;
+ return nullptr;
CSSFilterValue::FilterOperationType filterType = CSSFilterValue::UnknownFilterOperation;
// See if the specified primitive is one we understand.
if (value->unit == CSSPrimitiveValue::CSS_URI) {
- RefPtr<CSSFilterValue> referenceFilterValue = CSSFilterValue::create(CSSFilterValue::ReferenceFilterOperation);
+ RefPtrWillBeRawPtr<CSSFilterValue> referenceFilterValue = CSSFilterValue::create(CSSFilterValue::ReferenceFilterOperation);
list->append(referenceFilterValue);
referenceFilterValue->append(CSSSVGDocumentValue::create(value->string));
} else {
@@ -8824,26 +7360,15 @@ PassRefPtr<CSSValueList> CSSParser::parseFilter()
filterInfoForName(name, filterType, maximumArgumentCount);
if (filterType == CSSFilterValue::UnknownFilterOperation)
- return 0;
+ return nullptr;
- if (filterType == CSSFilterValue::CustomFilterOperation) {
- // Make sure parsing fails if custom filters are disabled.
- if (!RuntimeEnabledFeatures::cssCustomFilterEnabled())
- return 0;
-
- RefPtr<CSSFilterValue> filterValue = parseCustomFilterFunction(value);
- if (!filterValue)
- return 0;
- list->append(filterValue.release());
- continue;
- }
CSSParserValueList* args = value->function->args.get();
if (!args)
- return 0;
+ return nullptr;
- RefPtr<CSSFilterValue> filterValue = parseBuiltinFilterArguments(args, filterType);
+ RefPtrWillBeRawPtr<CSSFilterValue> filterValue = parseBuiltinFilterArguments(args, filterType);
if (!filterValue)
- return 0;
+ return nullptr;
list->append(filterValue);
}
@@ -8851,90 +7376,71 @@ PassRefPtr<CSSValueList> CSSParser::parseFilter()
return list.release();
}
-
-static bool validFlowName(const String& flowName)
-{
- return !(equalIgnoringCase(flowName, "auto")
- || equalIgnoringCase(flowName, "default")
- || equalIgnoringCase(flowName, "inherit")
- || equalIgnoringCase(flowName, "initial")
- || equalIgnoringCase(flowName, "none"));
-}
-
-bool CSSParser::parseFlowThread(const String& flowName)
-{
- setupParser("@-internal-decls -webkit-flow-into:", flowName, "");
- cssyyparse(this);
-
- m_rule = 0;
-
- return ((m_parsedProperties.size() == 1) && (m_parsedProperties.first().id() == CSSPropertyWebkitFlowInto));
-}
-
-// none | <ident>
-bool CSSParser::parseFlowThread(CSSPropertyID propId, bool important)
+PassRefPtrWillBeRawPtr<CSSValueList> CSSPropertyParser::parseTransformOrigin()
{
- ASSERT(propId == CSSPropertyWebkitFlowInto);
- ASSERT(RuntimeEnabledFeatures::cssRegionsEnabled());
-
- if (m_valueList->size() != 1)
- return false;
-
CSSParserValue* value = m_valueList->current();
- if (!value)
- return false;
-
- if (value->unit != CSSPrimitiveValue::CSS_IDENT)
- return false;
-
- if (value->id == CSSValueNone) {
- addProperty(propId, cssValuePool().createIdentifierValue(value->id), important);
- return true;
+ CSSValueID id = value->id;
+ RefPtrWillBeRawPtr<CSSValue> xValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> yValue = nullptr;
+ RefPtrWillBeRawPtr<CSSValue> zValue = nullptr;
+ if (id == CSSValueLeft || id == CSSValueRight) {
+ xValue = cssValuePool().createIdentifierValue(id);
+ } else if (id == CSSValueTop || id == CSSValueBottom) {
+ yValue = cssValuePool().createIdentifierValue(id);
+ } else if (id == CSSValueCenter) {
+ // Unresolved as to whether this is X or Y.
+ } else if (validUnit(value, FPercent | FLength)) {
+ xValue = createPrimitiveNumericValue(value);
+ } else {
+ return nullptr;
}
- String inputProperty = String(value->string);
- if (!inputProperty.isEmpty()) {
- if (!validFlowName(inputProperty))
- return false;
- addProperty(propId, cssValuePool().createValue(inputProperty, CSSPrimitiveValue::CSS_STRING), important);
- } else
- addProperty(propId, cssValuePool().createIdentifierValue(CSSValueNone), important);
-
- return true;
-}
-
-// -webkit-flow-from: none | <ident>
-bool CSSParser::parseRegionThread(CSSPropertyID propId, bool important)
-{
- ASSERT(propId == CSSPropertyWebkitFlowFrom);
- ASSERT(RuntimeEnabledFeatures::cssRegionsEnabled());
-
- if (m_valueList->size() != 1)
- return false;
+ if ((value = m_valueList->next())) {
+ id = value->id;
+ if (!xValue && (id == CSSValueLeft || id == CSSValueRight)) {
+ xValue = cssValuePool().createIdentifierValue(id);
+ } else if (!yValue && (id == CSSValueTop || id == CSSValueBottom)) {
+ yValue = cssValuePool().createIdentifierValue(id);
+ } else if (id == CSSValueCenter) {
+ // Resolved below.
+ } else if (!yValue && validUnit(value, FPercent | FLength)) {
+ yValue = createPrimitiveNumericValue(value);
+ } else {
+ return nullptr;
+ }
- CSSParserValue* value = m_valueList->current();
- if (!value)
- return false;
+ // If X or Y have not been resolved, they must be center.
+ if (!xValue)
+ xValue = cssValuePool().createIdentifierValue(CSSValueCenter);
+ if (!yValue)
+ yValue = cssValuePool().createIdentifierValue(CSSValueCenter);
- if (value->unit != CSSPrimitiveValue::CSS_IDENT)
- return false;
+ if ((value = m_valueList->next())) {
+ if (!validUnit(value, FLength))
+ return nullptr;
+ zValue = createPrimitiveNumericValue(value);
- if (value->id == CSSValueNone)
- addProperty(propId, cssValuePool().createIdentifierValue(value->id), important);
- else {
- String inputProperty = String(value->string);
- if (!inputProperty.isEmpty()) {
- if (!validFlowName(inputProperty))
- return false;
- addProperty(propId, cssValuePool().createValue(inputProperty, CSSPrimitiveValue::CSS_STRING), important);
- } else
- addProperty(propId, cssValuePool().createIdentifierValue(CSSValueNone), important);
+ if ((value = m_valueList->next()))
+ return nullptr;
+ }
+ } else if (!xValue) {
+ if (yValue) {
+ xValue = cssValuePool().createValue(50, CSSPrimitiveValue::CSS_PERCENTAGE);
+ } else {
+ xValue = cssValuePool().createIdentifierValue(CSSValueCenter);
+ }
}
- return true;
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ list->append(xValue.release());
+ if (yValue)
+ list->append(yValue.release());
+ if (zValue)
+ list->append(zValue.release());
+ return list.release();
}
-bool CSSParser::parseTransformOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, CSSPropertyID& propId3, RefPtr<CSSValue>& value, RefPtr<CSSValue>& value2, RefPtr<CSSValue>& value3)
+bool CSSPropertyParser::parseWebkitTransformOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, CSSPropertyID& propId3, RefPtrWillBeRawPtr<CSSValue>& value, RefPtrWillBeRawPtr<CSSValue>& value2, RefPtrWillBeRawPtr<CSSValue>& value3)
{
propId1 = propId;
propId2 = propId;
@@ -8947,9 +7453,9 @@ bool CSSParser::parseTransformOrigin(CSSPropertyID propId, CSSPropertyID& propId
switch (propId) {
case CSSPropertyWebkitTransformOrigin:
- if (!parseTransformOriginShorthand(value, value2, value3))
+ if (!parseWebkitTransformOriginShorthand(value, value2, value3))
return false;
- // parseTransformOriginShorthand advances the m_valueList pointer
+ // parseWebkitTransformOriginShorthand advances the m_valueList pointer
break;
case CSSPropertyWebkitTransformOriginX: {
value = parseFillPositionX(m_valueList.get());
@@ -8978,7 +7484,7 @@ bool CSSParser::parseTransformOrigin(CSSPropertyID propId, CSSPropertyID& propId
return value;
}
-bool CSSParser::parsePerspectiveOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, RefPtr<CSSValue>& value, RefPtr<CSSValue>& value2)
+bool CSSPropertyParser::parseWebkitPerspectiveOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, RefPtrWillBeRawPtr<CSSValue>& value, RefPtrWillBeRawPtr<CSSValue>& value2)
{
propId1 = propId;
propId2 = propId;
@@ -9013,14 +7519,14 @@ bool CSSParser::parsePerspectiveOrigin(CSSPropertyID propId, CSSPropertyID& prop
return value;
}
-bool CSSParser::parseTouchAction(bool important)
+bool CSSPropertyParser::parseTouchAction(bool important)
{
if (!RuntimeEnabledFeatures::cssTouchActionEnabled())
return false;
CSSParserValue* value = m_valueList->current();
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- if (m_valueList->size() == 1 && value && (value->id == CSSValueAuto || value->id == CSSValueNone)) {
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ if (m_valueList->size() == 1 && value && (value->id == CSSValueAuto || value->id == CSSValueNone || value->id == CSSValueManipulation)) {
list->append(cssValuePool().createIdentifierValue(value->id));
addProperty(CSSPropertyTouchAction, list.release(), important);
m_valueList->next();
@@ -9032,7 +7538,7 @@ bool CSSParser::parseTouchAction(bool important)
switch (value->id) {
case CSSValuePanX:
case CSSValuePanY: {
- RefPtr<CSSValue> panValue = cssValuePool().createIdentifierValue(value->id);
+ RefPtrWillBeRawPtr<CSSValue> panValue = cssValuePool().createIdentifierValue(value->id);
if (list->hasValue(panValue.get())) {
isValid = false;
break;
@@ -9056,7 +7562,7 @@ bool CSSParser::parseTouchAction(bool important)
return false;
}
-void CSSParser::addTextDecorationProperty(CSSPropertyID propId, PassRefPtr<CSSValue> value, bool important)
+void CSSPropertyParser::addTextDecorationProperty(CSSPropertyID propId, PassRefPtrWillBeRawPtr<CSSValue> value, bool important)
{
// The text-decoration-line property takes priority over text-decoration, unless the latter has important priority set.
if (propId == CSSPropertyTextDecoration && !important && !inShorthand()) {
@@ -9068,7 +7574,7 @@ void CSSParser::addTextDecorationProperty(CSSPropertyID propId, PassRefPtr<CSSVa
addProperty(propId, value, important);
}
-bool CSSParser::parseTextDecoration(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseTextDecoration(CSSPropertyID propId, bool important)
{
if (propId == CSSPropertyTextDecorationLine
&& !RuntimeEnabledFeatures::css3TextDecorationsEnabled())
@@ -9081,7 +7587,7 @@ bool CSSParser::parseTextDecoration(CSSPropertyID propId, bool important)
return true;
}
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
bool isValid = true;
while (isValid && value) {
switch (value->id) {
@@ -9108,7 +7614,7 @@ bool CSSParser::parseTextDecoration(CSSPropertyID propId, bool important)
return false;
}
-bool CSSParser::parseTextUnderlinePosition(bool important)
+bool CSSPropertyParser::parseTextUnderlinePosition(bool important)
{
// The text-underline-position property has syntax "auto | [ under || [ left | right ] ]".
// However, values 'left' and 'right' are not implemented yet, so we will parse syntax
@@ -9126,12 +7632,12 @@ bool CSSParser::parseTextUnderlinePosition(bool important)
}
}
-bool CSSParser::parseTextEmphasisStyle(bool important)
+bool CSSPropertyParser::parseTextEmphasisStyle(bool important)
{
unsigned valueListSize = m_valueList->size();
- RefPtr<CSSPrimitiveValue> fill;
- RefPtr<CSSPrimitiveValue> shape;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> fill = nullptr;
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> shape = nullptr;
for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
if (value->unit == CSSPrimitiveValue::CSS_STRING) {
@@ -9165,7 +7671,7 @@ bool CSSParser::parseTextEmphasisStyle(bool important)
}
if (fill && shape) {
- RefPtr<CSSValueList> parsedValues = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> parsedValues = CSSValueList::createSpaceSeparated();
parsedValues->append(fill.release());
parsedValues->append(shape.release());
addProperty(CSSPropertyWebkitTextEmphasisStyle, parsedValues.release(), important);
@@ -9183,52 +7689,46 @@ bool CSSParser::parseTextEmphasisStyle(bool important)
return false;
}
-PassRefPtr<CSSValue> CSSParser::parseTextIndent()
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseTextIndent()
{
- RefPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> list = CSSValueList::createSpaceSeparated();
- // <length> | <percentage> | inherit
- if (m_valueList->size() == 1) {
- CSSParserValue* value = m_valueList->current();
- if (!value->id && validUnit(value, FLength | FPercent)) {
+ bool hasLengthOrPercentage = false;
+ bool hasEachLine = false;
+ bool hasHanging = false;
+
+ for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
+ // <length> | <percentage> | inherit when RuntimeEnabledFeatures::css3TextEnabled() returns false
+ if (!hasLengthOrPercentage && validUnit(value, FLength | FPercent)) {
list->append(createPrimitiveNumericValue(value));
- m_valueList->next();
- return list.release();
+ hasLengthOrPercentage = true;
+ continue;
}
- }
-
- if (!RuntimeEnabledFeatures::css3TextEnabled())
- return 0;
-
- // The case where text-indent has only <length>(or <percentage>) value
- // is handled above if statement even though css3TextEnabled() returns true.
-
- // [ [ <length> | <percentage> ] && each-line ] | inherit
- if (m_valueList->size() != 2)
- return 0;
- CSSParserValue* firstValue = m_valueList->current();
- CSSParserValue* secondValue = m_valueList->next();
- CSSParserValue* lengthOrPercentageValue = 0;
-
- // [ <length> | <percentage> ] each-line
- if (validUnit(firstValue, FLength | FPercent) && secondValue->id == CSSValueEachLine)
- lengthOrPercentageValue = firstValue;
- // each-line [ <length> | <percentage> ]
- else if (firstValue->id == CSSValueEachLine && validUnit(secondValue, FLength | FPercent))
- lengthOrPercentageValue = secondValue;
-
- if (lengthOrPercentageValue) {
- list->append(createPrimitiveNumericValue(lengthOrPercentageValue));
- list->append(cssValuePool().createIdentifierValue(CSSValueEachLine));
- m_valueList->next();
- return list.release();
+ // [ <length> | <percentage> ] && hanging? && each-line? | inherit
+ // when RuntimeEnabledFeatures::css3TextEnabled() returns true
+ if (RuntimeEnabledFeatures::css3TextEnabled()) {
+ if (!hasEachLine && value->id == CSSValueEachLine) {
+ list->append(cssValuePool().createIdentifierValue(CSSValueEachLine));
+ hasEachLine = true;
+ continue;
+ }
+ if (!hasHanging && value->id == CSSValueHanging) {
+ list->append(cssValuePool().createIdentifierValue(CSSValueHanging));
+ hasHanging = true;
+ continue;
+ }
+ }
+ return nullptr;
}
- return 0;
+ if (!hasLengthOrPercentage)
+ return nullptr;
+
+ return list.release();
}
-bool CSSParser::parseLineBoxContain(bool important)
+bool CSSPropertyParser::parseLineBoxContain(bool important)
{
LineBoxContain lineBoxContain = LineBoxContainNone;
@@ -9268,7 +7768,7 @@ bool CSSParser::parseLineBoxContain(bool important)
return true;
}
-bool CSSParser::parseFontFeatureTag(CSSValueList* settings)
+bool CSSPropertyParser::parseFontFeatureTag(CSSValueList* settings)
{
// Feature tag name consists of 4-letter characters.
static const unsigned tagNameLength = 4;
@@ -9305,16 +7805,16 @@ bool CSSParser::parseFontFeatureTag(CSSValueList* settings)
return true;
}
-bool CSSParser::parseFontFeatureSettings(bool important)
+bool CSSPropertyParser::parseFontFeatureSettings(bool important)
{
if (m_valueList->size() == 1 && m_valueList->current()->id == CSSValueNormal) {
- RefPtr<CSSPrimitiveValue> normalValue = cssValuePool().createIdentifierValue(CSSValueNormal);
+ RefPtrWillBeRawPtr<CSSPrimitiveValue> normalValue = cssValuePool().createIdentifierValue(CSSValueNormal);
m_valueList->next();
addProperty(CSSPropertyWebkitFontFeatureSettings, normalValue.release(), important);
return true;
}
- RefPtr<CSSValueList> settings = CSSValueList::createCommaSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> settings = CSSValueList::createCommaSeparated();
for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
if (!parseFontFeatureTag(settings.get()))
return false;
@@ -9331,12 +7831,13 @@ bool CSSParser::parseFontFeatureSettings(bool important)
return false;
}
-bool CSSParser::parseFontVariantLigatures(bool important)
+bool CSSPropertyParser::parseFontVariantLigatures(bool important)
{
- RefPtr<CSSValueList> ligatureValues = CSSValueList::createSpaceSeparated();
+ RefPtrWillBeRawPtr<CSSValueList> ligatureValues = CSSValueList::createSpaceSeparated();
bool sawCommonLigaturesValue = false;
bool sawDiscretionaryLigaturesValue = false;
bool sawHistoricalLigaturesValue = false;
+ bool sawContextualLigaturesValue = false;
for (CSSParserValue* value = m_valueList->current(); value; value = m_valueList->next()) {
if (value->unit != CSSPrimitiveValue::CSS_IDENT)
@@ -9364,6 +7865,13 @@ bool CSSParser::parseFontVariantLigatures(bool important)
sawHistoricalLigaturesValue = true;
ligatureValues->append(cssValuePool().createIdentifierValue(value->id));
break;
+ case CSSValueNoContextual:
+ case CSSValueContextual:
+ if (sawContextualLigaturesValue)
+ return false;
+ sawContextualLigaturesValue = true;
+ ligatureValues->append(cssValuePool().createIdentifierValue(value->id));
+ break;
default:
return false;
}
@@ -9372,11 +7880,11 @@ bool CSSParser::parseFontVariantLigatures(bool important)
if (!ligatureValues->length())
return false;
- addProperty(CSSPropertyWebkitFontVariantLigatures, ligatureValues.release(), important);
+ addProperty(CSSPropertyFontVariantLigatures, ligatureValues.release(), important);
return true;
}
-bool CSSParser::parseCalculation(CSSParserValue* value, ValueRange range)
+bool CSSPropertyParser::parseCalculation(CSSParserValue* value, ValueRange range)
{
ASSERT(isCalculation(value));
@@ -9393,760 +7901,7 @@ bool CSSParser::parseCalculation(CSSParserValue* value, ValueRange range)
return true;
}
-#define END_TOKEN 0
-
-void CSSParser::ensureLineEndings()
-{
- if (!m_lineEndings)
- m_lineEndings = lineEndings(*m_source);
-}
-
-CSSParserSelector* CSSParser::createFloatingSelectorWithTagName(const QualifiedName& tagQName)
-{
- CSSParserSelector* selector = new CSSParserSelector(tagQName);
- m_floatingSelectors.append(selector);
- return selector;
-}
-
-CSSParserSelector* CSSParser::createFloatingSelector()
-{
- CSSParserSelector* selector = new CSSParserSelector;
- m_floatingSelectors.append(selector);
- return selector;
-}
-
-PassOwnPtr<CSSParserSelector> CSSParser::sinkFloatingSelector(CSSParserSelector* selector)
-{
- if (selector) {
- size_t index = m_floatingSelectors.reverseFind(selector);
- ASSERT(index != kNotFound);
- m_floatingSelectors.remove(index);
- }
- return adoptPtr(selector);
-}
-
-Vector<OwnPtr<CSSParserSelector> >* CSSParser::createFloatingSelectorVector()
-{
- Vector<OwnPtr<CSSParserSelector> >* selectorVector = new Vector<OwnPtr<CSSParserSelector> >;
- m_floatingSelectorVectors.append(selectorVector);
- return selectorVector;
-}
-
-PassOwnPtr<Vector<OwnPtr<CSSParserSelector> > > CSSParser::sinkFloatingSelectorVector(Vector<OwnPtr<CSSParserSelector> >* selectorVector)
-{
- if (selectorVector) {
- size_t index = m_floatingSelectorVectors.reverseFind(selectorVector);
- ASSERT(index != kNotFound);
- m_floatingSelectorVectors.remove(index);
- }
- return adoptPtr(selectorVector);
-}
-
-CSSParserValueList* CSSParser::createFloatingValueList()
-{
- CSSParserValueList* list = new CSSParserValueList;
- m_floatingValueLists.append(list);
- return list;
-}
-
-PassOwnPtr<CSSParserValueList> CSSParser::sinkFloatingValueList(CSSParserValueList* list)
-{
- if (list) {
- size_t index = m_floatingValueLists.reverseFind(list);
- ASSERT(index != kNotFound);
- m_floatingValueLists.remove(index);
- }
- return adoptPtr(list);
-}
-
-CSSParserFunction* CSSParser::createFloatingFunction()
-{
- CSSParserFunction* function = new CSSParserFunction;
- m_floatingFunctions.append(function);
- return function;
-}
-
-CSSParserFunction* CSSParser::createFloatingFunction(const CSSParserString& name, PassOwnPtr<CSSParserValueList> args)
-{
- CSSParserFunction* function = createFloatingFunction();
- function->name = name;
- function->args = args;
- return function;
-}
-
-PassOwnPtr<CSSParserFunction> CSSParser::sinkFloatingFunction(CSSParserFunction* function)
-{
- if (function) {
- size_t index = m_floatingFunctions.reverseFind(function);
- ASSERT(index != kNotFound);
- m_floatingFunctions.remove(index);
- }
- return adoptPtr(function);
-}
-
-CSSParserValue& CSSParser::sinkFloatingValue(CSSParserValue& value)
-{
- if (value.unit == CSSParserValue::Function) {
- size_t index = m_floatingFunctions.reverseFind(value.function);
- ASSERT(index != kNotFound);
- m_floatingFunctions.remove(index);
- }
- return value;
-}
-
-MediaQueryExp* CSSParser::createFloatingMediaQueryExp(const AtomicString& mediaFeature, CSSParserValueList* values)
-{
- m_floatingMediaQueryExp = MediaQueryExp::create(mediaFeature, values);
- return m_floatingMediaQueryExp.get();
-}
-
-PassOwnPtr<MediaQueryExp> CSSParser::sinkFloatingMediaQueryExp(MediaQueryExp* expression)
-{
- ASSERT_UNUSED(expression, expression == m_floatingMediaQueryExp);
- return m_floatingMediaQueryExp.release();
-}
-
-Vector<OwnPtr<MediaQueryExp> >* CSSParser::createFloatingMediaQueryExpList()
-{
- m_floatingMediaQueryExpList = adoptPtr(new Vector<OwnPtr<MediaQueryExp> >);
- return m_floatingMediaQueryExpList.get();
-}
-
-PassOwnPtr<Vector<OwnPtr<MediaQueryExp> > > CSSParser::sinkFloatingMediaQueryExpList(Vector<OwnPtr<MediaQueryExp> >* list)
-{
- ASSERT_UNUSED(list, list == m_floatingMediaQueryExpList);
- return m_floatingMediaQueryExpList.release();
-}
-
-MediaQuery* CSSParser::createFloatingMediaQuery(MediaQuery::Restrictor restrictor, const AtomicString& mediaType, PassOwnPtr<Vector<OwnPtr<MediaQueryExp> > > expressions)
-{
- m_floatingMediaQuery = adoptPtr(new MediaQuery(restrictor, mediaType, expressions));
- return m_floatingMediaQuery.get();
-}
-
-MediaQuery* CSSParser::createFloatingMediaQuery(PassOwnPtr<Vector<OwnPtr<MediaQueryExp> > > expressions)
-{
- return createFloatingMediaQuery(MediaQuery::None, AtomicString("all", AtomicString::ConstructFromLiteral), expressions);
-}
-
-MediaQuery* CSSParser::createFloatingNotAllQuery()
-{
- return createFloatingMediaQuery(MediaQuery::Not, AtomicString("all", AtomicString::ConstructFromLiteral), sinkFloatingMediaQueryExpList(createFloatingMediaQueryExpList()));
-}
-
-PassOwnPtr<MediaQuery> CSSParser::sinkFloatingMediaQuery(MediaQuery* query)
-{
- ASSERT_UNUSED(query, query == m_floatingMediaQuery);
- return m_floatingMediaQuery.release();
-}
-
-Vector<RefPtr<StyleKeyframe> >* CSSParser::createFloatingKeyframeVector()
-{
- m_floatingKeyframeVector = adoptPtr(new Vector<RefPtr<StyleKeyframe> >());
- return m_floatingKeyframeVector.get();
-}
-
-PassOwnPtr<Vector<RefPtr<StyleKeyframe> > > CSSParser::sinkFloatingKeyframeVector(Vector<RefPtr<StyleKeyframe> >* keyframeVector)
-{
- ASSERT_UNUSED(keyframeVector, m_floatingKeyframeVector == keyframeVector);
- return m_floatingKeyframeVector.release();
-}
-
-MediaQuerySet* CSSParser::createMediaQuerySet()
-{
- RefPtr<MediaQuerySet> queries = MediaQuerySet::create();
- MediaQuerySet* result = queries.get();
- m_parsedMediaQuerySets.append(queries.release());
- return result;
-}
-
-StyleRuleBase* CSSParser::createImportRule(const CSSParserString& url, MediaQuerySet* media)
-{
- if (!media || !m_allowImportRules)
- return 0;
- RefPtr<StyleRuleImport> rule = StyleRuleImport::create(url, media);
- StyleRuleImport* result = rule.get();
- m_parsedRules.append(rule.release());
- return result;
-}
-
-StyleRuleBase* CSSParser::createMediaRule(MediaQuerySet* media, RuleList* rules)
-{
- m_allowImportRules = m_allowNamespaceDeclarations = false;
- RefPtr<StyleRuleMedia> rule;
- if (rules) {
- rule = StyleRuleMedia::create(media ? media : MediaQuerySet::create(), *rules);
- } else {
- RuleList emptyRules;
- rule = StyleRuleMedia::create(media ? media : MediaQuerySet::create(), emptyRules);
- }
- StyleRuleMedia* result = rule.get();
- m_parsedRules.append(rule.release());
- return result;
-}
-
-StyleRuleBase* CSSParser::createSupportsRule(bool conditionIsSupported, RuleList* rules)
-{
- m_allowImportRules = m_allowNamespaceDeclarations = false;
-
- RefPtr<CSSRuleSourceData> data = popSupportsRuleData();
- RefPtr<StyleRuleSupports> rule;
- String conditionText;
- unsigned conditionOffset = data->ruleHeaderRange.start + 9;
- unsigned conditionLength = data->ruleHeaderRange.length() - 9;
-
- if (m_tokenizer.is8BitSource())
- conditionText = String(m_tokenizer.m_dataStart8.get() + conditionOffset, conditionLength).stripWhiteSpace();
- else
- conditionText = String(m_tokenizer.m_dataStart16.get() + conditionOffset, conditionLength).stripWhiteSpace();
-
- if (rules) {
- rule = StyleRuleSupports::create(conditionText, conditionIsSupported, *rules);
- } else {
- RuleList emptyRules;
- rule = StyleRuleSupports::create(conditionText, conditionIsSupported, emptyRules);
- }
-
- StyleRuleSupports* result = rule.get();
- m_parsedRules.append(rule.release());
-
- return result;
-}
-
-void CSSParser::markSupportsRuleHeaderStart()
-{
- if (!m_supportsRuleDataStack)
- m_supportsRuleDataStack = adoptPtr(new RuleSourceDataList());
-
- RefPtr<CSSRuleSourceData> data = CSSRuleSourceData::create(CSSRuleSourceData::SUPPORTS_RULE);
- data->ruleHeaderRange.start = m_tokenizer.tokenStartOffset();
- m_supportsRuleDataStack->append(data);
-}
-
-void CSSParser::markSupportsRuleHeaderEnd()
-{
- ASSERT(m_supportsRuleDataStack && !m_supportsRuleDataStack->isEmpty());
-
- if (m_tokenizer.is8BitSource())
- m_supportsRuleDataStack->last()->ruleHeaderRange.end = m_tokenizer.tokenStart<LChar>() - m_tokenizer.m_dataStart8.get();
- else
- m_supportsRuleDataStack->last()->ruleHeaderRange.end = m_tokenizer.tokenStart<UChar>() - m_tokenizer.m_dataStart16.get();
-}
-
-PassRefPtr<CSSRuleSourceData> CSSParser::popSupportsRuleData()
-{
- ASSERT(m_supportsRuleDataStack && !m_supportsRuleDataStack->isEmpty());
- RefPtr<CSSRuleSourceData> data = m_supportsRuleDataStack->last();
- m_supportsRuleDataStack->removeLast();
- return data.release();
-}
-
-CSSParser::RuleList* CSSParser::createRuleList()
-{
- OwnPtr<RuleList> list = adoptPtr(new RuleList);
- RuleList* listPtr = list.get();
-
- m_parsedRuleLists.append(list.release());
- return listPtr;
-}
-
-CSSParser::RuleList* CSSParser::appendRule(RuleList* ruleList, StyleRuleBase* rule)
-{
- if (rule) {
- if (!ruleList)
- ruleList = createRuleList();
- ruleList->append(rule);
- }
- return ruleList;
-}
-
-template <typename CharacterType>
-ALWAYS_INLINE static void makeLower(const CharacterType* input, CharacterType* output, unsigned length)
-{
- // FIXME: If we need Unicode lowercasing here, then we probably want the real kind
- // that can potentially change the length of the string rather than the character
- // by character kind. If we don't need Unicode lowercasing, it would be good to
- // simplify this function.
-
- if (charactersAreAllASCII(input, length)) {
- // Fast case for all-ASCII.
- for (unsigned i = 0; i < length; i++)
- output[i] = toASCIILower(input[i]);
- } else {
- for (unsigned i = 0; i < length; i++)
- output[i] = Unicode::toLower(input[i]);
- }
-}
-
-void CSSParser::tokenToLowerCase(const CSSParserString& token)
-{
- size_t length = token.length();
- if (m_tokenizer.is8BitSource()) {
- size_t offset = token.characters8() - m_tokenizer.m_dataStart8.get();
- makeLower(token.characters8(), m_tokenizer.m_dataStart8.get() + offset, length);
- } else {
- size_t offset = token.characters16() - m_tokenizer.m_dataStart16.get();
- makeLower(token.characters16(), m_tokenizer.m_dataStart16.get() + offset, length);
- }
-}
-
-void CSSParser::endInvalidRuleHeader()
-{
- if (m_ruleHeaderType == CSSRuleSourceData::UNKNOWN_RULE)
- return;
-
- CSSParserLocation location;
- location.lineNumber = m_tokenizer.m_lineNumber;
- location.offset = m_ruleHeaderStartOffset;
- if (m_tokenizer.is8BitSource())
- location.token.init(m_tokenizer.m_dataStart8.get() + m_ruleHeaderStartOffset, 0);
- else
- location.token.init(m_tokenizer.m_dataStart16.get() + m_ruleHeaderStartOffset, 0);
-
- reportError(location, m_ruleHeaderType == CSSRuleSourceData::STYLE_RULE ? InvalidSelectorError : InvalidRuleError);
-
- endRuleHeader();
-}
-
-void CSSParser::reportError(const CSSParserLocation&, ErrorType)
-{
- // FIXME: error reporting temporatily disabled.
-}
-
-bool CSSParser::isLoggingErrors()
-{
- return m_logErrors && !m_ignoreErrors;
-}
-
-void CSSParser::logError(const String& message, const CSSParserLocation& location)
-{
- unsigned lineNumberInStyleSheet;
- unsigned columnNumber = 0;
- PageConsole& console = m_styleSheet->singleOwnerDocument()->page()->console();
- if (InspectorInstrumentation::hasFrontends()) {
- ensureLineEndings();
- TextPosition tokenPosition = TextPosition::fromOffsetAndLineEndings(location.offset, *m_lineEndings);
- lineNumberInStyleSheet = tokenPosition.m_line.zeroBasedInt();
- columnNumber = (lineNumberInStyleSheet ? 0 : m_startPosition.m_column.zeroBasedInt()) + tokenPosition.m_column.zeroBasedInt();
- } else {
- lineNumberInStyleSheet = location.lineNumber;
- }
- console.addMessage(CSSMessageSource, WarningMessageLevel, message, m_styleSheet->baseURL().string(), lineNumberInStyleSheet + m_startPosition.m_line.zeroBasedInt() + 1, columnNumber + 1);
-}
-
-StyleRuleKeyframes* CSSParser::createKeyframesRule(const String& name, PassOwnPtr<Vector<RefPtr<StyleKeyframe> > > popKeyframes, bool isPrefixed)
-{
- OwnPtr<Vector<RefPtr<StyleKeyframe> > > keyframes = popKeyframes;
- m_allowImportRules = m_allowNamespaceDeclarations = false;
- RefPtr<StyleRuleKeyframes> rule = StyleRuleKeyframes::create();
- for (size_t i = 0; i < keyframes->size(); ++i)
- rule->parserAppendKeyframe(keyframes->at(i));
- rule->setName(name);
- rule->setVendorPrefixed(isPrefixed);
- StyleRuleKeyframes* rulePtr = rule.get();
- m_parsedRules.append(rule.release());
- return rulePtr;
-}
-
-StyleRuleBase* CSSParser::createStyleRule(Vector<OwnPtr<CSSParserSelector> >* selectors)
-{
- StyleRule* result = 0;
- if (selectors) {
- m_allowImportRules = m_allowNamespaceDeclarations = false;
- RefPtr<StyleRule> rule = StyleRule::create();
- rule->parserAdoptSelectorVector(*selectors);
- if (m_hasFontFaceOnlyValues)
- deleteFontFaceOnlyValues();
- rule->setProperties(createStylePropertySet());
- result = rule.get();
- m_parsedRules.append(rule.release());
- }
- clearProperties();
- return result;
-}
-
-StyleRuleBase* CSSParser::createFontFaceRule()
-{
- m_allowImportRules = m_allowNamespaceDeclarations = false;
- for (unsigned i = 0; i < m_parsedProperties.size(); ++i) {
- CSSProperty& property = m_parsedProperties[i];
- if (property.id() == CSSPropertyFontVariant && property.value()->isPrimitiveValue())
- property.wrapValueInCommaSeparatedList();
- else if (property.id() == CSSPropertyFontFamily && (!property.value()->isValueList() || toCSSValueList(property.value())->length() != 1)) {
- // Unlike font-family property, font-family descriptor in @font-face rule
- // has to be a value list with exactly one family name. It cannot have a
- // have 'initial' value and cannot 'inherit' from parent.
- // See http://dev.w3.org/csswg/css3-fonts/#font-family-desc
- clearProperties();
- return 0;
- }
- }
- RefPtr<StyleRuleFontFace> rule = StyleRuleFontFace::create();
- rule->setProperties(createStylePropertySet());
- clearProperties();
- StyleRuleFontFace* result = rule.get();
- m_parsedRules.append(rule.release());
- if (m_styleSheet)
- m_styleSheet->setHasFontFaceRule(true);
- return result;
-}
-
-void CSSParser::addNamespace(const AtomicString& prefix, const AtomicString& uri)
-{
- if (!m_styleSheet || !m_allowNamespaceDeclarations)
- return;
- m_allowImportRules = false;
- m_styleSheet->parserAddNamespace(prefix, uri);
- if (prefix.isEmpty() && !uri.isNull())
- m_defaultNamespace = uri;
-}
-
-QualifiedName CSSParser::determineNameInNamespace(const AtomicString& prefix, const AtomicString& localName)
-{
- if (!m_styleSheet)
- return QualifiedName(prefix, localName, m_defaultNamespace);
- return QualifiedName(prefix, localName, m_styleSheet->determineNamespace(prefix));
-}
-
-CSSParserSelector* CSSParser::rewriteSpecifiersWithNamespaceIfNeeded(CSSParserSelector* specifiers)
-{
- if (m_defaultNamespace != starAtom || specifiers->needsCrossingTreeScopeBoundary())
- return rewriteSpecifiersWithElementName(nullAtom, starAtom, specifiers, /*tagIsForNamespaceRule*/true);
- if (CSSParserSelector* distributedPseudoElementSelector = specifiers->findDistributedPseudoElementSelector()) {
- specifiers->prependTagSelector(QualifiedName(nullAtom, starAtom, m_defaultNamespace), /*tagIsForNamespaceRule*/true);
- return rewriteSpecifiersForShadowDistributed(specifiers, distributedPseudoElementSelector);
- }
- return specifiers;
-}
-
-CSSParserSelector* CSSParser::rewriteSpecifiersWithElementName(const AtomicString& namespacePrefix, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule)
-{
- AtomicString determinedNamespace = namespacePrefix != nullAtom && m_styleSheet ? m_styleSheet->determineNamespace(namespacePrefix) : m_defaultNamespace;
- QualifiedName tag(namespacePrefix, elementName, determinedNamespace);
-
- if (CSSParserSelector* distributedPseudoElementSelector = specifiers->findDistributedPseudoElementSelector()) {
- specifiers->prependTagSelector(tag, tagIsForNamespaceRule);
- return rewriteSpecifiersForShadowDistributed(specifiers, distributedPseudoElementSelector);
- }
-
- if (specifiers->needsCrossingTreeScopeBoundary())
- return rewriteSpecifiersWithElementNameForCustomPseudoElement(tag, elementName, specifiers, tagIsForNamespaceRule);
-
- if (specifiers->isContentPseudoElement())
- return rewriteSpecifiersWithElementNameForContentPseudoElement(tag, elementName, specifiers, tagIsForNamespaceRule);
-
- if (tag == anyQName())
- return specifiers;
- if (!(specifiers->pseudoType() == CSSSelector::PseudoCue))
- specifiers->prependTagSelector(tag, tagIsForNamespaceRule);
- return specifiers;
-}
-
-CSSParserSelector* CSSParser::rewriteSpecifiersWithElementNameForCustomPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule)
-{
- if (m_useCounter && specifiers->pseudoType() == CSSSelector::PseudoUserAgentCustomElement)
- m_useCounter->count(UseCounter::CSSPseudoElementUserAgentCustomPseudo);
-
- CSSParserSelector* lastShadowPseudo = specifiers;
- CSSParserSelector* history = specifiers;
- while (history->tagHistory()) {
- history = history->tagHistory();
- if (history->needsCrossingTreeScopeBoundary() || history->hasShadowPseudo())
- lastShadowPseudo = history;
- }
-
- if (lastShadowPseudo->tagHistory()) {
- if (tag != anyQName())
- lastShadowPseudo->tagHistory()->prependTagSelector(tag, tagIsForNamespaceRule);
- return specifiers;
- }
-
- // For shadow-ID pseudo-elements to be correctly matched, the ShadowPseudo combinator has to be used.
- // We therefore create a new Selector with that combinator here in any case, even if matching any (host) element in any namespace (i.e. '*').
- OwnPtr<CSSParserSelector> elementNameSelector = adoptPtr(new CSSParserSelector(tag));
- lastShadowPseudo->setTagHistory(elementNameSelector.release());
- lastShadowPseudo->setRelation(CSSSelector::ShadowPseudo);
- return specifiers;
-}
-
-CSSParserSelector* CSSParser::rewriteSpecifiersWithElementNameForContentPseudoElement(const QualifiedName& tag, const AtomicString& elementName, CSSParserSelector* specifiers, bool tagIsForNamespaceRule)
-{
- CSSParserSelector* last = specifiers;
- CSSParserSelector* history = specifiers;
- while (history->tagHistory()) {
- history = history->tagHistory();
- if (history->isContentPseudoElement() || history->relationIsAffectedByPseudoContent())
- last = history;
- }
-
- if (last->tagHistory()) {
- if (tag != anyQName())
- last->tagHistory()->prependTagSelector(tag, tagIsForNamespaceRule);
- return specifiers;
- }
-
- // For shadow-ID pseudo-elements to be correctly matched, the ShadowPseudo combinator has to be used.
- // We therefore create a new Selector with that combinator here in any case, even if matching any (host) element in any namespace (i.e. '*').
- OwnPtr<CSSParserSelector> elementNameSelector = adoptPtr(new CSSParserSelector(tag));
- last->setTagHistory(elementNameSelector.release());
- last->setRelation(CSSSelector::SubSelector);
- return specifiers;
-}
-
-CSSParserSelector* CSSParser::rewriteSpecifiersForShadowDistributed(CSSParserSelector* specifiers, CSSParserSelector* distributedPseudoElementSelector)
-{
- if (m_useCounter)
- m_useCounter->count(UseCounter::CSSPseudoElementPrefixedDistributed);
- CSSParserSelector* argumentSelector = distributedPseudoElementSelector->functionArgumentSelector();
- ASSERT(argumentSelector);
- ASSERT(!specifiers->isDistributedPseudoElement());
- for (CSSParserSelector* end = specifiers; end->tagHistory(); end = end->tagHistory()) {
- if (end->tagHistory()->isDistributedPseudoElement()) {
- end->clearTagHistory();
- break;
- }
- }
- CSSParserSelector* end = argumentSelector;
- while (end->tagHistory())
- end = end->tagHistory();
-
- switch (end->relation()) {
- case CSSSelector::Child:
- case CSSSelector::Descendant:
- end->setTagHistory(sinkFloatingSelector(specifiers));
- end->setRelationIsAffectedByPseudoContent();
- return argumentSelector;
- default:
- return 0;
- }
-}
-
-CSSParserSelector* CSSParser::rewriteSpecifiers(CSSParserSelector* specifiers, CSSParserSelector* newSpecifier)
-{
- if (newSpecifier->needsCrossingTreeScopeBoundary()) {
- // Unknown pseudo element always goes at the top of selector chain.
- newSpecifier->appendTagHistory(CSSSelector::ShadowPseudo, sinkFloatingSelector(specifiers));
- return newSpecifier;
- }
- if (newSpecifier->isContentPseudoElement()) {
- newSpecifier->appendTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(specifiers));
- return newSpecifier;
- }
- if (specifiers->needsCrossingTreeScopeBoundary()) {
- // Specifiers for unknown pseudo element go right behind it in the chain.
- specifiers->insertTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(newSpecifier), CSSSelector::ShadowPseudo);
- return specifiers;
- }
- if (specifiers->isContentPseudoElement()) {
- specifiers->insertTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(newSpecifier), CSSSelector::SubSelector);
- return specifiers;
- }
- specifiers->appendTagHistory(CSSSelector::SubSelector, sinkFloatingSelector(newSpecifier));
- return specifiers;
-}
-
-StyleRuleBase* CSSParser::createPageRule(PassOwnPtr<CSSParserSelector> pageSelector)
-{
- // FIXME: Margin at-rules are ignored.
- m_allowImportRules = m_allowNamespaceDeclarations = false;
- StyleRulePage* pageRule = 0;
- if (pageSelector) {
- RefPtr<StyleRulePage> rule = StyleRulePage::create();
- Vector<OwnPtr<CSSParserSelector> > selectorVector;
- selectorVector.append(pageSelector);
- rule->parserAdoptSelectorVector(selectorVector);
- rule->setProperties(createStylePropertySet());
- pageRule = rule.get();
- m_parsedRules.append(rule.release());
- }
- clearProperties();
- return pageRule;
-}
-
-void CSSParser::setReusableRegionSelectorVector(Vector<OwnPtr<CSSParserSelector> >* selectors)
-{
- if (selectors)
- m_reusableRegionSelectorVector.swap(*selectors);
-}
-
-StyleRuleBase* CSSParser::createRegionRule(Vector<OwnPtr<CSSParserSelector> >* regionSelector, RuleList* rules)
-{
- if (m_useCounter)
- m_useCounter->count(UseCounter::CSSWebkitRegionAtRule);
-
- if (!RuntimeEnabledFeatures::cssRegionsEnabled() || !regionSelector || !rules)
- return 0;
-
- m_allowImportRules = m_allowNamespaceDeclarations = false;
-
- RefPtr<StyleRuleRegion> regionRule = StyleRuleRegion::create(regionSelector, *rules);
-
- StyleRuleRegion* result = regionRule.get();
- m_parsedRules.append(regionRule.release());
- if (m_sourceDataHandler)
- m_sourceDataHandler->startEndUnknownRule();
-
- return result;
-}
-
-StyleRuleBase* CSSParser::createMarginAtRule(CSSSelector::MarginBoxType /* marginBox */)
-{
- // FIXME: Implement margin at-rule here, using:
- // - marginBox: margin box
- // - m_parsedProperties: properties at [m_numParsedPropertiesBeforeMarginBox, m_parsedProperties.size()] are for this at-rule.
- // Don't forget to also update the action for page symbol in CSSGrammar.y such that margin at-rule data is cleared if page_selector is invalid.
-
- endDeclarationsForMarginBox();
- return 0; // until this method is implemented.
-}
-
-void CSSParser::startDeclarationsForMarginBox()
-{
- m_numParsedPropertiesBeforeMarginBox = m_parsedProperties.size();
-}
-
-void CSSParser::endDeclarationsForMarginBox()
-{
- rollbackLastProperties(m_parsedProperties.size() - m_numParsedPropertiesBeforeMarginBox);
- m_numParsedPropertiesBeforeMarginBox = INVALID_NUM_PARSED_PROPERTIES;
-}
-
-void CSSParser::deleteFontFaceOnlyValues()
-{
- ASSERT(m_hasFontFaceOnlyValues);
- for (unsigned i = 0; i < m_parsedProperties.size();) {
- CSSProperty& property = m_parsedProperties[i];
- if (property.id() == CSSPropertyFontVariant && property.value()->isValueList()) {
- m_parsedProperties.remove(i);
- continue;
- }
- ++i;
- }
-}
-
-StyleKeyframe* CSSParser::createKeyframe(CSSParserValueList* keys)
-{
- OwnPtr<Vector<double> > keyVector = StyleKeyframe::createKeyList(keys);
- if (keyVector->isEmpty())
- return 0;
-
- RefPtr<StyleKeyframe> keyframe = StyleKeyframe::create();
- keyframe->setKeys(keyVector.release());
- keyframe->setProperties(createStylePropertySet());
-
- clearProperties();
-
- StyleKeyframe* keyframePtr = keyframe.get();
- m_parsedKeyframes.append(keyframe.release());
- return keyframePtr;
-}
-
-void CSSParser::invalidBlockHit()
-{
- if (m_styleSheet && !m_hadSyntacticallyValidCSSRule)
- m_styleSheet->setHasSyntacticallyValidCSSHeader(false);
-}
-
-void CSSParser::startRule()
-{
- if (!m_sourceDataHandler)
- return;
-
- ASSERT(m_ruleHasHeader);
- m_ruleHasHeader = false;
-}
-
-void CSSParser::endRule(bool valid)
-{
- if (!m_sourceDataHandler)
- return;
-
- if (m_ruleHasHeader)
- m_sourceDataHandler->endRuleBody(m_tokenizer.safeUserStringTokenOffset(), !valid);
- m_ruleHasHeader = true;
-}
-
-void CSSParser::startRuleHeader(CSSRuleSourceData::Type ruleType)
-{
- resumeErrorLogging();
- m_ruleHeaderType = ruleType;
- m_ruleHeaderStartOffset = m_tokenizer.safeUserStringTokenOffset();
- m_ruleHeaderStartLineNumber = m_tokenizer.m_tokenStartLineNumber;
- if (m_sourceDataHandler) {
- ASSERT(!m_ruleHasHeader);
- m_sourceDataHandler->startRuleHeader(ruleType, m_ruleHeaderStartOffset);
- m_ruleHasHeader = true;
- }
-}
-
-void CSSParser::endRuleHeader()
-{
- ASSERT(m_ruleHeaderType != CSSRuleSourceData::UNKNOWN_RULE);
- m_ruleHeaderType = CSSRuleSourceData::UNKNOWN_RULE;
- if (m_sourceDataHandler) {
- ASSERT(m_ruleHasHeader);
- m_sourceDataHandler->endRuleHeader(m_tokenizer.safeUserStringTokenOffset());
- }
-}
-
-void CSSParser::startSelector()
-{
- if (m_sourceDataHandler)
- m_sourceDataHandler->startSelector(m_tokenizer.safeUserStringTokenOffset());
-}
-
-void CSSParser::endSelector()
-{
- if (m_sourceDataHandler)
- m_sourceDataHandler->endSelector(m_tokenizer.safeUserStringTokenOffset());
-}
-
-void CSSParser::startRuleBody()
-{
- if (m_sourceDataHandler)
- m_sourceDataHandler->startRuleBody(m_tokenizer.safeUserStringTokenOffset());
-}
-
-void CSSParser::startProperty()
-{
- resumeErrorLogging();
- if (m_sourceDataHandler)
- m_sourceDataHandler->startProperty(m_tokenizer.safeUserStringTokenOffset());
-}
-
-void CSSParser::endProperty(bool isImportantFound, bool isPropertyParsed, ErrorType errorType)
-{
- m_id = CSSPropertyInvalid;
- if (m_sourceDataHandler)
- m_sourceDataHandler->endProperty(isImportantFound, isPropertyParsed, m_tokenizer.safeUserStringTokenOffset(), errorType);
-}
-
-void CSSParser::startEndUnknownRule()
-{
- if (m_sourceDataHandler)
- m_sourceDataHandler->startEndUnknownRule();
-}
-
-StyleRuleBase* CSSParser::createViewportRule()
-{
- // Allow @viewport rules from UA stylesheets even if the feature is disabled.
- if (!RuntimeEnabledFeatures::cssViewportEnabled() && !isUASheetBehavior(m_context.mode()))
- return 0;
-
- m_allowImportRules = m_allowNamespaceDeclarations = false;
-
- RefPtr<StyleRuleViewport> rule = StyleRuleViewport::create();
-
- rule->setProperties(createStylePropertySet());
- clearProperties();
-
- StyleRuleViewport* result = rule.get();
- m_parsedRules.append(rule.release());
-
- return result;
-}
-
-bool CSSParser::parseViewportProperty(CSSPropertyID propId, bool important)
+bool CSSPropertyParser::parseViewportProperty(CSSPropertyID propId, bool important)
{
ASSERT(RuntimeEnabledFeatures::cssViewportEnabled() || isUASheetBehavior(m_context.mode()));
@@ -10190,7 +7945,7 @@ bool CSSParser::parseViewportProperty(CSSPropertyID propId, bool important)
break;
}
- RefPtr<CSSValue> parsedValue;
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = nullptr;
if (validPrimitive) {
parsedValue = parseValidPrimitive(id, value);
m_valueList->next();
@@ -10206,7 +7961,7 @@ bool CSSParser::parseViewportProperty(CSSPropertyID propId, bool important)
return false;
}
-bool CSSParser::parseViewportShorthand(CSSPropertyID propId, CSSPropertyID first, CSSPropertyID second, bool important)
+bool CSSPropertyParser::parseViewportShorthand(CSSPropertyID propId, CSSPropertyID first, CSSPropertyID second, bool important)
{
ASSERT(RuntimeEnabledFeatures::cssViewportEnabled() || isUASheetBehavior(m_context.mode()));
unsigned numValues = m_valueList->size();
@@ -10297,169 +8052,384 @@ CSSValueID cssValueKeywordID(const CSSParserString& string)
return string.is8Bit() ? cssValueKeywordID(string.characters8(), length) : cssValueKeywordID(string.characters16(), length);
}
-template <typename CharacterType>
-static inline bool isCSSTokenizerIdentifier(const CharacterType* characters, unsigned length)
+bool isValidNthToken(const CSSParserString& token)
{
- const CharacterType* end = characters + length;
+ // The tokenizer checks for the construct of an+b.
+ // However, since the {ident} rule precedes the {nth} rule, some of those
+ // tokens are identified as string literal. Furthermore we need to accept
+ // "odd" and "even" which does not match to an+b.
+ return equalIgnoringCase(token, "odd") || equalIgnoringCase(token, "even")
+ || equalIgnoringCase(token, "n") || equalIgnoringCase(token, "-n");
+}
- // -?
- if (characters != end && characters[0] == '-')
- ++characters;
+bool CSSPropertyParser::isSystemColor(int id)
+{
+ return (id >= CSSValueActiveborder && id <= CSSValueWindowtext) || id == CSSValueMenu;
+}
- // {nmstart}
- if (characters == end || !(characters[0] == '_' || characters[0] >= 128 || isASCIIAlpha(characters[0])))
+bool CSSPropertyParser::parseSVGValue(CSSPropertyID propId, bool important)
+{
+ CSSParserValue* value = m_valueList->current();
+ if (!value)
return false;
- ++characters;
- // {nmchar}*
- for (; characters != end; ++characters) {
- if (!(characters[0] == '_' || characters[0] == '-' || characters[0] >= 128 || isASCIIAlphanumeric(characters[0])))
- return false;
- }
+ CSSValueID id = value->id;
- return true;
-}
+ bool validPrimitive = false;
+ RefPtrWillBeRawPtr<CSSValue> parsedValue = nullptr;
-// "ident" from the CSS tokenizer, minus backslash-escape sequences
-static bool isCSSTokenizerIdentifier(const String& string)
-{
- unsigned length = string.length();
+ switch (propId) {
+ /* The comment to the right defines all valid value of these
+ * properties as defined in SVG 1.1, Appendix N. Property index */
+ case CSSPropertyAlignmentBaseline:
+ // auto | baseline | before-edge | text-before-edge | middle |
+ // central | after-edge | text-after-edge | ideographic | alphabetic |
+ // hanging | mathematical | inherit
+ if (id == CSSValueAuto || id == CSSValueBaseline || id == CSSValueMiddle
+ || (id >= CSSValueBeforeEdge && id <= CSSValueMathematical))
+ validPrimitive = true;
+ break;
- if (!length)
- return false;
+ case CSSPropertyBaselineShift:
+ // baseline | super | sub | <percentage> | <length> | inherit
+ if (id == CSSValueBaseline || id == CSSValueSub
+ || id >= CSSValueSuper)
+ validPrimitive = true;
+ else
+ validPrimitive = validUnit(value, FLength | FPercent, SVGAttributeMode);
+ break;
- if (string.is8Bit())
- return isCSSTokenizerIdentifier(string.characters8(), length);
- return isCSSTokenizerIdentifier(string.characters16(), length);
-}
+ case CSSPropertyDominantBaseline:
+ // auto | use-script | no-change | reset-size | ideographic |
+ // alphabetic | hanging | mathematical | central | middle |
+ // text-after-edge | text-before-edge | inherit
+ if (id == CSSValueAuto || id == CSSValueMiddle
+ || (id >= CSSValueUseScript && id <= CSSValueResetSize)
+ || (id >= CSSValueCentral && id <= CSSValueMathematical))
+ validPrimitive = true;
+ break;
-template <typename CharacterType>
-static inline bool isCSSTokenizerURL(const CharacterType* characters, unsigned length)
-{
- const CharacterType* end = characters + length;
-
- for (; characters != end; ++characters) {
- CharacterType c = characters[0];
- switch (c) {
- case '!':
- case '#':
- case '$':
- case '%':
- case '&':
- break;
- default:
- if (c < '*')
- return false;
- if (c <= '~')
- break;
- if (c < 128)
- return false;
+ case CSSPropertyEnableBackground:
+ // accumulate | new [x] [y] [width] [height] | inherit
+ if (id == CSSValueAccumulate) // TODO : new
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyMarkerStart:
+ case CSSPropertyMarkerMid:
+ case CSSPropertyMarkerEnd:
+ case CSSPropertyMask:
+ if (id == CSSValueNone) {
+ validPrimitive = true;
+ } else if (value->unit == CSSPrimitiveValue::CSS_URI) {
+ parsedValue = CSSPrimitiveValue::create(value->string, CSSPrimitiveValue::CSS_URI);
+ if (parsedValue)
+ m_valueList->next();
}
- }
+ break;
- return true;
-}
+ case CSSPropertyClipRule: // nonzero | evenodd | inherit
+ case CSSPropertyFillRule:
+ if (id == CSSValueNonzero || id == CSSValueEvenodd)
+ validPrimitive = true;
+ break;
-// "url" from the CSS tokenizer, minus backslash-escape sequences
-static bool isCSSTokenizerURL(const String& string)
-{
- unsigned length = string.length();
+ case CSSPropertyStrokeMiterlimit: // <miterlimit> | inherit
+ validPrimitive = validUnit(value, FNumber | FNonNeg, SVGAttributeMode);
+ break;
- if (!length)
- return true;
+ case CSSPropertyStrokeLinejoin: // miter | round | bevel | inherit
+ if (id == CSSValueMiter || id == CSSValueRound || id == CSSValueBevel)
+ validPrimitive = true;
+ break;
- if (string.is8Bit())
- return isCSSTokenizerURL(string.characters8(), length);
- return isCSSTokenizerURL(string.characters16(), length);
-}
+ case CSSPropertyStrokeLinecap: // butt | round | square | inherit
+ if (id == CSSValueButt || id == CSSValueRound || id == CSSValueSquare)
+ validPrimitive = true;
+ break;
+ case CSSPropertyStrokeOpacity: // <opacity-value> | inherit
+ case CSSPropertyFillOpacity:
+ case CSSPropertyStopOpacity:
+ case CSSPropertyFloodOpacity:
+ validPrimitive = (!id && validUnit(value, FNumber | FPercent, SVGAttributeMode));
+ break;
-template <typename CharacterType>
-static inline String quoteCSSStringInternal(const CharacterType* characters, unsigned length)
-{
- // For efficiency, we first pre-calculate the length of the quoted string, then we build the actual one.
- // Please see below for the actual logic.
- unsigned quotedStringSize = 2; // Two quotes surrounding the entire string.
- bool afterEscape = false;
- for (unsigned i = 0; i < length; ++i) {
- CharacterType ch = characters[i];
- if (ch == '\\' || ch == '\'') {
- quotedStringSize += 2;
- afterEscape = false;
- } else if (ch < 0x20 || ch == 0x7F) {
- quotedStringSize += 2 + (ch >= 0x10);
- afterEscape = true;
- } else {
- quotedStringSize += 1 + (afterEscape && (isASCIIHexDigit(ch) || ch == ' '));
- afterEscape = false;
+ case CSSPropertyShapeRendering:
+ // auto | optimizeSpeed | crispEdges | geometricPrecision | inherit
+ if (id == CSSValueAuto || id == CSSValueOptimizespeed
+ || id == CSSValueCrispedges || id == CSSValueGeometricprecision)
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyImageRendering: // auto | optimizeSpeed |
+ case CSSPropertyColorRendering: // optimizeQuality | inherit
+ if (id == CSSValueAuto || id == CSSValueOptimizespeed
+ || id == CSSValueOptimizequality)
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyBufferedRendering: // auto | dynamic | static
+ if (id == CSSValueAuto || id == CSSValueDynamic || id == CSSValueStatic)
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyColorInterpolation: // auto | sRGB | linearRGB | inherit
+ case CSSPropertyColorInterpolationFilters:
+ if (id == CSSValueAuto || id == CSSValueSrgb || id == CSSValueLinearrgb)
+ validPrimitive = true;
+ break;
+
+ /* Start of supported CSS properties with validation. This is needed for parseShortHand to work
+ * correctly and allows optimization in applyRule(..)
+ */
+
+ case CSSPropertyTextAnchor: // start | middle | end | inherit
+ if (id == CSSValueStart || id == CSSValueMiddle || id == CSSValueEnd)
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyGlyphOrientationVertical: // auto | <angle> | inherit
+ if (id == CSSValueAuto) {
+ validPrimitive = true;
+ break;
}
- }
+ /* fallthrough intentional */
+ case CSSPropertyGlyphOrientationHorizontal: // <angle> (restricted to _deg_ per SVG 1.1 spec) | inherit
+ if (value->unit == CSSPrimitiveValue::CSS_DEG || value->unit == CSSPrimitiveValue::CSS_NUMBER) {
+ parsedValue = CSSPrimitiveValue::create(value->fValue, CSSPrimitiveValue::CSS_DEG);
- StringBuffer<CharacterType> buffer(quotedStringSize);
- unsigned index = 0;
- buffer[index++] = '\'';
- afterEscape = false;
- for (unsigned i = 0; i < length; ++i) {
- CharacterType ch = characters[i];
- if (ch == '\\' || ch == '\'') {
- buffer[index++] = '\\';
- buffer[index++] = ch;
- afterEscape = false;
- } else if (ch < 0x20 || ch == 0x7F) { // Control characters.
- buffer[index++] = '\\';
- placeByteAsHexCompressIfPossible(ch, buffer, index, Lowercase);
- afterEscape = true;
- } else {
- // Space character may be required to separate backslash-escape sequence and normal characters.
- if (afterEscape && (isASCIIHexDigit(ch) || ch == ' '))
- buffer[index++] = ' ';
- buffer[index++] = ch;
- afterEscape = false;
+ if (parsedValue)
+ m_valueList->next();
}
- }
- buffer[index++] = '\'';
+ break;
- ASSERT(quotedStringSize == index);
- return String::adopt(buffer);
-}
+ case CSSPropertyFill: // <paint> | inherit
+ case CSSPropertyStroke: // <paint> | inherit
+ {
+ if (id == CSSValueNone) {
+ parsedValue = SVGPaint::createNone();
+ } else if (id == CSSValueCurrentcolor) {
+ parsedValue = SVGPaint::createCurrentColor();
+ } else if (isSystemColor(id)) {
+ parsedValue = SVGPaint::createColor(RenderTheme::theme().systemColor(id));
+ } else if (value->unit == CSSPrimitiveValue::CSS_URI) {
+ RGBA32 c = Color::transparent;
+ if (m_valueList->next()) {
+ if (parseColorFromValue(m_valueList->current(), c))
+ parsedValue = SVGPaint::createURIAndColor(value->string, c);
+ else if (m_valueList->current()->id == CSSValueNone)
+ parsedValue = SVGPaint::createURIAndNone(value->string);
+ else if (m_valueList->current()->id == CSSValueCurrentcolor)
+ parsedValue = SVGPaint::createURIAndCurrentColor(value->string);
+ }
+ if (!parsedValue)
+ parsedValue = SVGPaint::createURI(value->string);
+ } else {
+ parsedValue = parseSVGPaint();
+ }
-// We use single quotes for now because markup.cpp uses double quotes.
-String quoteCSSString(const String& string)
-{
- // This function expands each character to at most 3 characters ('\u0010' -> '\' '1' '0') as well as adds
- // 2 quote characters (before and after). Make sure the resulting size (3 * length + 2) will not overflow unsigned.
+ if (parsedValue)
+ m_valueList->next();
+ }
+ break;
- unsigned length = string.length();
+ case CSSPropertyStopColor: // TODO : icccolor
+ case CSSPropertyFloodColor:
+ case CSSPropertyLightingColor:
+ if (isSystemColor(id)) {
+ parsedValue = cssValuePool().createColorValue(RenderTheme::theme().systemColor(id).rgb());
+ } else if ((id >= CSSValueAqua && id <= CSSValueTransparent)
+ || (id >= CSSValueAliceblue && id <= CSSValueYellowgreen) || id == CSSValueGrey) {
+ StyleColor styleColor = SVGPaint::colorFromRGBColorString(value->string);
+ ASSERT(!styleColor.isCurrentColor());
+ parsedValue = cssValuePool().createColorValue(styleColor.color().rgb());
+ } else if (id == CSSValueCurrentcolor) {
+ parsedValue = cssValuePool().createIdentifierValue(id);
+ } else { // TODO : svgcolor (iccColor)
+ parsedValue = parseColor();
+ }
- if (!length)
- return String("\'\'");
+ if (parsedValue)
+ m_valueList->next();
+
+ break;
+
+ case CSSPropertyPaintOrder:
+ if (m_valueList->size() == 1 && id == CSSValueNormal)
+ validPrimitive = true;
+ else if ((parsedValue = parsePaintOrder()))
+ m_valueList->next();
+ break;
+
+ case CSSPropertyVectorEffect: // none | non-scaling-stroke | inherit
+ if (id == CSSValueNone || id == CSSValueNonScalingStroke)
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyWritingMode:
+ // lr-tb | rl_tb | tb-rl | lr | rl | tb | inherit
+ if (id == CSSValueLrTb || id == CSSValueRlTb || id == CSSValueTbRl || id == CSSValueLr || id == CSSValueRl || id == CSSValueTb)
+ validPrimitive = true;
+ break;
+
+ case CSSPropertyStrokeWidth: // <length> | inherit
+ case CSSPropertyStrokeDashoffset:
+ validPrimitive = validUnit(value, FLength | FPercent, SVGAttributeMode);
+ break;
+ case CSSPropertyStrokeDasharray: // none | <dasharray> | inherit
+ if (id == CSSValueNone)
+ validPrimitive = true;
+ else
+ parsedValue = parseSVGStrokeDasharray();
- if (length > std::numeric_limits<unsigned>::max() / 3 - 2)
- return emptyString();
+ break;
- if (string.is8Bit())
- return quoteCSSStringInternal(string.characters8(), length);
- return quoteCSSStringInternal(string.characters16(), length);
+ case CSSPropertyClipPath: // <uri> | none | inherit
+ case CSSPropertyFilter:
+ if (id == CSSValueNone) {
+ validPrimitive = true;
+ } else if (value->unit == CSSPrimitiveValue::CSS_URI) {
+ parsedValue = CSSPrimitiveValue::create(value->string, (CSSPrimitiveValue::UnitType) value->unit);
+ if (parsedValue)
+ m_valueList->next();
+ }
+ break;
+ case CSSPropertyMaskType: // luminance | alpha | inherit
+ if (id == CSSValueLuminance || id == CSSValueAlpha)
+ validPrimitive = true;
+ break;
+
+ /* shorthand properties */
+ case CSSPropertyMarker: {
+ ShorthandScope scope(this, propId);
+ CSSPropertyParser::ImplicitScope implicitScope(this, PropertyImplicit);
+ if (!parseValue(CSSPropertyMarkerStart, important))
+ return false;
+ if (m_valueList->current()) {
+ rollbackLastProperties(1);
+ return false;
+ }
+ CSSValue* value = m_parsedProperties.last().value();
+ addProperty(CSSPropertyMarkerMid, value, important);
+ addProperty(CSSPropertyMarkerEnd, value, important);
+ return true;
+ }
+ default:
+ // If you crash here, it's because you added a css property and are not handling it
+ // in either this switch statement or the one in CSSPropertyParser::parseValue
+ ASSERT_WITH_MESSAGE(0, "unimplemented propertyID: %d", propId);
+ return false;
+ }
+
+ if (validPrimitive) {
+ if (id)
+ parsedValue = CSSPrimitiveValue::createIdentifier(id);
+ else if (value->unit == CSSPrimitiveValue::CSS_STRING)
+ parsedValue = CSSPrimitiveValue::create(value->string, (CSSPrimitiveValue::UnitType) value->unit);
+ else if (value->unit >= CSSPrimitiveValue::CSS_NUMBER && value->unit <= CSSPrimitiveValue::CSS_KHZ)
+ parsedValue = CSSPrimitiveValue::create(value->fValue, (CSSPrimitiveValue::UnitType) value->unit);
+ else if (value->unit >= CSSParserValue::Q_EMS)
+ parsedValue = CSSPrimitiveValue::createAllowingMarginQuirk(value->fValue, CSSPrimitiveValue::CSS_EMS);
+ if (isCalculation(value)) {
+ // FIXME calc() http://webkit.org/b/16662 : actually create a CSSPrimitiveValue here, ie
+ // parsedValue = CSSPrimitiveValue::create(m_parsedCalculation.release());
+ m_parsedCalculation.release();
+ parsedValue = nullptr;
+ }
+ m_valueList->next();
+ }
+ if (!parsedValue || (m_valueList->current() && !inShorthand()))
+ return false;
+
+ addProperty(propId, parsedValue.release(), important);
+ return true;
}
-String quoteCSSStringIfNeeded(const String& string)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseSVGStrokeDasharray()
{
- return isCSSTokenizerIdentifier(string) ? string : quoteCSSString(string);
+ RefPtrWillBeRawPtr<CSSValueList> ret = CSSValueList::createCommaSeparated();
+ CSSParserValue* value = m_valueList->current();
+ bool validPrimitive = true;
+ while (value) {
+ validPrimitive = validUnit(value, FLength | FPercent | FNonNeg, SVGAttributeMode);
+ if (!validPrimitive)
+ break;
+ if (value->id)
+ ret->append(CSSPrimitiveValue::createIdentifier(value->id));
+ else if (value->unit >= CSSPrimitiveValue::CSS_NUMBER && value->unit <= CSSPrimitiveValue::CSS_KHZ)
+ ret->append(CSSPrimitiveValue::create(value->fValue, (CSSPrimitiveValue::UnitType) value->unit));
+ value = m_valueList->next();
+ if (value && value->unit == CSSParserValue::Operator && value->iValue == ',')
+ value = m_valueList->next();
+ }
+ if (!validPrimitive)
+ return nullptr;
+ return ret.release();
}
-String quoteCSSURLIfNeeded(const String& string)
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parseSVGPaint()
{
- return isCSSTokenizerURL(string) ? string : quoteCSSString(string);
+ RGBA32 c = Color::transparent;
+ if (!parseColorFromValue(m_valueList->current(), c))
+ return SVGPaint::createUnknown();
+ return SVGPaint::createColor(Color(c));
}
-bool isValidNthToken(const CSSParserString& token)
+// normal | [ fill || stroke || markers ]
+PassRefPtrWillBeRawPtr<CSSValue> CSSPropertyParser::parsePaintOrder() const
{
- // The tokenizer checks for the construct of an+b.
- // However, since the {ident} rule precedes the {nth} rule, some of those
- // tokens are identified as string literal. Furthermore we need to accept
- // "odd" and "even" which does not match to an+b.
- return equalIgnoringCase(token, "odd") || equalIgnoringCase(token, "even")
- || equalIgnoringCase(token, "n") || equalIgnoringCase(token, "-n");
-}
+ if (m_valueList->size() > 3)
+ return nullptr;
+ CSSParserValue* value = m_valueList->current();
+ if (!value)
+ return nullptr;
+
+ RefPtrWillBeRawPtr<CSSValueList> parsedValues = CSSValueList::createSpaceSeparated();
+
+ // The default paint-order is: Fill, Stroke, Markers.
+ bool seenFill = false, seenStroke = false, seenMarkers = false;
+
+ do {
+ switch (value->id) {
+ case CSSValueNormal:
+ // normal inside [fill || stroke || markers] not valid
+ return nullptr;
+ case CSSValueFill:
+ if (seenFill)
+ return nullptr;
+
+ seenFill = true;
+ break;
+ case CSSValueStroke:
+ if (seenStroke)
+ return nullptr;
+
+ seenStroke = true;
+ break;
+ case CSSValueMarkers:
+ if (seenMarkers)
+ return nullptr;
+
+ seenMarkers = true;
+ break;
+ default:
+ return nullptr;
+ }
+
+ parsedValues->append(CSSPrimitiveValue::createIdentifier(value->id));
+ } while ((value = m_valueList->next()));
+
+ // fill out the rest of the paint order
+ if (!seenFill)
+ parsedValues->append(CSSPrimitiveValue::createIdentifier(CSSValueFill));
+ if (!seenStroke)
+ parsedValues->append(CSSPrimitiveValue::createIdentifier(CSSValueStroke));
+ if (!seenMarkers)
+ parsedValues->append(CSSPrimitiveValue::createIdentifier(CSSValueMarkers));
+
+ return parsedValues.release();
}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.h b/chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.h
new file mode 100644
index 00000000000..1fc76568cee
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/CSSPropertyParser.h
@@ -0,0 +1,410 @@
+/*
+ * Copyright (C) 2003 Lars Knoll (knoll@kde.org)
+ * Copyright (C) 2004, 2005, 2006, 2008, 2009, 2010 Apple Inc. All rights reserved.
+ * Copyright (C) 2008 Eric Seidel <eric@webkit.org>
+ * Copyright (C) 2009 - 2010 Torch Mobile (Beijing) Co. Ltd. All rights reserved.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef CSSPropertyParser_h
+#define CSSPropertyParser_h
+
+// FIXME: Way too many.
+#include "core/CSSPropertyNames.h"
+#include "core/CSSValueKeywords.h"
+#include "core/css/CSSCalculationValue.h"
+#include "core/css/CSSFilterValue.h"
+#include "core/css/CSSGradientValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
+#include "core/css/CSSParserMode.h"
+#include "core/css/CSSParserValues.h"
+#include "core/css/CSSProperty.h"
+#include "core/css/CSSPropertySourceData.h"
+#include "core/css/CSSSelector.h"
+#include "platform/graphics/Color.h"
+#include "wtf/OwnPtr.h"
+#include "wtf/Vector.h"
+
+namespace WebCore {
+
+// FIXME: Many of these may not be used.
+class CSSArrayFunctionValue;
+class CSSBorderImageSliceValue;
+class CSSPrimitiveValue;
+class CSSSelectorList;
+class CSSValue;
+class CSSValueList;
+class CSSBasicShape;
+class CSSBasicShapeInset;
+class CSSGridLineNamesValue;
+class Document;
+class Element;
+class ImmutableStylePropertySet;
+class StyleKeyframe;
+class StylePropertyShorthand;
+class StyleKeyframe;
+class UseCounter;
+
+// Inputs: PropertyID, isImportant bool, CSSParserValueList.
+// Outputs: Vector of CSSProperties
+
+class CSSPropertyParser {
+ STACK_ALLOCATED();
+public:
+ CSSPropertyParser(OwnPtr<CSSParserValueList>&,
+ const CSSParserContext&, bool inViewport, bool savedImportant,
+ WillBeHeapVector<CSSProperty, 256>&, CSSRuleSourceData::Type);
+ ~CSSPropertyParser();
+
+ // FIXME: Should this be on a separate ColorParser object?
+ template<typename StringType>
+ static bool fastParseColor(RGBA32&, const StringType&, bool strict);
+
+ bool parseValue(CSSPropertyID, bool important);
+
+ static bool isSystemColor(int id);
+
+private:
+ bool inShorthand() const { return m_inParseShorthand; }
+ bool inQuirksMode() const { return isQuirksModeBehavior(m_context.mode()); }
+
+ bool inViewport() const { return m_inViewport; }
+ bool parseViewportProperty(CSSPropertyID propId, bool important);
+ bool parseViewportShorthand(CSSPropertyID propId, CSSPropertyID first, CSSPropertyID second, bool important);
+
+ KURL completeURL(const String& url) const;
+
+ void addPropertyWithPrefixingVariant(CSSPropertyID, PassRefPtrWillBeRawPtr<CSSValue>, bool important, bool implicit = false);
+ void addProperty(CSSPropertyID, PassRefPtrWillBeRawPtr<CSSValue>, bool important, bool implicit = false);
+ void rollbackLastProperties(int num);
+ bool hasProperties() const { return !m_parsedProperties.isEmpty(); }
+ void addExpandedPropertyForValue(CSSPropertyID propId, PassRefPtrWillBeRawPtr<CSSValue>, bool);
+
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseValidPrimitive(CSSValueID ident, CSSParserValue*);
+
+ bool parseShorthand(CSSPropertyID, const StylePropertyShorthand&, bool important);
+ bool parse4Values(CSSPropertyID, const CSSPropertyID* properties, bool important);
+ bool parseContent(CSSPropertyID, bool important);
+ bool parseQuotes(CSSPropertyID, bool important);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseAttr(CSSParserValueList* args);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseBackgroundColor();
+
+ bool parseFillImage(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&);
+
+ enum FillPositionFlag { InvalidFillPosition = 0, AmbiguousFillPosition = 1, XFillPosition = 2, YFillPosition = 4 };
+ enum FillPositionParsingMode { ResolveValuesAsPercent = 0, ResolveValuesAsKeyword = 1 };
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseFillPositionComponent(CSSParserValueList*, unsigned& cumulativeFlags, FillPositionFlag& individualFlag, FillPositionParsingMode = ResolveValuesAsPercent);
+ PassRefPtrWillBeRawPtr<CSSValue> parseFillPositionX(CSSParserValueList*);
+ PassRefPtrWillBeRawPtr<CSSValue> parseFillPositionY(CSSParserValueList*);
+ void parse2ValuesFillPosition(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+ bool isPotentialPositionValue(CSSParserValue*);
+ void parseFillPosition(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+ void parse3ValuesFillPosition(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&, PassRefPtrWillBeRawPtr<CSSPrimitiveValue>, PassRefPtrWillBeRawPtr<CSSPrimitiveValue>);
+ void parse4ValuesFillPosition(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&, PassRefPtrWillBeRawPtr<CSSPrimitiveValue>, PassRefPtrWillBeRawPtr<CSSPrimitiveValue>);
+
+ void parseFillRepeat(RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+ PassRefPtrWillBeRawPtr<CSSValue> parseFillSize(CSSPropertyID, bool &allowComma);
+
+ bool parseFillProperty(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+ bool parseFillShorthand(CSSPropertyID, const CSSPropertyID* properties, int numProperties, bool important);
+
+ void addFillValue(RefPtrWillBeRawPtr<CSSValue>& lval, PassRefPtrWillBeRawPtr<CSSValue> rval);
+
+ void addAnimationValue(RefPtrWillBeRawPtr<CSSValue>& lval, PassRefPtrWillBeRawPtr<CSSValue> rval);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationDelay();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationDirection();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationDuration();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationFillMode();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationIterationCount();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationName();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationPlayState();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationProperty();
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationTimingFunction();
+
+ bool parseWebkitTransformOriginShorthand(RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+ bool parseCubicBezierTimingFunctionValue(CSSParserValueList*& args, double& result);
+ PassRefPtrWillBeRawPtr<CSSValue> parseAnimationProperty(CSSPropertyID);
+ PassRefPtrWillBeRawPtr<CSSValueList> parseAnimationPropertyList(CSSPropertyID);
+ bool parseTransitionShorthand(CSSPropertyID, bool important);
+ bool parseAnimationShorthand(CSSPropertyID, bool important);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseColumnWidth();
+ PassRefPtrWillBeRawPtr<CSSValue> parseColumnCount();
+ bool parseColumnsShorthand(bool important);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseGridPosition();
+ bool parseIntegerOrCustomIdentFromGridPosition(RefPtrWillBeRawPtr<CSSPrimitiveValue>& numericValue, RefPtrWillBeRawPtr<CSSPrimitiveValue>& gridLineName);
+ bool parseGridItemPositionShorthand(CSSPropertyID, bool important);
+ bool parseGridTemplateRowsAndAreas(PassRefPtrWillBeRawPtr<CSSValue>, bool important);
+ bool parseGridTemplateShorthand(bool important);
+ bool parseGridShorthand(bool important);
+ bool parseGridAreaShorthand(bool important);
+ bool parseSingleGridAreaLonghand(RefPtrWillBeRawPtr<CSSValue>&);
+ PassRefPtrWillBeRawPtr<CSSValue> parseGridTrackList(bool important);
+ bool parseGridTrackRepeatFunction(CSSValueList&);
+ PassRefPtrWillBeRawPtr<CSSValue> parseGridTrackSize(CSSParserValueList& inputList);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseGridBreadth(CSSParserValue*);
+ bool parseGridTemplateAreasRow(NamedGridAreaMap&, const size_t, size_t&);
+ PassRefPtrWillBeRawPtr<CSSValue> parseGridTemplateAreas();
+ void parseGridLineNames(CSSParserValueList&, CSSValueList&, CSSGridLineNamesValue* = 0);
+
+ bool parseClipShape(CSSPropertyID, bool important);
+
+ bool parseItemPositionOverflowPosition(CSSPropertyID, bool important);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseShapeProperty(CSSPropertyID propId);
+ PassRefPtrWillBeRawPtr<CSSValue> parseBasicShapeAndOrBox();
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseBasicShape();
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseShapeRadius(CSSParserValue*);
+
+ PassRefPtrWillBeRawPtr<CSSBasicShape> parseBasicShapeCircle(CSSParserValueList* args);
+ PassRefPtrWillBeRawPtr<CSSBasicShape> parseBasicShapeEllipse(CSSParserValueList* args);
+ PassRefPtrWillBeRawPtr<CSSBasicShape> parseBasicShapePolygon(CSSParserValueList* args);
+ PassRefPtrWillBeRawPtr<CSSBasicShape> parseBasicShapeInset(CSSParserValueList* args);
+
+ bool parseFont(bool important);
+ PassRefPtrWillBeRawPtr<CSSValueList> parseFontFamily();
+
+ bool parseCounter(CSSPropertyID, int defaultValue, bool important);
+ PassRefPtrWillBeRawPtr<CSSValue> parseCounterContent(CSSParserValueList* args, bool counters);
+
+ bool parseColorParameters(CSSParserValue*, int* colorValues, bool parseAlpha);
+ bool parseHSLParameters(CSSParserValue*, double* colorValues, bool parseAlpha);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseColor(CSSParserValue* = 0);
+ bool parseColorFromValue(CSSParserValue*, RGBA32&);
+
+ bool parseLineHeight(bool important);
+ bool parseFontSize(bool important);
+ bool parseFontVariant(bool important);
+ bool parseFontWeight(bool important);
+ bool parseFontFaceSrc();
+ bool parseFontFaceUnicodeRange();
+
+ bool parseSVGValue(CSSPropertyID propId, bool important);
+ PassRefPtrWillBeRawPtr<CSSValue> parseSVGPaint();
+ PassRefPtrWillBeRawPtr<CSSValue> parseSVGStrokeDasharray();
+
+ PassRefPtrWillBeRawPtr<CSSValue> parsePaintOrder() const;
+
+ // CSS3 Parsing Routines (for properties specific to CSS3)
+ PassRefPtrWillBeRawPtr<CSSValueList> parseShadow(CSSParserValueList*, CSSPropertyID);
+ bool parseBorderImageShorthand(CSSPropertyID, bool important);
+ PassRefPtrWillBeRawPtr<CSSValue> parseBorderImage(CSSPropertyID);
+ bool parseBorderImageRepeat(RefPtrWillBeRawPtr<CSSValue>&);
+ bool parseBorderImageSlice(CSSPropertyID, RefPtrWillBeRawPtr<CSSBorderImageSliceValue>&);
+ bool parseBorderImageWidth(RefPtrWillBeRawPtr<CSSPrimitiveValue>&);
+ bool parseBorderImageOutset(RefPtrWillBeRawPtr<CSSPrimitiveValue>&);
+ bool parseBorderRadius(CSSPropertyID, bool important);
+
+ bool parseAspectRatio(bool important);
+
+ bool parseReflect(CSSPropertyID, bool important);
+
+ bool parseFlex(CSSParserValueList* args, bool important);
+
+ bool parseObjectPosition(bool important);
+
+ // Image generators
+ bool parseCanvas(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&);
+
+ bool parseDeprecatedGradient(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&);
+ bool parseDeprecatedLinearGradient(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, CSSGradientRepeat repeating);
+ bool parseDeprecatedRadialGradient(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, CSSGradientRepeat repeating);
+ bool parseLinearGradient(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, CSSGradientRepeat repeating);
+ bool parseRadialGradient(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&, CSSGradientRepeat repeating);
+ bool parseGradientColorStops(CSSParserValueList*, CSSGradientValue*, bool expectComma);
+
+ bool parseCrossfade(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseImageSet(CSSParserValueList*);
+
+ bool parseWillChange(bool important);
+
+ PassRefPtrWillBeRawPtr<CSSValueList> parseFilter();
+ PassRefPtrWillBeRawPtr<CSSFilterValue> parseBuiltinFilterArguments(CSSParserValueList*, CSSFilterValue::FilterOperationType);
+
+ PassRefPtrWillBeRawPtr<CSSValueList> parseTransformOrigin();
+ PassRefPtrWillBeRawPtr<CSSValueList> parseTransform(CSSPropertyID);
+ PassRefPtrWillBeRawPtr<CSSValue> parseTransformValue(CSSPropertyID, CSSParserValue*);
+ bool parseWebkitTransformOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, CSSPropertyID& propId3, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+ bool parseWebkitPerspectiveOrigin(CSSPropertyID propId, CSSPropertyID& propId1, CSSPropertyID& propId2, RefPtrWillBeRawPtr<CSSValue>&, RefPtrWillBeRawPtr<CSSValue>&);
+
+ bool parseTextEmphasisStyle(bool important);
+
+ bool parseTouchAction(bool important);
+
+ void addTextDecorationProperty(CSSPropertyID, PassRefPtrWillBeRawPtr<CSSValue>, bool important);
+ bool parseTextDecoration(CSSPropertyID propId, bool important);
+ bool parseTextUnderlinePosition(bool important);
+
+ PassRefPtrWillBeRawPtr<CSSValue> parseTextIndent();
+
+ bool parseLineBoxContain(bool important);
+ bool parseCalculation(CSSParserValue*, ValueRange);
+
+ bool parseFontFeatureTag(CSSValueList*);
+ bool parseFontFeatureSettings(bool important);
+
+ bool parseFontVariantLigatures(bool important);
+
+ bool parseGeneratedImage(CSSParserValueList*, RefPtrWillBeRawPtr<CSSValue>&);
+
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createPrimitiveNumericValue(CSSParserValue*);
+ PassRefPtrWillBeRawPtr<CSSPrimitiveValue> createPrimitiveStringValue(CSSParserValue*);
+
+ PassRefPtrWillBeRawPtr<CSSValue> createCSSImageValueWithReferrer(const String& rawValue, const KURL&);
+
+ bool validWidthOrHeight(CSSParserValue*);
+
+ PassRefPtrWillBeRawPtr<CSSBasicShape> parseInsetRoundedCorners(PassRefPtrWillBeRawPtr<CSSBasicShapeInset>, CSSParserValueList*);
+
+ enum SizeParameterType {
+ None,
+ Auto,
+ Length,
+ PageSize,
+ Orientation,
+ };
+
+ bool parsePage(CSSPropertyID propId, bool important);
+ bool parseSize(CSSPropertyID propId, bool important);
+ SizeParameterType parseSizeParameter(CSSValueList* parsedValues, CSSParserValue*, SizeParameterType prevParamType);
+
+ bool parseFontFaceSrcURI(CSSValueList*);
+ bool parseFontFaceSrcLocal(CSSValueList*);
+
+ enum PropertyType {
+ PropertyExplicit,
+ PropertyImplicit
+ };
+
+ class ImplicitScope {
+ STACK_ALLOCATED();
+ WTF_MAKE_NONCOPYABLE(ImplicitScope);
+ public:
+ ImplicitScope(CSSPropertyParser* parser, PropertyType propertyType)
+ : m_parser(parser)
+ {
+ m_parser->m_implicitShorthand = propertyType == CSSPropertyParser::PropertyImplicit;
+ }
+
+ ~ImplicitScope()
+ {
+ m_parser->m_implicitShorthand = false;
+ }
+
+ private:
+ CSSPropertyParser* m_parser;
+ };
+
+ class ShorthandScope {
+ STACK_ALLOCATED();
+ public:
+ ShorthandScope(CSSPropertyParser* parser, CSSPropertyID propId) : m_parser(parser)
+ {
+ if (!(m_parser->m_inParseShorthand++))
+ m_parser->m_currentShorthand = propId;
+ }
+ ~ShorthandScope()
+ {
+ if (!(--m_parser->m_inParseShorthand))
+ m_parser->m_currentShorthand = CSSPropertyInvalid;
+ }
+
+ private:
+ CSSPropertyParser* m_parser;
+ };
+
+ enum ReleaseParsedCalcValueCondition {
+ ReleaseParsedCalcValue,
+ DoNotReleaseParsedCalcValue
+ };
+
+ enum Units {
+ FUnknown = 0x0000,
+ FInteger = 0x0001,
+ FNumber = 0x0002, // Real Numbers
+ FPercent = 0x0004,
+ FLength = 0x0008,
+ FAngle = 0x0010,
+ FTime = 0x0020,
+ FFrequency = 0x0040,
+ FPositiveInteger = 0x0080,
+ FRelative = 0x0100,
+ FResolution = 0x0200,
+ FNonNeg = 0x0400
+ };
+
+ friend inline Units operator|(Units a, Units b)
+ {
+ return static_cast<Units>(static_cast<unsigned>(a) | static_cast<unsigned>(b));
+ }
+
+ bool validCalculationUnit(CSSParserValue*, Units, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue);
+
+ bool shouldAcceptUnitLessValues(CSSParserValue*, Units, CSSParserMode);
+
+ inline bool validUnit(CSSParserValue* value, Units unitflags, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue) { return validUnit(value, unitflags, m_context.mode(), releaseCalc); }
+ bool validUnit(CSSParserValue*, Units, CSSParserMode, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue);
+
+ bool parseBorderImageQuad(Units, RefPtrWillBeRawPtr<CSSPrimitiveValue>&);
+ int colorIntFromValue(CSSParserValue*);
+ double parsedDouble(CSSParserValue*, ReleaseParsedCalcValueCondition releaseCalc = DoNotReleaseParsedCalcValue);
+ bool isCalculation(CSSParserValue*);
+
+private:
+ // Inputs:
+ // FIXME: This should not be an OwnPtr&, many callers will need to be changed.
+ const OwnPtr<CSSParserValueList>& m_valueList;
+ const CSSParserContext& m_context;
+ const bool m_inViewport;
+ const bool m_important; // FIXME: This is only used by font-face-src and unicode-range and undoubtably wrong!
+
+ // Outputs:
+ WillBeHeapVector<CSSProperty, 256>& m_parsedProperties;
+ CSSRuleSourceData::Type m_ruleType;
+
+ // Locals during parsing:
+ int m_inParseShorthand;
+ CSSPropertyID m_currentShorthand;
+ bool m_implicitShorthand;
+ RefPtrWillBeMember<CSSCalcValue> m_parsedCalculation;
+
+ // FIXME: There is probably a small set of APIs we could expose for these
+ // classes w/o needing to make them friends.
+ friend class ShadowParseContext;
+ friend class BorderImageParseContext;
+ friend class BorderImageSliceParseContext;
+ friend class BorderImageQuadParseContext;
+ friend class TransformOperationInfo;
+ friend bool parseDeprecatedGradientColorStop(CSSPropertyParser*, CSSParserValue*, CSSGradientColorStop&);
+ friend PassRefPtrWillBeRawPtr<CSSPrimitiveValue> parseGradientColorOrKeyword(CSSPropertyParser*, CSSParserValue*);
+};
+
+CSSPropertyID cssPropertyID(const CSSParserString&);
+CSSPropertyID cssPropertyID(const String&);
+CSSValueID cssValueKeywordID(const CSSParserString&);
+
+bool isKeywordPropertyID(CSSPropertyID);
+bool isValidKeywordPropertyAndValue(CSSPropertyID, CSSValueID, const CSSParserContext&);
+
+} // namespace WebCore
+
+#endif // CSSPropertyParser_h
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaConditionTest.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaConditionTest.cpp
new file mode 100644
index 00000000000..46985d38ad2
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaConditionTest.cpp
@@ -0,0 +1,54 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+
+#include "core/css/MediaList.h"
+#include "core/css/MediaQuery.h"
+#include "core/css/parser/MediaQueryParser.h"
+#include "core/css/parser/MediaQueryTokenizer.h"
+#include "wtf/PassOwnPtr.h"
+#include "wtf/text/StringBuilder.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+typedef struct {
+ const char* input;
+ const char* output;
+} TestCase;
+
+TEST(MediaConditionParserTest, Basic)
+{
+ // The first string represents the input string.
+ // The second string represents the output string, if present.
+ // Otherwise, the output string is identical to the first string.
+ TestCase testCases[] = {
+ {"screen", "not all"},
+ {"screen and (color)", "not all"},
+ {"all and (min-width:500px)", "not all"},
+ {"(min-width:500px)", "(min-width: 500px)"},
+ {"screen and (color), projection and (color)", "not all"},
+ {"(min-width: -100px)", "not all"},
+ {"(min-width: 100px) and print", "not all"},
+ {"(min-width: 100px) and (max-width: 900px)", "(max-width: 900px) and (min-width: 100px)"},
+ {"(min-width: [100px) and (max-width: 900px)", "not all"},
+ {0, 0} // Do not remove the terminator line.
+ };
+
+ for (unsigned i = 0; testCases[i].input; ++i) {
+ Vector<MediaQueryToken> tokens;
+ MediaQueryTokenizer::tokenize(testCases[i].input, tokens);
+ MediaQueryTokenIterator endToken;
+ // Stop the input once we hit a comma token
+ for (endToken = tokens.begin(); endToken != tokens.end() && endToken->type() != CommaToken; ++endToken) { }
+ RefPtrWillBeRawPtr<MediaQuerySet> mediaConditionQuerySet = MediaQueryParser::parseMediaCondition(tokens.begin(), endToken);
+ ASSERT_EQ(mediaConditionQuerySet->queryVector().size(), (unsigned)1);
+ String queryText = mediaConditionQuerySet->queryVector()[0]->cssText();
+ ASSERT_STREQ(testCases[i].output, queryText.ascii().data());
+ }
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.cpp
new file mode 100644
index 00000000000..fdceea230d0
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.cpp
@@ -0,0 +1,28 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/MediaQueryBlockWatcher.h"
+
+#include "core/css/parser/MediaQueryToken.h"
+
+namespace WebCore {
+
+MediaQueryBlockWatcher::MediaQueryBlockWatcher()
+ : m_blockLevel(0)
+{
+}
+
+void MediaQueryBlockWatcher::handleToken(const MediaQueryToken& token)
+{
+ if (token.blockType() == MediaQueryToken::BlockStart) {
+ ++m_blockLevel;
+ } else if (token.blockType() == MediaQueryToken::BlockEnd) {
+ ASSERT(m_blockLevel);
+ --m_blockLevel;
+ }
+}
+
+} // namespace
+
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.h b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.h
new file mode 100644
index 00000000000..73937c06653
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryBlockWatcher.h
@@ -0,0 +1,25 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaQueryBlockWatcher_h
+#define MediaQueryBlockWatcher_h
+
+namespace WebCore {
+
+class MediaQueryToken;
+
+class MediaQueryBlockWatcher {
+public:
+
+ MediaQueryBlockWatcher();
+ void handleToken(const MediaQueryToken&);
+ unsigned blockLevel() const { return m_blockLevel; }
+
+private:
+ unsigned m_blockLevel;
+};
+
+} // namespace
+
+#endif // MediaQueryBlockWatcher_h
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.cpp
new file mode 100644
index 00000000000..a5adeb551a4
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.cpp
@@ -0,0 +1,66 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/MediaQueryInputStream.h"
+
+#include "core/html/parser/InputStreamPreprocessor.h"
+
+namespace WebCore {
+
+MediaQueryInputStream::MediaQueryInputStream(String input)
+ : m_offset(0)
+ , m_string(input)
+{
+}
+
+UChar MediaQueryInputStream::peek(unsigned lookaheadOffset)
+{
+ ASSERT((m_offset + lookaheadOffset) <= maxLength());
+ if ((m_offset + lookaheadOffset) >= m_string.length())
+ return kEndOfFileMarker;
+ return m_string[m_offset + lookaheadOffset];
+}
+
+void MediaQueryInputStream::advance(unsigned offset)
+{
+ ASSERT(m_offset + offset <= maxLength());
+ m_offset += offset;
+}
+
+void MediaQueryInputStream::pushBack(UChar cc)
+{
+ --m_offset;
+ ASSERT(nextInputChar() == cc);
+}
+
+unsigned long long MediaQueryInputStream::getUInt(unsigned start, unsigned end)
+{
+ ASSERT(start <= end && ((m_offset + end) <= m_string.length()));
+ bool isResultOK = false;
+ unsigned long long result = 0;
+ if (start < end) {
+ if (m_string.is8Bit())
+ result = charactersToUInt64Strict(m_string.characters8() + m_offset + start, end - start, &isResultOK);
+ else
+ result = charactersToUInt64Strict(m_string.characters16() + m_offset + start, end - start, &isResultOK);
+ }
+ return isResultOK ? result : 0;
+}
+
+double MediaQueryInputStream::getDouble(unsigned start, unsigned end)
+{
+ ASSERT(start <= end && ((m_offset + end) <= m_string.length()));
+ bool isResultOK = false;
+ double result = 0.0;
+ if (start < end) {
+ if (m_string.is8Bit())
+ result = charactersToDouble(m_string.characters8() + m_offset + start, end - start, &isResultOK);
+ else
+ result = charactersToDouble(m_string.characters16() + m_offset + start, end - start, &isResultOK);
+ }
+ return isResultOK ? result : 0.0;
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.h b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.h
new file mode 100644
index 00000000000..24018d095bd
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryInputStream.h
@@ -0,0 +1,57 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaQueryInputStream_h
+#define MediaQueryInputStream_h
+
+#include "wtf/text/WTFString.h"
+
+namespace WebCore {
+
+class MediaQueryInputStream {
+ WTF_MAKE_NONCOPYABLE(MediaQueryInputStream);
+ WTF_MAKE_FAST_ALLOCATED;
+public:
+ MediaQueryInputStream(String input);
+
+ UChar peek(unsigned);
+ inline UChar nextInputChar()
+ {
+ return peek(0);
+ }
+
+ void advance(unsigned = 1);
+ void pushBack(UChar);
+
+ inline size_t maxLength()
+ {
+ return m_string.length() + 1;
+ }
+
+ inline size_t leftChars()
+ {
+ return m_string.length() - m_offset;
+
+ }
+
+ unsigned long long getUInt(unsigned start, unsigned end);
+ double getDouble(unsigned start, unsigned end);
+
+ template<bool characterPredicate(UChar)>
+ unsigned skipWhilePredicate(unsigned offset)
+ {
+ while ((m_offset + offset) < m_string.length() && characterPredicate(m_string[m_offset + offset]))
+ ++offset;
+ return offset;
+ }
+
+private:
+ size_t m_offset;
+ String m_string;
+};
+
+} // namespace WebCore
+
+#endif // MediaQueryInputStream_h
+
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.cpp
new file mode 100644
index 00000000000..63b720cfe4b
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.cpp
@@ -0,0 +1,265 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/MediaQueryParser.h"
+
+#include "core/MediaTypeNames.h"
+#include "core/css/parser/CSSPropertyParser.h"
+#include "core/css/parser/MediaQueryTokenizer.h"
+
+namespace WebCore {
+
+PassRefPtrWillBeRawPtr<MediaQuerySet> MediaQueryParser::parseMediaQuerySet(const String& queryString)
+{
+ // FIXME: Replace the MediaQueryTokenizer with a generic CSSTokenizer, once there is one,
+ // or better yet, replace the MediaQueryParser with a generic thread-safe CSS parser.
+ Vector<MediaQueryToken> tokens;
+ MediaQueryTokenizer::tokenize(queryString, tokens);
+ return MediaQueryParser(MediaQuerySetParser).parseImpl(tokens.begin(), tokens.end());
+}
+
+PassRefPtrWillBeRawPtr<MediaQuerySet> MediaQueryParser::parseMediaCondition(MediaQueryTokenIterator token, MediaQueryTokenIterator endToken)
+{
+ return MediaQueryParser(MediaConditionParser).parseImpl(token, endToken);
+}
+
+const MediaQueryParser::State MediaQueryParser::ReadRestrictor = &MediaQueryParser::readRestrictor;
+const MediaQueryParser::State MediaQueryParser::ReadMediaType = &MediaQueryParser::readMediaType;
+const MediaQueryParser::State MediaQueryParser::ReadAnd = &MediaQueryParser::readAnd;
+const MediaQueryParser::State MediaQueryParser::ReadFeatureStart = &MediaQueryParser::readFeatureStart;
+const MediaQueryParser::State MediaQueryParser::ReadFeature = &MediaQueryParser::readFeature;
+const MediaQueryParser::State MediaQueryParser::ReadFeatureColon = &MediaQueryParser::readFeatureColon;
+const MediaQueryParser::State MediaQueryParser::ReadFeatureValue = &MediaQueryParser::readFeatureValue;
+const MediaQueryParser::State MediaQueryParser::ReadFeatureEnd = &MediaQueryParser::readFeatureEnd;
+const MediaQueryParser::State MediaQueryParser::SkipUntilComma = &MediaQueryParser::skipUntilComma;
+const MediaQueryParser::State MediaQueryParser::SkipUntilBlockEnd = &MediaQueryParser::skipUntilBlockEnd;
+const MediaQueryParser::State MediaQueryParser::Done = &MediaQueryParser::done;
+
+MediaQueryParser::MediaQueryParser(ParserType parserType)
+ : m_parserType(parserType)
+ , m_querySet(MediaQuerySet::create())
+{
+ if (parserType == MediaQuerySetParser)
+ m_state = &MediaQueryParser::readRestrictor;
+ else // MediaConditionParser
+ m_state = &MediaQueryParser::readFeatureStart;
+}
+
+MediaQueryParser::~MediaQueryParser() { };
+
+void MediaQueryParser::setStateAndRestrict(State state, MediaQuery::Restrictor restrictor)
+{
+ m_mediaQueryData.setRestrictor(restrictor);
+ m_state = state;
+}
+
+// State machine member functions start here
+void MediaQueryParser::readRestrictor(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ readMediaType(type, token);
+}
+
+void MediaQueryParser::readMediaType(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == LeftParenthesisToken) {
+ m_state = ReadFeature;
+ } else if (type == IdentToken) {
+ if (m_state == ReadRestrictor && equalIgnoringCase(token.value(), "not")) {
+ setStateAndRestrict(ReadMediaType, MediaQuery::Not);
+ } else if (m_state == ReadRestrictor && equalIgnoringCase(token.value(), "only")) {
+ setStateAndRestrict(ReadMediaType, MediaQuery::Only);
+ } else {
+ m_mediaQueryData.setMediaType(token.value());
+ m_state = ReadAnd;
+ }
+ } else if (type == EOFToken && (!m_querySet->queryVector().size() || m_state != ReadRestrictor)) {
+ m_state = Done;
+ } else {
+ m_state = SkipUntilComma;
+ if (type == CommaToken)
+ skipUntilComma(type, token);
+ }
+}
+
+void MediaQueryParser::readAnd(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == IdentToken && equalIgnoringCase(token.value(), "and")) {
+ m_state = ReadFeatureStart;
+ } else if (type == CommaToken && m_parserType != MediaConditionParser) {
+ m_querySet->addMediaQuery(m_mediaQueryData.takeMediaQuery());
+ m_state = ReadRestrictor;
+ } else if (type == EOFToken) {
+ m_state = Done;
+ } else {
+ m_state = SkipUntilComma;
+ }
+}
+
+void MediaQueryParser::readFeatureStart(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == LeftParenthesisToken)
+ m_state = ReadFeature;
+ else
+ m_state = SkipUntilComma;
+}
+
+void MediaQueryParser::readFeature(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == IdentToken) {
+ m_mediaQueryData.setMediaFeature(token.value());
+ m_state = ReadFeatureColon;
+ } else {
+ m_state = SkipUntilComma;
+ }
+}
+
+void MediaQueryParser::readFeatureColon(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == ColonToken)
+ m_state = ReadFeatureValue;
+ else if (type == RightParenthesisToken || type == EOFToken)
+ readFeatureEnd(type, token);
+ else
+ m_state = SkipUntilBlockEnd;
+}
+
+void MediaQueryParser::readFeatureValue(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == DimensionToken && token.unitType() == CSSPrimitiveValue::CSS_UNKNOWN) {
+ m_state = SkipUntilComma;
+ } else {
+ m_mediaQueryData.addParserValue(type, token);
+ m_state = ReadFeatureEnd;
+ }
+}
+
+void MediaQueryParser::readFeatureEnd(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (type == RightParenthesisToken || type == EOFToken) {
+ if (m_mediaQueryData.addExpression())
+ m_state = ReadAnd;
+ else
+ m_state = SkipUntilComma;
+ } else if (type == DelimiterToken && token.delimiter() == '/') {
+ m_mediaQueryData.addParserValue(type, token);
+ m_state = ReadFeatureValue;
+ } else {
+ m_state = SkipUntilBlockEnd;
+ }
+}
+
+void MediaQueryParser::skipUntilComma(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if ((type == CommaToken && !m_blockWatcher.blockLevel()) || type == EOFToken) {
+ m_state = ReadRestrictor;
+ m_mediaQueryData.clear();
+ m_querySet->addMediaQuery(MediaQuery::createNotAll());
+ }
+}
+
+void MediaQueryParser::skipUntilBlockEnd(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ if (token.blockType() == MediaQueryToken::BlockEnd && !m_blockWatcher.blockLevel())
+ m_state = SkipUntilComma;
+}
+
+void MediaQueryParser::done(MediaQueryTokenType type, const MediaQueryToken& token) { }
+
+void MediaQueryParser::handleBlocks(const MediaQueryToken& token)
+{
+ if (token.blockType() == MediaQueryToken::BlockStart
+ && (token.type() != LeftParenthesisToken || m_blockWatcher.blockLevel()))
+ m_state = SkipUntilBlockEnd;
+}
+
+void MediaQueryParser::processToken(const MediaQueryToken& token)
+{
+ MediaQueryTokenType type = token.type();
+
+ handleBlocks(token);
+ m_blockWatcher.handleToken(token);
+
+ // Call the function that handles current state
+ if (type != WhitespaceToken && type != CommentToken)
+ ((this)->*(m_state))(type, token);
+}
+
+// The state machine loop
+PassRefPtrWillBeRawPtr<MediaQuerySet> MediaQueryParser::parseImpl(MediaQueryTokenIterator token, MediaQueryTokenIterator endToken)
+{
+ for (; token != endToken; ++token)
+ processToken(*token);
+
+ if (m_state != ReadAnd && m_state != ReadRestrictor && m_state != Done && (m_parserType != MediaConditionParser || m_state != ReadFeatureStart))
+ m_querySet->addMediaQuery(MediaQuery::createNotAll());
+ else if (m_mediaQueryData.currentMediaQueryChanged())
+ m_querySet->addMediaQuery(m_mediaQueryData.takeMediaQuery());
+
+ return m_querySet;
+}
+
+MediaQueryData::MediaQueryData()
+ : m_restrictor(MediaQuery::None)
+ , m_mediaType(MediaTypeNames::all)
+ , m_expressions(adoptPtrWillBeNoop(new ExpressionHeapVector))
+ , m_mediaTypeSet(false)
+{
+}
+
+void MediaQueryData::clear()
+{
+ m_restrictor = MediaQuery::None;
+ m_mediaType = MediaTypeNames::all;
+ m_mediaTypeSet = false;
+ m_mediaFeature = String();
+ m_valueList.destroyAndClear();
+ m_expressions = adoptPtrWillBeNoop(new ExpressionHeapVector);
+}
+
+PassOwnPtrWillBeRawPtr<MediaQuery> MediaQueryData::takeMediaQuery()
+{
+ OwnPtrWillBeRawPtr<MediaQuery> mediaQuery = adoptPtrWillBeNoop(new MediaQuery(m_restrictor, m_mediaType, m_expressions.release()));
+ clear();
+ return mediaQuery.release();
+}
+
+bool MediaQueryData::addExpression()
+{
+ OwnPtrWillBeRawPtr<MediaQueryExp> expression = MediaQueryExp::createIfValid(m_mediaFeature, &m_valueList);
+ bool isValid = !!expression;
+ m_expressions->append(expression.release());
+ m_valueList.destroyAndClear();
+ return isValid;
+}
+
+void MediaQueryData::addParserValue(MediaQueryTokenType type, const MediaQueryToken& token)
+{
+ CSSParserValue value;
+ if (type == NumberToken || type == PercentageToken || type == DimensionToken) {
+ value.setFromNumber(token.numericValue(), token.unitType());
+ value.isInt = (token.numericValueType() == IntegerValueType);
+ } else if (type == DelimiterToken) {
+ value.unit = CSSParserValue::Operator;
+ value.iValue = token.delimiter();
+ value.id = CSSValueInvalid;
+ value.isInt = false;
+ } else {
+ CSSParserFunction* function = new CSSParserFunction;
+ function->name.init(token.value());
+ value.setFromFunction(function);
+ CSSParserString tokenValue;
+ tokenValue.init(token.value());
+ value.id = cssValueKeywordID(tokenValue);
+ }
+ m_valueList.addValue(value);
+}
+
+void MediaQueryData::setMediaType(const String& mediaType)
+{
+ m_mediaType = mediaType;
+ m_mediaTypeSet = true;
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.h b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.h
new file mode 100644
index 00000000000..84609982f3c
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryParser.h
@@ -0,0 +1,107 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaQueryParser_h
+#define MediaQueryParser_h
+
+#include "core/css/CSSParserValues.h"
+#include "core/css/MediaList.h"
+#include "core/css/MediaQuery.h"
+#include "core/css/MediaQueryExp.h"
+#include "core/css/parser/MediaQueryBlockWatcher.h"
+#include "core/css/parser/MediaQueryToken.h"
+#include "wtf/Vector.h"
+#include "wtf/text/WTFString.h"
+
+namespace WebCore {
+
+class MediaQuerySet;
+
+class MediaQueryData {
+ STACK_ALLOCATED();
+private:
+ MediaQuery::Restrictor m_restrictor;
+ String m_mediaType;
+ OwnPtrWillBeMember<ExpressionHeapVector> m_expressions;
+ String m_mediaFeature;
+ CSSParserValueList m_valueList;
+ bool m_mediaTypeSet;
+
+public:
+ MediaQueryData();
+ void clear();
+ bool addExpression();
+ void addParserValue(MediaQueryTokenType, const MediaQueryToken&);
+ void setMediaType(const String&);
+ PassOwnPtrWillBeRawPtr<MediaQuery> takeMediaQuery();
+
+ inline bool currentMediaQueryChanged() const
+ {
+ return (m_restrictor != MediaQuery::None || m_mediaTypeSet || m_expressions->size() > 0);
+ }
+
+ inline void setRestrictor(MediaQuery::Restrictor restrictor) { m_restrictor = restrictor; }
+
+ inline void setMediaFeature(const String& str) { m_mediaFeature = str; }
+};
+
+class MediaQueryParser {
+ STACK_ALLOCATED();
+public:
+ static PassRefPtrWillBeRawPtr<MediaQuerySet> parseMediaQuerySet(const String&);
+ static PassRefPtrWillBeRawPtr<MediaQuerySet> parseMediaCondition(MediaQueryTokenIterator, MediaQueryTokenIterator endToken);
+
+private:
+ enum ParserType {
+ MediaQuerySetParser,
+ MediaConditionParser,
+ };
+
+ MediaQueryParser(ParserType);
+ virtual ~MediaQueryParser();
+
+ PassRefPtrWillBeRawPtr<MediaQuerySet> parseImpl(MediaQueryTokenIterator, MediaQueryTokenIterator endToken);
+
+ void processToken(const MediaQueryToken&);
+
+ void readRestrictor(MediaQueryTokenType, const MediaQueryToken&);
+ void readMediaType(MediaQueryTokenType, const MediaQueryToken&);
+ void readAnd(MediaQueryTokenType, const MediaQueryToken&);
+ void readFeatureStart(MediaQueryTokenType, const MediaQueryToken&);
+ void readFeature(MediaQueryTokenType, const MediaQueryToken&);
+ void readFeatureColon(MediaQueryTokenType, const MediaQueryToken&);
+ void readFeatureValue(MediaQueryTokenType, const MediaQueryToken&);
+ void readFeatureEnd(MediaQueryTokenType, const MediaQueryToken&);
+ void skipUntilComma(MediaQueryTokenType, const MediaQueryToken&);
+ void skipUntilBlockEnd(MediaQueryTokenType, const MediaQueryToken&);
+ void done(MediaQueryTokenType, const MediaQueryToken&);
+
+ typedef void (MediaQueryParser::*State)(MediaQueryTokenType, const MediaQueryToken&);
+
+ void setStateAndRestrict(State, MediaQuery::Restrictor);
+ void handleBlocks(const MediaQueryToken&);
+
+ State m_state;
+ ParserType m_parserType;
+ MediaQueryData m_mediaQueryData;
+ RefPtrWillBeMember<MediaQuerySet> m_querySet;
+ MediaQueryBlockWatcher m_blockWatcher;
+
+ const static State ReadRestrictor;
+ const static State ReadMediaType;
+ const static State ReadAnd;
+ const static State ReadFeatureStart;
+ const static State ReadFeature;
+ const static State ReadFeatureColon;
+ const static State ReadFeatureValue;
+ const static State ReadFeatureEnd;
+ const static State SkipUntilComma;
+ const static State SkipUntilBlockEnd;
+ const static State Done;
+
+};
+
+} // namespace WebCore
+
+#endif // MediaQueryParser_h
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.cpp
new file mode 100644
index 00000000000..fb6bcb39d05
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.cpp
@@ -0,0 +1,129 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/MediaQueryToken.h"
+
+#include "wtf/HashMap.h"
+#include "wtf/text/StringHash.h"
+#include <limits.h>
+
+namespace WebCore {
+
+
+MediaQueryToken::MediaQueryToken(MediaQueryTokenType type, BlockType blockType)
+ : m_type(type)
+ , m_delimiter(0)
+ , m_numericValue(0)
+ , m_unit(CSSPrimitiveValue::CSS_UNKNOWN)
+ , m_blockType(blockType)
+{
+}
+
+// Just a helper used for Delimiter tokens.
+MediaQueryToken::MediaQueryToken(MediaQueryTokenType type, UChar c)
+ : m_type(type)
+ , m_delimiter(c)
+ , m_numericValue(0)
+ , m_unit(CSSPrimitiveValue::CSS_UNKNOWN)
+ , m_blockType(NotBlock)
+{
+ ASSERT(m_type == DelimiterToken);
+}
+
+MediaQueryToken::MediaQueryToken(MediaQueryTokenType type, String value, BlockType blockType)
+ : m_type(type)
+ , m_value(value)
+ , m_delimiter(0)
+ , m_numericValue(0)
+ , m_unit(CSSPrimitiveValue::CSS_UNKNOWN)
+ , m_blockType(blockType)
+{
+}
+
+MediaQueryToken::MediaQueryToken(MediaQueryTokenType type, double numericValue, NumericValueType numericValueType)
+ : m_type(type)
+ , m_delimiter(0)
+ , m_numericValueType(numericValueType)
+ , m_numericValue(numericValue)
+ , m_unit(CSSPrimitiveValue::CSS_NUMBER)
+ , m_blockType(NotBlock)
+{
+ ASSERT(type == NumberToken);
+}
+
+void MediaQueryToken::convertToDimensionWithUnit(String unit)
+{
+ ASSERT(m_type == NumberToken);
+ m_type = DimensionToken;
+ m_unit = CSSPrimitiveValue::fromName(unit);
+}
+
+void MediaQueryToken::convertToPercentage()
+{
+ ASSERT(m_type == NumberToken);
+ m_type = PercentageToken;
+ m_unit = CSSPrimitiveValue::CSS_PERCENTAGE;
+}
+
+// This function is used only for testing
+// FIXME - This doesn't cover all possible Token types, but it's enough for current testing.
+String MediaQueryToken::textForUnitTests() const
+{
+ char buffer[std::numeric_limits<float>::digits];
+ if (!m_value.isNull())
+ return m_value;
+ if (m_type == LeftParenthesisToken)
+ return String("(");
+ if (m_type == RightParenthesisToken)
+ return String(")");
+ if (m_type == ColonToken)
+ return String(":");
+ if (m_type == WhitespaceToken)
+ return String(" ");
+
+ if (m_delimiter) {
+ sprintf(buffer, "'%c'", m_delimiter);
+ return String(buffer, strlen(buffer));
+ }
+ if (m_numericValue) {
+ static const unsigned maxUnitBufferLength = 6;
+ char unitBuffer[maxUnitBufferLength] = {0};
+ if (m_unit == CSSPrimitiveValue::CSS_PERCENTAGE)
+ sprintf(unitBuffer, "%s", "%");
+ else if (m_unit == CSSPrimitiveValue::CSS_PX)
+ sprintf(unitBuffer, "%s", "px");
+ else if (m_unit == CSSPrimitiveValue::CSS_EMS)
+ sprintf(unitBuffer, "%s", "em");
+ else if (m_unit != CSSPrimitiveValue::CSS_NUMBER)
+ sprintf(unitBuffer, "%s", "other");
+ if (m_numericValueType == IntegerValueType)
+ sprintf(buffer, "%d%s", static_cast<int>(m_numericValue), unitBuffer);
+ else
+ sprintf(buffer, "%f%s", m_numericValue, unitBuffer);
+
+ return String(buffer, strlen(buffer));
+ }
+ return String();
+}
+
+UChar MediaQueryToken::delimiter() const
+{
+ ASSERT(m_type == DelimiterToken);
+ return m_delimiter;
+}
+
+NumericValueType MediaQueryToken::numericValueType() const
+{
+ ASSERT(m_type == NumberToken || m_type == PercentageToken || m_type == DimensionToken);
+ return m_numericValueType;
+}
+
+double MediaQueryToken::numericValue() const
+{
+ ASSERT(m_type == NumberToken || m_type == PercentageToken || m_type == DimensionToken);
+ return m_numericValue;
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.h b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.h
new file mode 100644
index 00000000000..5e602e8cbf6
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryToken.h
@@ -0,0 +1,88 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaQueryToken_h
+#define MediaQueryToken_h
+
+#include "core/css/CSSPrimitiveValue.h"
+#include "wtf/text/WTFString.h"
+
+namespace WebCore {
+
+enum MediaQueryTokenType {
+ IdentToken = 0,
+ FunctionToken,
+ DelimiterToken,
+ NumberToken,
+ PercentageToken,
+ DimensionToken,
+ WhitespaceToken,
+ ColonToken,
+ SemicolonToken,
+ CommaToken,
+ LeftParenthesisToken,
+ RightParenthesisToken,
+ LeftBracketToken,
+ RightBracketToken,
+ LeftBraceToken,
+ RightBraceToken,
+ StringToken,
+ BadStringToken,
+ EOFToken,
+ CommentToken,
+};
+
+enum NumericValueType {
+ IntegerValueType,
+ NumberValueType,
+};
+
+class MediaQueryToken {
+public:
+ enum BlockType {
+ NotBlock,
+ BlockStart,
+ BlockEnd,
+ };
+
+ MediaQueryToken(MediaQueryTokenType, BlockType = NotBlock);
+ MediaQueryToken(MediaQueryTokenType, String value, BlockType = NotBlock);
+
+ MediaQueryToken(MediaQueryTokenType, UChar); // for DelimiterToken
+ MediaQueryToken(MediaQueryTokenType, double, NumericValueType); // for NumberToken
+
+ // Converts NumberToken to DimensionToken.
+ void convertToDimensionWithUnit(String);
+
+ // Converts NumberToken to PercentageToken.
+ void convertToPercentage();
+
+ MediaQueryTokenType type() const { return m_type; }
+ String value() const { return m_value; }
+ String textForUnitTests() const;
+
+ UChar delimiter() const;
+ NumericValueType numericValueType() const;
+ double numericValue() const;
+ BlockType blockType() const { return m_blockType; }
+ CSSPrimitiveValue::UnitType unitType() const { return m_unit; }
+
+private:
+ MediaQueryTokenType m_type;
+ String m_value;
+
+ UChar m_delimiter; // Could be rolled into m_value?
+
+ NumericValueType m_numericValueType;
+ double m_numericValue;
+ CSSPrimitiveValue::UnitType m_unit;
+
+ BlockType m_blockType;
+};
+
+typedef Vector<MediaQueryToken>::iterator MediaQueryTokenIterator;
+
+} // namespace
+
+#endif // MediaQueryToken_h
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.cpp
new file mode 100644
index 00000000000..1e0b467f4f9
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.cpp
@@ -0,0 +1,527 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/MediaQueryTokenizer.h"
+
+namespace WebCore {
+#include "core/MediaQueryTokenizerCodepoints.cpp"
+}
+
+#include "core/css/parser/MediaQueryInputStream.h"
+#include "core/html/parser/HTMLParserIdioms.h"
+#include "wtf/unicode/CharacterNames.h"
+
+namespace WebCore {
+
+// http://dev.w3.org/csswg/css-syntax/#name-start-code-point
+static bool isNameStart(UChar c)
+{
+ if (isASCIIAlpha(c))
+ return true;
+ if (c == '_')
+ return true;
+ return !isASCII(c);
+}
+
+// http://dev.w3.org/csswg/css-syntax/#name-code-point
+static bool isNameChar(UChar c)
+{
+ return isNameStart(c) || isASCIIDigit(c) || c == '-';
+}
+
+// http://dev.w3.org/csswg/css-syntax/#check-if-two-code-points-are-a-valid-escape
+static bool twoCharsAreValidEscape(UChar first, UChar second)
+{
+ return ((first == '\\') && (second != '\n') && (second != kEndOfFileMarker));
+}
+
+MediaQueryTokenizer::MediaQueryTokenizer(MediaQueryInputStream& inputStream)
+ : m_input(inputStream)
+{
+}
+
+void MediaQueryTokenizer::reconsume(UChar c)
+{
+ m_input.pushBack(c);
+}
+
+UChar MediaQueryTokenizer::consume()
+{
+ UChar current = m_input.nextInputChar();
+ m_input.advance();
+ return current;
+}
+
+void MediaQueryTokenizer::consume(unsigned offset)
+{
+ m_input.advance(offset);
+}
+
+MediaQueryToken MediaQueryTokenizer::whiteSpace(UChar cc)
+{
+ // CSS Tokenization is currently lossy, but we could record
+ // the exact whitespace instead of discarding it here.
+ consumeUntilNonWhitespace();
+ return MediaQueryToken(WhitespaceToken);
+}
+
+static bool popIfBlockMatches(Vector<MediaQueryTokenType>& blockStack, MediaQueryTokenType type)
+{
+ if (!blockStack.isEmpty() && blockStack.last() == type) {
+ blockStack.removeLast();
+ return true;
+ }
+ return false;
+}
+
+MediaQueryToken MediaQueryTokenizer::blockStart(MediaQueryTokenType type)
+{
+ m_blockStack.append(type);
+ return MediaQueryToken(type, MediaQueryToken::BlockStart);
+}
+
+MediaQueryToken MediaQueryTokenizer::blockStart(MediaQueryTokenType blockType, MediaQueryTokenType type, String name)
+{
+ m_blockStack.append(blockType);
+ return MediaQueryToken(type, name, MediaQueryToken::BlockStart);
+}
+
+MediaQueryToken MediaQueryTokenizer::blockEnd(MediaQueryTokenType type, MediaQueryTokenType startType)
+{
+ if (popIfBlockMatches(m_blockStack, startType))
+ return MediaQueryToken(type, MediaQueryToken::BlockEnd);
+ return MediaQueryToken(type);
+}
+
+MediaQueryToken MediaQueryTokenizer::leftParenthesis(UChar cc)
+{
+ return blockStart(LeftParenthesisToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::rightParenthesis(UChar cc)
+{
+ return blockEnd(RightParenthesisToken, LeftParenthesisToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::leftBracket(UChar cc)
+{
+ return blockStart(LeftBracketToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::rightBracket(UChar cc)
+{
+ return blockEnd(RightBracketToken, LeftBracketToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::leftBrace(UChar cc)
+{
+ return blockStart(LeftBraceToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::rightBrace(UChar cc)
+{
+ return blockEnd(RightBraceToken, LeftBraceToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::plusOrFullStop(UChar cc)
+{
+ if (nextCharsAreNumber(cc)) {
+ reconsume(cc);
+ return consumeNumericToken();
+ }
+ return MediaQueryToken(DelimiterToken, cc);
+}
+
+MediaQueryToken MediaQueryTokenizer::asterisk(UChar cc)
+{
+ return MediaQueryToken(DelimiterToken, cc);
+}
+
+MediaQueryToken MediaQueryTokenizer::comma(UChar cc)
+{
+ return MediaQueryToken(CommaToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::hyphenMinus(UChar cc)
+{
+ if (nextCharsAreNumber(cc)) {
+ reconsume(cc);
+ return consumeNumericToken();
+ }
+ if (nextCharsAreIdentifier(cc)) {
+ reconsume(cc);
+ return consumeIdentLikeToken();
+ }
+ return MediaQueryToken(DelimiterToken, cc);
+}
+
+MediaQueryToken MediaQueryTokenizer::solidus(UChar cc)
+{
+ if (consumeIfNext('*')) {
+ // We're intentionally deviating from the spec here, by creating tokens for CSS comments.
+ return consumeUntilCommentEndFound()? MediaQueryToken(CommentToken): MediaQueryToken(EOFToken);
+ }
+
+ return MediaQueryToken(DelimiterToken, cc);
+}
+
+MediaQueryToken MediaQueryTokenizer::colon(UChar cc)
+{
+ return MediaQueryToken(ColonToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::semiColon(UChar cc)
+{
+ return MediaQueryToken(SemicolonToken);
+}
+
+MediaQueryToken MediaQueryTokenizer::reverseSolidus(UChar cc)
+{
+ if (twoCharsAreValidEscape(cc, m_input.nextInputChar())) {
+ reconsume(cc);
+ return consumeIdentLikeToken();
+ }
+ return MediaQueryToken(DelimiterToken, cc);
+}
+
+MediaQueryToken MediaQueryTokenizer::asciiDigit(UChar cc)
+{
+ reconsume(cc);
+ return consumeNumericToken();
+}
+
+MediaQueryToken MediaQueryTokenizer::nameStart(UChar cc)
+{
+ reconsume(cc);
+ return consumeIdentLikeToken();
+}
+
+MediaQueryToken MediaQueryTokenizer::stringStart(UChar cc)
+{
+ return consumeStringTokenUntil(cc);
+}
+
+MediaQueryToken MediaQueryTokenizer::endOfFile(UChar cc)
+{
+ return MediaQueryToken(EOFToken);
+}
+
+void MediaQueryTokenizer::tokenize(String string, Vector<MediaQueryToken>& outTokens)
+{
+ // According to the spec, we should perform preprocessing here.
+ // See: http://dev.w3.org/csswg/css-syntax/#input-preprocessing
+ //
+ // However, we can skip this step since:
+ // * We're using HTML spaces (which accept \r and \f as a valid white space)
+ // * Do not count white spaces
+ // * consumeEscape replaces NULLs for replacement characters
+
+ if (string.isEmpty())
+ return;
+
+ MediaQueryInputStream input(string);
+ MediaQueryTokenizer tokenizer(input);
+ while (true) {
+ MediaQueryToken token = tokenizer.nextToken();
+ outTokens.append(token);
+ if (token.type() == EOFToken)
+ return;
+ }
+}
+
+MediaQueryToken MediaQueryTokenizer::nextToken()
+{
+ // Unlike the HTMLTokenizer, the CSS Syntax spec is written
+ // as a stateless, (fixed-size) look-ahead tokenizer.
+ // We could move to the stateful model and instead create
+ // states for all the "next 3 codepoints are X" cases.
+ // State-machine tokenizers are easier to write to handle
+ // incremental tokenization of partial sources.
+ // However, for now we follow the spec exactly.
+ UChar cc = consume();
+ CodePoint codePointFunc = 0;
+
+ if (isASCII(cc)) {
+ ASSERT_WITH_SECURITY_IMPLICATION(cc < codePointsNumber);
+ codePointFunc = codePoints[cc];
+ } else {
+ codePointFunc = &MediaQueryTokenizer::nameStart;
+ }
+
+ if (codePointFunc)
+ return ((this)->*(codePointFunc))(cc);
+ return MediaQueryToken(DelimiterToken, cc);
+}
+
+static int getSign(MediaQueryInputStream& input, unsigned& offset)
+{
+ int sign = 1;
+ if (input.nextInputChar() == '+') {
+ ++offset;
+ } else if (input.peek(offset) == '-') {
+ sign = -1;
+ ++offset;
+ }
+ return sign;
+}
+
+static unsigned long long getInteger(MediaQueryInputStream& input, unsigned& offset)
+{
+ unsigned intStartPos = offset;
+ offset = input.skipWhilePredicate<isASCIIDigit>(offset);
+ unsigned intEndPos = offset;
+ return input.getUInt(intStartPos, intEndPos);
+}
+
+static double getFraction(MediaQueryInputStream& input, unsigned& offset, unsigned& digitsNumber)
+{
+ unsigned fractionStartPos = 0;
+ unsigned fractionEndPos = 0;
+ if (input.peek(offset) == '.' && isASCIIDigit(input.peek(++offset))) {
+ fractionStartPos = offset - 1;
+ offset = input.skipWhilePredicate<isASCIIDigit>(offset);
+ fractionEndPos = offset;
+ }
+ digitsNumber = fractionEndPos- fractionStartPos;
+ return input.getDouble(fractionStartPos, fractionEndPos);
+}
+
+static unsigned long long getExponent(MediaQueryInputStream& input, unsigned& offset, int& sign)
+{
+ unsigned exponentStartPos = 0;
+ unsigned exponentEndPos = 0;
+ if ((input.peek(offset) == 'E' || input.peek(offset) == 'e')) {
+ int offsetBeforeExponent = offset;
+ ++offset;
+ if (input.peek(offset) == '+') {
+ ++offset;
+ } else if (input.peek(offset) =='-') {
+ sign = -1;
+ ++offset;
+ }
+ exponentStartPos = offset;
+ offset = input.skipWhilePredicate<isASCIIDigit>(offset);
+ exponentEndPos = offset;
+ if (exponentEndPos == exponentStartPos)
+ offset = offsetBeforeExponent;
+ }
+ return input.getUInt(exponentStartPos, exponentEndPos);
+}
+
+// This method merges the following spec sections for efficiency
+// http://www.w3.org/TR/css3-syntax/#consume-a-number
+// http://www.w3.org/TR/css3-syntax/#convert-a-string-to-a-number
+MediaQueryToken MediaQueryTokenizer::consumeNumber()
+{
+ ASSERT(nextCharsAreNumber());
+ NumericValueType type = IntegerValueType;
+ double value = 0;
+ unsigned offset = 0;
+ int exponentSign = 1;
+ unsigned fractionDigits;
+ int sign = getSign(m_input, offset);
+ unsigned long long integerPart = getInteger(m_input, offset);
+ double fractionPart = getFraction(m_input, offset, fractionDigits);
+ unsigned long long exponentPart = getExponent(m_input, offset, exponentSign);
+ double exponent = pow(10, (float)exponentSign * (double)exponentPart);
+ value = (double)sign * ((double)integerPart + fractionPart) * exponent;
+
+ m_input.advance(offset);
+ if (fractionDigits > 0)
+ type = NumberValueType;
+
+ return MediaQueryToken(NumberToken, value, type);
+}
+
+// http://www.w3.org/TR/css3-syntax/#consume-a-numeric-token
+MediaQueryToken MediaQueryTokenizer::consumeNumericToken()
+{
+ MediaQueryToken token = consumeNumber();
+ if (nextCharsAreIdentifier())
+ token.convertToDimensionWithUnit(consumeName());
+ else if (consumeIfNext('%'))
+ token.convertToPercentage();
+ return token;
+}
+
+// http://www.w3.org/TR/css3-syntax/#consume-an-ident-like-token
+MediaQueryToken MediaQueryTokenizer::consumeIdentLikeToken()
+{
+ String name = consumeName();
+ if (consumeIfNext('(')) {
+ return blockStart(LeftParenthesisToken, FunctionToken, name);
+ }
+ return MediaQueryToken(IdentToken, name);
+}
+
+static bool isNewLine(UChar cc)
+{
+ // We check \r and \f here, since we have no preprocessing stage
+ return (cc == '\r' || cc == '\n' || cc == '\f');
+}
+
+// http://dev.w3.org/csswg/css-syntax/#consume-a-string-token
+MediaQueryToken MediaQueryTokenizer::consumeStringTokenUntil(UChar endingCodePoint)
+{
+ StringBuilder output;
+ while (true) {
+ UChar cc = consume();
+ if (cc == endingCodePoint || cc == kEndOfFileMarker) {
+ // The "reconsume" here deviates from the spec, but is required to avoid consuming past the EOF
+ if (cc == kEndOfFileMarker)
+ reconsume(cc);
+ return MediaQueryToken(StringToken, output.toString());
+ }
+ if (isNewLine(cc)) {
+ reconsume(cc);
+ return MediaQueryToken(BadStringToken);
+ }
+ if (cc == '\\') {
+ if (m_input.nextInputChar() == kEndOfFileMarker)
+ continue;
+ if (isNewLine(m_input.nextInputChar()))
+ consume();
+ else
+ output.append(consumeEscape());
+ } else {
+ output.append(cc);
+ }
+ }
+}
+
+void MediaQueryTokenizer::consumeUntilNonWhitespace()
+{
+ // Using HTML space here rather than CSS space since we don't do preprocessing
+ while (isHTMLSpace<UChar>(m_input.nextInputChar()))
+ consume();
+}
+
+bool MediaQueryTokenizer::consumeUntilCommentEndFound()
+{
+ UChar c = consume();
+ while (true) {
+ if (c == kEndOfFileMarker)
+ return false;
+ if (c != '*') {
+ c = consume();
+ continue;
+ }
+ c = consume();
+ if (c == '/')
+ break;
+ }
+ return true;
+}
+
+bool MediaQueryTokenizer::consumeIfNext(UChar character)
+{
+ if (m_input.nextInputChar() == character) {
+ consume();
+ return true;
+ }
+ return false;
+}
+
+// http://www.w3.org/TR/css3-syntax/#consume-a-name
+String MediaQueryTokenizer::consumeName()
+{
+ // FIXME: Is this as efficient as it can be?
+ // The possibility of escape chars mandates a copy AFAICT.
+ StringBuilder result;
+ while (true) {
+ UChar cc = consume();
+ if (isNameChar(cc)) {
+ result.append(cc);
+ continue;
+ }
+ if (twoCharsAreValidEscape(cc, m_input.nextInputChar())) {
+ result.append(consumeEscape());
+ continue;
+ }
+ reconsume(cc);
+ return result.toString();
+ }
+}
+
+// http://dev.w3.org/csswg/css-syntax/#consume-an-escaped-code-point
+UChar MediaQueryTokenizer::consumeEscape()
+{
+ UChar cc = consume();
+ ASSERT(cc != '\n');
+ if (isASCIIHexDigit(cc)) {
+ unsigned consumedHexDigits = 1;
+ StringBuilder hexChars;
+ hexChars.append(cc);
+ while (consumedHexDigits < 6 && isASCIIHexDigit(m_input.nextInputChar())) {
+ cc = consume();
+ hexChars.append(cc);
+ consumedHexDigits++;
+ };
+ bool ok = false;
+ UChar codePoint = hexChars.toString().toUIntStrict(&ok, 16);
+ if (!ok)
+ return WTF::Unicode::replacementCharacter;
+ return codePoint;
+ }
+
+ // Replaces NULLs with replacement characters, since we do not perform preprocessing
+ if (cc == kEndOfFileMarker)
+ return WTF::Unicode::replacementCharacter;
+ return cc;
+}
+
+bool MediaQueryTokenizer::nextTwoCharsAreValidEscape()
+{
+ if (m_input.leftChars() < 1)
+ return false;
+ return twoCharsAreValidEscape(m_input.nextInputChar(), m_input.peek(1));
+}
+
+// http://www.w3.org/TR/css3-syntax/#starts-with-a-number
+bool MediaQueryTokenizer::nextCharsAreNumber(UChar first)
+{
+ UChar second = m_input.nextInputChar();
+ if (isASCIIDigit(first))
+ return true;
+ if (first == '+' || first == '-')
+ return ((isASCIIDigit(second)) || (second == '.' && isASCIIDigit(m_input.peek(1))));
+ if (first =='.')
+ return (isASCIIDigit(second));
+ return false;
+}
+
+bool MediaQueryTokenizer::nextCharsAreNumber()
+{
+ UChar first = consume();
+ bool areNumber = nextCharsAreNumber(first);
+ reconsume(first);
+ return areNumber;
+}
+
+// http://www.w3.org/TR/css3-syntax/#would-start-an-identifier
+bool MediaQueryTokenizer::nextCharsAreIdentifier(UChar first)
+{
+ UChar second = m_input.nextInputChar();
+ if (isNameStart(first) || twoCharsAreValidEscape(first, second))
+ return true;
+
+ if (first == '-') {
+ if (isNameStart(m_input.nextInputChar()))
+ return true;
+ return nextTwoCharsAreValidEscape();
+ }
+
+ return false;
+}
+
+bool MediaQueryTokenizer::nextCharsAreIdentifier()
+{
+ UChar first = consume();
+ bool areIdentifier = nextCharsAreIdentifier(first);
+ reconsume(first);
+ return areIdentifier;
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.h b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.h
new file mode 100644
index 00000000000..c59a96d299a
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizer.h
@@ -0,0 +1,85 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MediaQueryTokenizer_h
+#define MediaQueryTokenizer_h
+
+#include "core/css/parser/MediaQueryToken.h"
+#include "core/html/parser/InputStreamPreprocessor.h"
+#include "wtf/text/WTFString.h"
+
+#include <climits>
+
+namespace WebCore {
+
+class MediaQueryInputStream;
+
+class MediaQueryTokenizer {
+ WTF_MAKE_NONCOPYABLE(MediaQueryTokenizer);
+ WTF_MAKE_FAST_ALLOCATED;
+public:
+ static void tokenize(String, Vector<MediaQueryToken>&);
+private:
+ MediaQueryTokenizer(MediaQueryInputStream&);
+
+ MediaQueryToken nextToken();
+
+ UChar consume();
+ void consume(unsigned);
+ void reconsume(UChar);
+
+ MediaQueryToken consumeNumericToken();
+ MediaQueryToken consumeIdentLikeToken();
+ MediaQueryToken consumeNumber();
+ MediaQueryToken consumeStringTokenUntil(UChar);
+
+ void consumeUntilNonWhitespace();
+ bool consumeUntilCommentEndFound();
+
+ bool consumeIfNext(UChar);
+ String consumeName();
+ UChar consumeEscape();
+
+ bool nextTwoCharsAreValidEscape();
+ bool nextCharsAreNumber(UChar);
+ bool nextCharsAreNumber();
+ bool nextCharsAreIdentifier(UChar);
+ bool nextCharsAreIdentifier();
+ MediaQueryToken blockStart(MediaQueryTokenType);
+ MediaQueryToken blockStart(MediaQueryTokenType blockType, MediaQueryTokenType, String);
+ MediaQueryToken blockEnd(MediaQueryTokenType, MediaQueryTokenType startType);
+
+ typedef MediaQueryToken (MediaQueryTokenizer::*CodePoint)(UChar);
+
+ static const CodePoint codePoints[];
+ Vector<MediaQueryTokenType> m_blockStack;
+
+ MediaQueryToken whiteSpace(UChar);
+ MediaQueryToken leftParenthesis(UChar);
+ MediaQueryToken rightParenthesis(UChar);
+ MediaQueryToken leftBracket(UChar);
+ MediaQueryToken rightBracket(UChar);
+ MediaQueryToken leftBrace(UChar);
+ MediaQueryToken rightBrace(UChar);
+ MediaQueryToken plusOrFullStop(UChar);
+ MediaQueryToken comma(UChar);
+ MediaQueryToken hyphenMinus(UChar);
+ MediaQueryToken asterisk(UChar);
+ MediaQueryToken solidus(UChar);
+ MediaQueryToken colon(UChar);
+ MediaQueryToken semiColon(UChar);
+ MediaQueryToken reverseSolidus(UChar);
+ MediaQueryToken asciiDigit(UChar);
+ MediaQueryToken nameStart(UChar);
+ MediaQueryToken stringStart(UChar);
+ MediaQueryToken endOfFile(UChar);
+
+ MediaQueryInputStream& m_input;
+};
+
+
+
+} // namespace WebCore
+
+#endif // MediaQueryTokenizer_h
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizerTest.cpp b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizerTest.cpp
new file mode 100644
index 00000000000..c611dc435c2
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/MediaQueryTokenizerTest.cpp
@@ -0,0 +1,173 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/MediaQueryTokenizer.h"
+
+#include "core/css/parser/MediaQueryBlockWatcher.h"
+#include "wtf/PassOwnPtr.h"
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+typedef struct {
+ const char* input;
+ const char* output;
+} TestCase;
+
+typedef struct {
+ const char* input;
+ const unsigned maxLevel;
+ const unsigned finalLevel;
+} BlockTestCase;
+
+TEST(MediaQueryTokenizerTest, Basic)
+{
+ TestCase testCases[] = {
+ { "(max-width: 50px)", "(max-width: 50px)" },
+ { "(max-width: 1e+2px)", "(max-width: 100px)" },
+ { "(max-width: 1e2px)", "(max-width: 100px)" },
+ { "(max-width: 1000e-1px)", "(max-width: 100px)" },
+ { "(max-width: 50\\70\\78)", "(max-width: 50px)" },
+ { "(max-width: /* comment */50px)", "(max-width: 50px)" },
+ { "(max-width: /** *commen*t */60px)", "(max-width: 60px)" },
+ { "(max-width: /** *commen*t **/70px)", "(max-width: 70px)" },
+ { "(max-width: /** *commen*t **//**/80px)", "(max-width: 80px)" },
+ { "(max-width: /*/ **/90px)", "(max-width: 90px)" },
+ { "(max-width: /*/ **/*100px)", "(max-width: '*'100px)" },
+ { "(max-width: 110px/*)", "(max-width: 110px" },
+ { "(max-width: 120px)/*", "(max-width: 120px)" },
+ { "(max-width: 130px)/**", "(max-width: 130px)" },
+ { "(max-width: /***/140px)/**/", "(max-width: 140px)" },
+ { "(max-width: '40px')", "(max-width: 40px)" },
+ { "(max-width: '40px", "(max-width: 40px" },
+ { "(max-width: '40px\n", "(max-width: " },
+ { "(max-width: '40px\\", "(max-width: 40px" },
+ { "(max-width: '40px\\\n", "(max-width: 40px" },
+ { "(max-width: '40px\\\n')", "(max-width: 40px)" },
+ { "(max-width: '40\\70\\78')", "(max-width: 40px)" },
+ { "(max-width: '40\\\npx')", "(max-width: 40px)" },
+ { "(max-aspect-ratio: 5)", "(max-aspect-ratio: 5)" },
+ { "(max-aspect-ratio: +5)", "(max-aspect-ratio: 5)" },
+ { "(max-aspect-ratio: -5)", "(max-aspect-ratio: -5)" },
+ { "(max-aspect-ratio: -+5)", "(max-aspect-ratio: '-'5)" },
+ { "(max-aspect-ratio: +-5)", "(max-aspect-ratio: '+'-5)" },
+ { "(max-aspect-ratio: +bla5)", "(max-aspect-ratio: '+'bla5)" },
+ { "(max-aspect-ratio: +5bla)", "(max-aspect-ratio: 5other)" },
+ { "(max-aspect-ratio: -bla)", "(max-aspect-ratio: -bla)" },
+ { "(max-aspect-ratio: --bla)", "(max-aspect-ratio: '-'-bla)" },
+ { 0, 0 } // Do not remove the terminator line.
+ };
+
+ for (int i = 0; testCases[i].input; ++i) {
+ Vector<MediaQueryToken> tokens;
+ MediaQueryTokenizer::tokenize(testCases[i].input, tokens);
+ StringBuilder output;
+ for (size_t j = 0; j < tokens.size(); ++j)
+ output.append(tokens[j].textForUnitTests());
+ ASSERT_STREQ(testCases[i].output, output.toString().ascii().data());
+ }
+}
+
+TEST(MediaQueryTokenizerBlockTest, Basic)
+{
+ BlockTestCase testCases[] = {
+ {"(max-width: 800px()), (max-width: 800px)", 2, 0},
+ {"(max-width: 900px(()), (max-width: 900px)", 3, 1},
+ {"(max-width: 600px(())))), (max-width: 600px)", 3, 0},
+ {"(max-width: 500px(((((((((())))), (max-width: 500px)", 11, 6},
+ {"(max-width: 800px[]), (max-width: 800px)", 2, 0},
+ {"(max-width: 900px[[]), (max-width: 900px)", 3, 2},
+ {"(max-width: 600px[[]]]]), (max-width: 600px)", 3, 0},
+ {"(max-width: 500px[[[[[[[[[[]]]]), (max-width: 500px)", 11, 7},
+ {"(max-width: 800px{}), (max-width: 800px)", 2, 0},
+ {"(max-width: 900px{{}), (max-width: 900px)", 3, 2},
+ {"(max-width: 600px{{}}}}), (max-width: 600px)", 3, 0},
+ {"(max-width: 500px{{{{{{{{{{}}}}), (max-width: 500px)", 11, 7},
+ {"[(), (max-width: 400px)", 2, 1},
+ {"[{}, (max-width: 500px)", 2, 1},
+ {"[{]}], (max-width: 900px)", 2, 0},
+ {"[{[]{}{{{}}}}], (max-width: 900px)", 5, 0},
+ {"[{[}], (max-width: 900px)", 3, 2},
+ {"[({)}], (max-width: 900px)", 3, 2},
+ {"[]((), (max-width: 900px)", 2, 1},
+ {"((), (max-width: 900px)", 2, 1},
+ {"(foo(), (max-width: 900px)", 2, 1},
+ {"[](()), (max-width: 900px)", 2, 0},
+ {"all an[isdfs bla())(i())]icalc(i)(()), (max-width: 400px)", 3, 0},
+ {"all an[isdfs bla())(]icalc(i)(()), (max-width: 500px)", 4, 2},
+ {"all an[isdfs bla())(]icalc(i)(())), (max-width: 600px)", 4, 1},
+ {"all an[isdfs bla())(]icalc(i)(()))], (max-width: 800px)", 4, 0},
+ {0, 0, 0} // Do not remove the terminator line.
+ };
+ for (int i = 0; testCases[i].input; ++i) {
+ Vector<MediaQueryToken> tokens;
+ MediaQueryTokenizer::tokenize(testCases[i].input, tokens);
+ MediaQueryBlockWatcher blockWatcher;
+
+ unsigned maxLevel = 0;
+ unsigned level = 0;
+ for (size_t j = 0; j < tokens.size(); ++j) {
+ blockWatcher.handleToken(tokens[j]);
+ level = blockWatcher.blockLevel();
+ maxLevel = std::max(level, maxLevel);
+ }
+ ASSERT_EQ(testCases[i].maxLevel, maxLevel);
+ ASSERT_EQ(testCases[i].finalLevel, level);
+ }
+}
+
+void testToken(UChar c, MediaQueryTokenType tokenType)
+{
+ Vector<MediaQueryToken> tokens;
+ StringBuilder input;
+ input.append(c);
+ MediaQueryTokenizer::tokenize(input.toString(), tokens);
+ ASSERT_EQ(tokens[0].type(), tokenType);
+}
+
+TEST(MediaQueryTokenizerCodepointsTest, Basic)
+{
+ for (UChar c = 0; c <= 1000; ++c) {
+ if (isASCIIDigit(c))
+ testToken(c, NumberToken);
+ else if (isASCIIAlpha(c))
+ testToken(c, IdentToken);
+ else if (c == '_')
+ testToken(c, IdentToken);
+ else if (c == '\r' || c == ' ' || c == '\n' || c == '\t' || c == '\f')
+ testToken(c, WhitespaceToken);
+ else if (c == '(')
+ testToken(c, LeftParenthesisToken);
+ else if (c == ')')
+ testToken(c, RightParenthesisToken);
+ else if (c == '[')
+ testToken(c, LeftBracketToken);
+ else if (c == ']')
+ testToken(c, RightBracketToken);
+ else if (c == '{')
+ testToken(c, LeftBraceToken);
+ else if (c == '}')
+ testToken(c, RightBraceToken);
+ else if (c == '.' || c == '+' || c == '-' || c == '/' || c == '\\')
+ testToken(c, DelimiterToken);
+ else if (c == '\'' || c == '"')
+ testToken(c, StringToken);
+ else if (c == ',')
+ testToken(c, CommaToken);
+ else if (c == ':')
+ testToken(c, ColonToken);
+ else if (c == ';')
+ testToken(c, SemicolonToken);
+ else if (!c)
+ testToken(c, EOFToken);
+ else if (c > SCHAR_MAX)
+ testToken(c, IdentToken);
+ else
+ testToken(c, DelimiterToken);
+ }
+ testToken(USHRT_MAX, IdentToken);
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.cpp b/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.cpp
new file mode 100644
index 00000000000..15f5590fa19
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.cpp
@@ -0,0 +1,141 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/SizesAttributeParser.h"
+
+#include "core/MediaTypeNames.h"
+#include "core/css/MediaQueryEvaluator.h"
+#include "core/css/parser/MediaQueryTokenizer.h"
+#include "core/css/parser/SizesCalcParser.h"
+
+namespace WebCore {
+
+unsigned SizesAttributeParser::findEffectiveSize(const String& attribute, PassRefPtr<MediaValues> mediaValues)
+{
+ Vector<MediaQueryToken> tokens;
+ SizesAttributeParser parser(mediaValues);
+
+ MediaQueryTokenizer::tokenize(attribute, tokens);
+ if (!parser.parse(tokens))
+ return parser.effectiveSizeDefaultValue();
+ return parser.effectiveSize();
+}
+
+bool SizesAttributeParser::calculateLengthInPixels(MediaQueryTokenIterator startToken, MediaQueryTokenIterator endToken, unsigned& result)
+{
+ if (startToken == endToken)
+ return false;
+ MediaQueryTokenType type = startToken->type();
+ if (type == DimensionToken) {
+ int length;
+ if (!CSSPrimitiveValue::isLength(startToken->unitType()))
+ return false;
+ if ((m_mediaValues->computeLength(startToken->numericValue(), startToken->unitType(), length)) && (length > 0)) {
+ result = (unsigned)length;
+ return true;
+ }
+ } else if (type == FunctionToken) {
+ return SizesCalcParser::parse(startToken, endToken, m_mediaValues, result);
+ } else if (type == NumberToken && !startToken->numericValue()) {
+ result = 0;
+ return true;
+ }
+
+ return false;
+}
+
+static void reverseSkipIrrelevantTokens(MediaQueryTokenIterator& token, MediaQueryTokenIterator startToken)
+{
+ MediaQueryTokenIterator endToken = token;
+ while (token != startToken && (token->type() == WhitespaceToken || token->type() == CommentToken || token->type() == EOFToken))
+ --token;
+ if (token != endToken)
+ ++token;
+}
+
+static void reverseSkipUntilComponentStart(MediaQueryTokenIterator& token, MediaQueryTokenIterator startToken)
+{
+ if (token == startToken)
+ return;
+ --token;
+ if (token->blockType() != MediaQueryToken::BlockEnd)
+ return;
+ unsigned blockLevel = 0;
+ while (token != startToken) {
+ if (token->blockType() == MediaQueryToken::BlockEnd) {
+ ++blockLevel;
+ } else if (token->blockType() == MediaQueryToken::BlockStart) {
+ --blockLevel;
+ if (!blockLevel)
+ break;
+ }
+
+ --token;
+ }
+}
+
+bool SizesAttributeParser::mediaConditionMatches(PassRefPtrWillBeRawPtr<MediaQuerySet> mediaCondition)
+{
+ // A Media Condition cannot have a media type other then screen.
+ MediaQueryEvaluator mediaQueryEvaluator(MediaTypeNames::screen, *m_mediaValues);
+ return mediaQueryEvaluator.eval(mediaCondition.get());
+}
+
+bool SizesAttributeParser::parseMediaConditionAndLength(MediaQueryTokenIterator startToken, MediaQueryTokenIterator endToken)
+{
+ MediaQueryTokenIterator lengthTokenStart;
+ MediaQueryTokenIterator lengthTokenEnd;
+
+ reverseSkipIrrelevantTokens(endToken, startToken);
+ lengthTokenEnd = endToken;
+ reverseSkipUntilComponentStart(endToken, startToken);
+ lengthTokenStart = endToken;
+ unsigned length;
+ if (!calculateLengthInPixels(lengthTokenStart, lengthTokenEnd, length))
+ return false;
+ RefPtrWillBeRawPtr<MediaQuerySet> mediaCondition = MediaQueryParser::parseMediaCondition(startToken, endToken);
+ if (mediaCondition && mediaConditionMatches(mediaCondition)) {
+ m_length = length;
+ m_lengthWasSet = true;
+ return true;
+ }
+ return false;
+}
+
+bool SizesAttributeParser::parse(Vector<MediaQueryToken>& tokens)
+{
+ if (tokens.isEmpty())
+ return false;
+ MediaQueryTokenIterator startToken = tokens.begin();
+ MediaQueryTokenIterator endToken;
+ // Split on a comma token, and send the result tokens to be parsed as (media-condition, length) pairs
+ for (MediaQueryTokenIterator token = tokens.begin(); token != tokens.end(); ++token) {
+ if (token->type() == CommaToken) {
+ endToken = token;
+ if (parseMediaConditionAndLength(startToken, endToken))
+ return true;
+ startToken = token;
+ ++startToken;
+ }
+ }
+ endToken = tokens.end();
+ return parseMediaConditionAndLength(startToken, --endToken);
+}
+
+unsigned SizesAttributeParser::effectiveSize()
+{
+ if (m_lengthWasSet)
+ return m_length;
+ return effectiveSizeDefaultValue();
+}
+
+unsigned SizesAttributeParser::effectiveSizeDefaultValue()
+{
+ // Returning the equivalent of "100%"
+ return m_mediaValues->viewportWidth();
+}
+
+} // namespace
+
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.h b/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.h
new file mode 100644
index 00000000000..3c7bc4ee260
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParser.h
@@ -0,0 +1,44 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef SizesAttributeParser_h
+#define SizesAttributeParser_h
+
+#include "core/css/MediaValues.h"
+#include "core/css/parser/MediaQueryParser.h"
+#include "platform/heap/Handle.h"
+#include "wtf/text/WTFString.h"
+
+namespace WebCore {
+
+class SizesAttributeParser {
+ STACK_ALLOCATED();
+public:
+ static unsigned findEffectiveSize(const String& attribute, PassRefPtr<MediaValues>);
+
+private:
+ SizesAttributeParser(PassRefPtr<MediaValues> mediaValues)
+ : m_mediaValues(mediaValues)
+ , m_length(0)
+ , m_lengthWasSet(false)
+ {
+ }
+
+ bool parse(Vector<MediaQueryToken>& tokens);
+ bool parseMediaConditionAndLength(MediaQueryTokenIterator startToken, MediaQueryTokenIterator endToken);
+ unsigned effectiveSize();
+ bool calculateLengthInPixels(MediaQueryTokenIterator startToken, MediaQueryTokenIterator endToken, unsigned& result);
+ bool mediaConditionMatches(PassRefPtrWillBeRawPtr<MediaQuerySet> mediaCondition);
+ unsigned effectiveSizeDefaultValue();
+
+ RefPtrWillBeMember<MediaQuerySet> m_mediaCondition;
+ RefPtr<MediaValues> m_mediaValues;
+ unsigned m_length;
+ bool m_lengthWasSet;
+};
+
+} // namespace
+
+#endif
+
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParserTest.cpp b/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParserTest.cpp
new file mode 100644
index 00000000000..0cc866c2acf
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/SizesAttributeParserTest.cpp
@@ -0,0 +1,82 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/SizesAttributeParser.h"
+
+#include "core/css/MediaValuesCached.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+typedef struct {
+ const char* input;
+ const int output;
+} TestCase;
+
+TEST(SizesAttributeParserTest, Basic)
+{
+ TestCase testCases[] = {
+ {"screen", 500},
+ {"(min-width:500px)", 500},
+ {"(min-width:500px) 200px", 200},
+ {"(min-width:500px) 50vw", 250},
+ {"(min-width:500px) 200px, 400px", 200},
+ {"400px, (min-width:500px) 200px", 400},
+ {"(min-width:5000px) 200px, 400px", 400},
+ {"(blalbadfsdf) 200px, 400px", 400},
+ {"0", 0},
+ {"-0", 0},
+ {"1", 500},
+ {"300px, 400px", 300},
+ {"(min-width:5000px) 200px, (min-width:500px) 400px", 400},
+ {"", 500},
+ {" ", 500},
+ {" /**/ ", 500},
+ {" /**/ 300px", 300},
+ {"300px /**/ ", 300},
+ {" /**/ (min-width:500px) /**/ 300px", 300},
+ {"-100px, 200px", 200},
+ {"-50vw, 20vw", 100},
+ {"50asdf, 200px", 200},
+ {"asdf, 200px", 200},
+ {"(max-width: 3000px) 200w, 400w", 500},
+ {",, , /**/ ,200px", 200},
+ {"50vw", 250},
+ {"calc(40vw*2)", 400},
+ {"(min-width:5000px) calc(5000px/10), (min-width:500px) calc(1200px/3)", 400},
+ {"(min-width:500px) calc(1200/3)", 500},
+ {"(min-width:500px) calc(1200px/(0px*14))", 500},
+ {"(max-width: 3000px) 200px, 400px", 200},
+ {"(max-width: 3000px) 20em, 40em", 320},
+ {"(max-width: 3000px) 0, 40em", 0},
+ {"(max-width: 3000px) 50vw, 40em", 250},
+ {0, 0} // Do not remove the terminator line.
+ };
+
+ MediaValuesCached::MediaValuesCachedData data;
+ data.viewportWidth = 500;
+ data.viewportHeight = 500;
+ data.deviceWidth = 500;
+ data.deviceHeight = 500;
+ data.devicePixelRatio = 2.0;
+ data.colorBitsPerComponent = 24;
+ data.monochromeBitsPerComponent = 0;
+ data.pointer = MediaValues::MousePointer;
+ data.defaultFontSize = 16;
+ data.threeDEnabled = true;
+ data.scanMediaType = false;
+ data.screenMediaType = true;
+ data.printMediaType = false;
+ data.strictMode = true;
+ RefPtr<MediaValues> mediaValues = MediaValuesCached::create(data);
+
+ for (unsigned i = 0; testCases[i].input; ++i) {
+ int effectiveSize = SizesAttributeParser::findEffectiveSize(testCases[i].input, mediaValues);
+ ASSERT_EQ(testCases[i].output, effectiveSize);
+ }
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.cpp b/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.cpp
new file mode 100644
index 00000000000..f99688bb609
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.cpp
@@ -0,0 +1,214 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/SizesCalcParser.h"
+
+#include "core/css/MediaValues.h"
+#include "core/css/parser/MediaQueryToken.h"
+
+namespace WebCore {
+
+bool SizesCalcParser::parse(MediaQueryTokenIterator start, MediaQueryTokenIterator end, PassRefPtr<MediaValues> mediaValues, unsigned& result)
+{
+ SizesCalcParser parser(mediaValues);
+ if (!parser.calcToReversePolishNotation(start, end))
+ return false;
+ return parser.calculate(result);
+}
+
+static bool operatorPriority(UChar cc, bool& highPriority)
+{
+ if (cc == '+' || cc == '-')
+ highPriority = false;
+ else if (cc == '*' || cc == '/')
+ highPriority = true;
+ else
+ return false;
+ return true;
+}
+
+bool SizesCalcParser::handleOperator(Vector<MediaQueryToken>& stack, const MediaQueryToken& token)
+{
+ // If the token is an operator, o1, then:
+ // while there is an operator token, o2, at the top of the stack, and
+ // either o1 is left-associative and its precedence is equal to that of o2,
+ // or o1 has precedence less than that of o2,
+ // pop o2 off the stack, onto the output queue;
+ // push o1 onto the stack.
+ bool stackOperatorPriority;
+ bool incomingOperatorPriority;
+
+ if (!operatorPriority(token.delimiter(), incomingOperatorPriority))
+ return false;
+ if (!stack.isEmpty() && stack.last().type() == DelimiterToken) {
+ if (!operatorPriority(stack.last().delimiter(), stackOperatorPriority))
+ return false;
+ if (!incomingOperatorPriority || stackOperatorPriority) {
+ appendOperator(stack.last());
+ stack.removeLast();
+ }
+ }
+ stack.append(token);
+ return true;
+}
+
+void SizesCalcParser::appendNumber(const MediaQueryToken& token)
+{
+ SizesCalcValue value;
+ value.value = token.numericValue();
+ m_valueList.append(value);
+}
+
+bool SizesCalcParser::appendLength(const MediaQueryToken& token)
+{
+ SizesCalcValue value;
+ double result = 0;
+ if (!m_mediaValues->computeLength(token.numericValue(), token.unitType(), result))
+ return false;
+ value.value = result;
+ value.isLength = true;
+ m_valueList.append(value);
+ return true;
+}
+
+void SizesCalcParser::appendOperator(const MediaQueryToken& token)
+{
+ SizesCalcValue value;
+ value.operation = token.delimiter();
+ m_valueList.append(value);
+}
+
+bool SizesCalcParser::calcToReversePolishNotation(MediaQueryTokenIterator start, MediaQueryTokenIterator end)
+{
+ // This method implements the shunting yard algorithm, to turn the calc syntax into a reverse polish notation.
+ // http://en.wikipedia.org/wiki/Shunting-yard_algorithm
+
+ Vector<MediaQueryToken> stack;
+ for (MediaQueryTokenIterator it = start; it != end; ++it) {
+ MediaQueryTokenType type = it->type();
+ switch (type) {
+ case NumberToken:
+ appendNumber(*it);
+ break;
+ case DimensionToken:
+ if (!CSSPrimitiveValue::isLength(it->unitType()) || !appendLength(*it))
+ return false;
+ break;
+ case DelimiterToken:
+ if (!handleOperator(stack, *it))
+ return false;
+ break;
+ case FunctionToken:
+ if (it->value() != "calc")
+ return false;
+ // "calc(" is the same as "("
+ case LeftParenthesisToken:
+ // If the token is a left parenthesis, then push it onto the stack.
+ stack.append(*it);
+ break;
+ case RightParenthesisToken:
+ // If the token is a right parenthesis:
+ // Until the token at the top of the stack is a left parenthesis, pop operators off the stack onto the output queue.
+ while (!stack.isEmpty() && stack.last().type() != LeftParenthesisToken && stack.last().type() != FunctionToken) {
+ appendOperator(stack.last());
+ stack.removeLast();
+ }
+ // If the stack runs out without finding a left parenthesis, then there are mismatched parentheses.
+ if (stack.isEmpty())
+ return false;
+ // Pop the left parenthesis from the stack, but not onto the output queue.
+ stack.removeLast();
+ break;
+ case CommentToken:
+ case WhitespaceToken:
+ case EOFToken:
+ break;
+ case PercentageToken:
+ case IdentToken:
+ case CommaToken:
+ case ColonToken:
+ case SemicolonToken:
+ case LeftBraceToken:
+ case LeftBracketToken:
+ case RightBraceToken:
+ case RightBracketToken:
+ case StringToken:
+ case BadStringToken:
+ return false;
+ }
+ }
+
+ // When there are no more tokens to read:
+ // While there are still operator tokens in the stack:
+ while (!stack.isEmpty()) {
+ // If the operator token on the top of the stack is a parenthesis, then there are mismatched parentheses.
+ MediaQueryTokenType type = stack.last().type();
+ if (type == LeftParenthesisToken || type == FunctionToken)
+ return false;
+ // Pop the operator onto the output queue.
+ appendOperator(stack.last());
+ stack.removeLast();
+ }
+ return true;
+}
+
+static bool operateOnStack(Vector<SizesCalcValue>& stack, UChar operation)
+{
+ if (stack.size() < 2)
+ return false;
+ SizesCalcValue rightOperand = stack.last();
+ stack.removeLast();
+ SizesCalcValue leftOperand = stack.last();
+ stack.removeLast();
+ bool isLength;
+ switch (operation) {
+ case '+':
+ if (rightOperand.isLength != leftOperand.isLength)
+ return false;
+ isLength = (rightOperand.isLength && leftOperand.isLength);
+ stack.append(SizesCalcValue(leftOperand.value + rightOperand.value, isLength));
+ break;
+ case '-':
+ if (rightOperand.isLength != leftOperand.isLength)
+ return false;
+ isLength = (rightOperand.isLength && leftOperand.isLength);
+ stack.append(SizesCalcValue(leftOperand.value - rightOperand.value, isLength));
+ break;
+ case '*':
+ if (rightOperand.isLength && leftOperand.isLength)
+ return false;
+ isLength = (rightOperand.isLength || leftOperand.isLength);
+ stack.append(SizesCalcValue(leftOperand.value * rightOperand.value, isLength));
+ break;
+ case '/':
+ if (rightOperand.isLength || rightOperand.value == 0)
+ return false;
+ stack.append(SizesCalcValue(leftOperand.value / rightOperand.value, leftOperand.isLength));
+ break;
+ default:
+ return false;
+ }
+ return true;
+}
+
+bool SizesCalcParser::calculate(unsigned& result)
+{
+ Vector<SizesCalcValue> stack;
+ for (Vector<SizesCalcValue>::iterator it = m_valueList.begin(); it != m_valueList.end(); ++it) {
+ if (it->operation == 0) {
+ stack.append(*it);
+ } else {
+ if (!operateOnStack(stack, it->operation))
+ return false;
+ }
+ }
+ if (stack.size() == 1 && stack.last().isLength) {
+ result = clampTo<unsigned>(stack.last().value);
+ return true;
+ }
+ return false;
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.h b/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.h
new file mode 100644
index 00000000000..4e040c6cee6
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParser.h
@@ -0,0 +1,59 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef SizesCalcParser_h
+#define SizesCalcParser_h
+
+#include "core/css/MediaValues.h"
+#include "core/css/parser/MediaQueryToken.h"
+#include "wtf/text/WTFString.h"
+
+namespace WebCore {
+
+struct SizesCalcValue {
+ double value;
+ bool isLength;
+ UChar operation;
+
+ SizesCalcValue()
+ : value(0)
+ , isLength(false)
+ , operation(0)
+ {
+ }
+
+ SizesCalcValue(double numericValue, bool length)
+ : value(numericValue)
+ , isLength(length)
+ , operation(0)
+ {
+ }
+};
+
+class SizesCalcParser {
+
+public:
+ static bool parse(MediaQueryTokenIterator start, MediaQueryTokenIterator end, PassRefPtr<MediaValues>, unsigned& result);
+
+private:
+ SizesCalcParser(PassRefPtr<MediaValues> mediaValues)
+ : m_mediaValues(mediaValues)
+ {
+ }
+
+ bool calcToReversePolishNotation(MediaQueryTokenIterator start, MediaQueryTokenIterator end);
+ bool calculate(unsigned& result);
+ void appendNumber(const MediaQueryToken&);
+ bool appendLength(const MediaQueryToken&);
+ bool handleOperator(Vector<MediaQueryToken>& stack, const MediaQueryToken&);
+ void appendOperator(const MediaQueryToken&);
+
+ Vector<SizesCalcValue> m_valueList;
+ RefPtr<MediaValues> m_mediaValues;
+};
+
+} // namespace WebCore
+
+#endif // SizesCalcParser_h
+
diff --git a/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParserTest.cpp b/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParserTest.cpp
new file mode 100644
index 00000000000..67a6f4d92c2
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/parser/SizesCalcParserTest.cpp
@@ -0,0 +1,136 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/parser/SizesCalcParser.h"
+
+#include "core/css/CSSPrimitiveValue.h"
+#include "core/css/MediaValuesCached.h"
+#include "core/css/StylePropertySet.h"
+#include "core/css/parser/MediaQueryTokenizer.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+struct TestCase {
+ const char* input;
+ const unsigned output;
+ const bool valid;
+ const bool dontRunInCSSCalc;
+};
+
+static void initLengthArray(CSSLengthArray& lengthArray)
+{
+ lengthArray.resize(CSSPrimitiveValue::LengthUnitTypeCount);
+ for (size_t i = 0; i < CSSPrimitiveValue::LengthUnitTypeCount; ++i)
+ lengthArray.at(i) = 0;
+}
+
+static void verifyCSSCalc(String text, double value, bool valid, unsigned fontSize, unsigned viewportWidth, unsigned viewportHeight)
+{
+ CSSLengthArray lengthArray;
+ initLengthArray(lengthArray);
+ RefPtr<MutableStylePropertySet> propertySet = MutableStylePropertySet::create();
+ propertySet->setProperty(CSSPropertyLeft, text);
+ RefPtrWillBeRawPtr<CSSValue> cssValue = propertySet->getPropertyCSSValue(CSSPropertyLeft);
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(cssValue.get());
+ if (primitiveValue)
+ primitiveValue->accumulateLengthArray(lengthArray);
+ else
+ ASSERT_EQ(valid, false);
+ int length = lengthArray.at(CSSPrimitiveValue::UnitTypePixels);
+ length += lengthArray.at(CSSPrimitiveValue::UnitTypeFontSize) * fontSize;
+ length += lengthArray.at(CSSPrimitiveValue::UnitTypeViewportWidth) * viewportWidth / 100.0;
+ length += lengthArray.at(CSSPrimitiveValue::UnitTypeViewportHeight) * viewportHeight / 100.0;
+ ASSERT_EQ(value, length);
+}
+
+
+TEST(SizesCalcParserTest, Basic)
+{
+ TestCase testCases[] = {
+ {"calc(500px + 10em)", 660, true, false},
+ {"calc(500px + 2 * 10em)", 820, true, false},
+ {"calc(500px + 2*10em)", 820, true, false},
+ {"calc(500px + 0.5*10em)", 580, true, false},
+ {"calc(500px + (0.5*10em + 13px))", 593, true, false},
+ {"calc(100vw + (0.5*10em + 13px))", 593, true, false},
+ {"calc(100vh + (0.5*10em + 13px))", 736, true, false},
+ {"calc(100vh + calc(0.5*10em + 13px))", 736, true, true}, // CSSCalculationValue does not parse internal "calc(".
+ {"calc(100vh + (50%*10em + 13px))", 0, false, false},
+ {"calc(50em+13px)", 0, false, false},
+ {"calc(50em-13px)", 0, false, false},
+ {"calc(500px + 10)", 0, false, false},
+ {"calc(500 + 10)", 0, false, false},
+ {"calc(500px + 10s)", 0, false, true}, // This test ASSERTs in CSSCalculationValue.
+ {"calc(500px + 1cm)", 537, true, false},
+ {"calc(500px - 10s)", 0, false, true}, // This test ASSERTs in CSSCalculationValue.
+ {"calc(500px - 1cm)", 462, true, false},
+ {"calc(50px*10)", 500, true, false},
+ {"calc(50px*10px)", 0, false, false},
+ {"calc(50px/10px)", 0, false, false},
+ {"calc(500px/10)", 50, true, false},
+ {"calc(500/10)", 0, false, false},
+ {"calc(500px/0.5)", 1000, true, false},
+ {"calc(500px/.5)", 1000, true, false},
+ {"calc(500/0)", 0, false, false},
+ {"calc(500px/0)", 0, false, false},
+ {"calc(-500px/10)", 0, true, true}, // CSSCalculationValue does not clamp negative values to 0.
+ {"calc(((4) * ((10px))))", 40, true, false},
+ {"calc(50px / 0)", 0, false, false},
+ {"calc(50px / (10 + 10))", 2, true, false},
+ {"calc(50px / (10 - 10))", 0, false, false},
+ {"calc(50px / (10 * 10))", 0, true, false},
+ {"calc(50px / (10 / 10))", 50, true, false},
+ {"calc(200px*)", 0, false, false},
+ {"calc(+ +200px)", 0, false, false},
+ {"calc()", 0, false, false},
+ {"calc(100px + + +100px)", 0, false, false},
+ {"calc(200px 200px)", 0, false, false},
+ {"calc(100px * * 2)", 0, false, false},
+ {"calc(100px @ 2)", 0, false, false},
+ {"calc(1 flim 2)", 0, false, false},
+ {"calc(100px @ 2)", 0, false, false},
+ {"calc(1 flim 2)", 0, false, false},
+ {"calc(1 flim (2))", 0, false, false},
+ {0, 0, true, false} // Do not remove the terminator line.
+ };
+
+
+ MediaValuesCached::MediaValuesCachedData data;
+ data.viewportWidth = 500;
+ data.viewportHeight = 643;
+ data.deviceWidth = 500;
+ data.deviceHeight = 643;
+ data.devicePixelRatio = 2.0;
+ data.colorBitsPerComponent = 24;
+ data.monochromeBitsPerComponent = 0;
+ data.pointer = MediaValues::MousePointer;
+ data.defaultFontSize = 16;
+ data.threeDEnabled = true;
+ data.scanMediaType = false;
+ data.screenMediaType = true;
+ data.printMediaType = false;
+ data.strictMode = true;
+ RefPtr<MediaValues> mediaValues = MediaValuesCached::create(data);
+
+ for (unsigned i = 0; testCases[i].input; ++i) {
+ Vector<MediaQueryToken> tokens;
+ MediaQueryTokenizer::tokenize(testCases[i].input, tokens);
+ unsigned output;
+ bool valid = SizesCalcParser::parse(tokens.begin(), tokens.end(), mediaValues, output);
+ ASSERT_EQ(testCases[i].valid, valid);
+ if (valid)
+ ASSERT_EQ(testCases[i].output, output);
+ }
+
+ for (unsigned i = 0; testCases[i].input; ++i) {
+ if (testCases[i].dontRunInCSSCalc)
+ continue;
+ verifyCSSCalc(testCases[i].input, testCases[i].output, testCases[i].valid, data.defaultFontSize, data.viewportWidth, data.viewportHeight);
+ }
+}
+
+} // namespace
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.cpp
index dbfd63b8bb6..89d6cc3d0bd 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.cpp
@@ -40,6 +40,7 @@
#include "core/animation/AnimatableLengthBox.h"
#include "core/animation/AnimatableLengthBoxAndBool.h"
#include "core/animation/AnimatableLengthPoint.h"
+#include "core/animation/AnimatableLengthPoint3D.h"
#include "core/animation/AnimatableLengthSize.h"
#include "core/animation/AnimatableRepeatable.h"
#include "core/animation/AnimatableSVGLength.h"
@@ -63,11 +64,11 @@ namespace WebCore {
namespace {
-Length animatableValueToLength(const AnimatableValue* value, const StyleResolverState& state, NumberRange range = AllValues)
+Length animatableValueToLength(const AnimatableValue* value, const StyleResolverState& state, ValueRange range = ValueRangeAll)
{
if (value->isLength())
- return toAnimatableLength(value)->toLength(state.cssToLengthConversionData(), range);
- RefPtr<CSSValue> cssValue = toAnimatableUnknown(value)->toCSSValue();
+ return toAnimatableLength(value)->length(state.style()->effectiveZoom(), range);
+ RefPtrWillBeRawPtr<CSSValue> cssValue = toAnimatableUnknown(value)->toCSSValue();
CSSPrimitiveValue* cssPrimitiveValue = toCSSPrimitiveValue(cssValue.get());
return cssPrimitiveValue->convertToLength<AnyConversion>(state.cssToLengthConversionData());
}
@@ -75,10 +76,10 @@ Length animatableValueToLength(const AnimatableValue* value, const StyleResolver
BorderImageLength animatableValueToBorderImageLength(const AnimatableValue* value, const StyleResolverState& state)
{
if (value->isLength())
- return BorderImageLength(toAnimatableLength(value)->toLength(state.cssToLengthConversionData(), NonNegativeValues));
+ return BorderImageLength(toAnimatableLength(value)->length(state.style()->effectiveZoom(), ValueRangeNonNegative));
if (value->isDouble())
return BorderImageLength(clampTo<double>(toAnimatableDouble(value)->toDouble(), 0));
- RefPtr<CSSValue> cssValue = toAnimatableUnknown(value)->toCSSValue();
+ RefPtrWillBeRawPtr<CSSValue> cssValue = toAnimatableUnknown(value)->toCSSValue();
CSSPrimitiveValue* cssPrimitiveValue = toCSSPrimitiveValue(cssValue.get());
return BorderImageLength(cssPrimitiveValue->convertToLength<AnyConversion>(state.cssToLengthConversionData()));
}
@@ -89,7 +90,7 @@ template<typename T> T animatableValueRoundClampTo(const AnimatableValue* value,
return clampTo<T>(round(toAnimatableDouble(value)->toDouble()), min, max);
}
-LengthBox animatableValueToLengthBox(const AnimatableValue* value, const StyleResolverState& state, NumberRange range = AllValues)
+LengthBox animatableValueToLengthBox(const AnimatableValue* value, const StyleResolverState& state, ValueRange range = ValueRangeAll)
{
const AnimatableLengthBox* animatableLengthBox = toAnimatableLengthBox(value);
return LengthBox(
@@ -109,7 +110,7 @@ BorderImageLengthBox animatableValueToBorderImageLengthBox(const AnimatableValue
animatableValueToBorderImageLength(animatableLengthBox->left(), state));
}
-LengthPoint animatableValueToLengthPoint(const AnimatableValue* value, const StyleResolverState& state, NumberRange range = AllValues)
+LengthPoint animatableValueToLengthPoint(const AnimatableValue* value, const StyleResolverState& state, ValueRange range = ValueRangeAll)
{
const AnimatableLengthPoint* animatableLengthPoint = toAnimatableLengthPoint(value);
return LengthPoint(
@@ -117,7 +118,7 @@ LengthPoint animatableValueToLengthPoint(const AnimatableValue* value, const Sty
animatableValueToLength(animatableLengthPoint->y(), state, range));
}
-LengthSize animatableValueToLengthSize(const AnimatableValue* value, const StyleResolverState& state, NumberRange range)
+LengthSize animatableValueToLengthSize(const AnimatableValue* value, const StyleResolverState& state, ValueRange range)
{
const AnimatableLengthSize* animatableLengthSize = toAnimatableLengthSize(value);
return LengthSize(
@@ -129,23 +130,23 @@ template <CSSPropertyID property>
void setFillSize(FillLayer* fillLayer, const AnimatableValue* value, const StyleResolverState& state)
{
if (value->isLengthSize())
- fillLayer->setSize(FillSize(SizeLength, animatableValueToLengthSize(value, state, NonNegativeValues)));
+ fillLayer->setSize(FillSize(SizeLength, animatableValueToLengthSize(value, state, ValueRangeNonNegative)));
else
state.styleMap().mapFillSize(property, fillLayer, toAnimatableUnknown(value)->toCSSValue().get());
}
-SVGLength animatableValueToNonNegativeSVGLength(const AnimatableValue* value)
+PassRefPtr<SVGLength> animatableValueToNonNegativeSVGLength(const AnimatableValue* value)
{
- SVGLength length = toAnimatableSVGLength(value)->toSVGLength();
- if (length.valueInSpecifiedUnits() < 0)
- length.setValueInSpecifiedUnits(0);
- return length;
+ RefPtr<SVGLength> length = toAnimatableSVGLength(value)->toSVGLength();
+ if (length->valueInSpecifiedUnits() < 0)
+ length->setValueInSpecifiedUnits(0);
+ return length.release();
}
template <CSSPropertyID property>
void setOnFillLayers(FillLayer* fillLayer, const AnimatableValue* value, StyleResolverState& state)
{
- const Vector<RefPtr<AnimatableValue> >& values = toAnimatableRepeatable(value)->values();
+ const WillBeHeapVector<RefPtrWillBeMember<AnimatableValue> >& values = toAnimatableRepeatable(value)->values();
ASSERT(!values.isEmpty());
FillLayer* prev = 0;
for (size_t i = 0; i < values.size(); ++i) {
@@ -174,10 +175,10 @@ void setOnFillLayers(FillLayer* fillLayer, const AnimatableValue* value, StyleRe
case CSSPropertyBackgroundImage:
case CSSPropertyWebkitMaskImage:
if (layerValue->isImage()) {
- fillLayer->setImage(toAnimatableImage(layerValue)->toStyleImage());
+ fillLayer->setImage(state.styleImage(property, toAnimatableImage(layerValue)->toCSSValue()));
} else {
ASSERT(toAnimatableUnknown(layerValue)->toCSSValueID() == CSSValueNone);
- fillLayer->setImage(0);
+ fillLayer->setImage(nullptr);
}
break;
case CSSPropertyBackgroundPositionX:
@@ -225,11 +226,33 @@ void setOnFillLayers(FillLayer* fillLayer, const AnimatableValue* value, StyleRe
}
}
+FontWeight animatableValueToFontWeight(const AnimatableValue* value)
+{
+ int index = round(toAnimatableDouble(value)->toDouble() / 100) - 1;
+
+ static const FontWeight weights[] = {
+ FontWeight100,
+ FontWeight200,
+ FontWeight300,
+ FontWeight400,
+ FontWeight500,
+ FontWeight600,
+ FontWeight700,
+ FontWeight800,
+ FontWeight900
+ };
+
+ index = clampTo<int>(index, 0, WTF_ARRAY_LENGTH(weights) - 1);
+
+ return weights[index];
+}
+
} // namespace
// FIXME: Generate this function.
void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverState& state, const AnimatableValue* value)
{
+ ASSERT(CSSAnimations::isAnimatableProperty(property));
if (value->isUnknown()) {
StyleBuilder::applyProperty(property, state, toAnimatableUnknown(value)->toCSSValue().get());
return;
@@ -260,10 +283,10 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setVisitedLinkBorderBottomColor(toAnimatableColor(value)->visitedLinkColor());
return;
case CSSPropertyBorderBottomLeftRadius:
- style->setBorderBottomLeftRadius(animatableValueToLengthSize(value, state, NonNegativeValues));
+ style->setBorderBottomLeftRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
return;
case CSSPropertyBorderBottomRightRadius:
- style->setBorderBottomRightRadius(animatableValueToLengthSize(value, state, NonNegativeValues));
+ style->setBorderBottomRightRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
return;
case CSSPropertyBorderBottomWidth:
style->setBorderBottomWidth(animatableValueRoundClampTo<unsigned>(value));
@@ -272,10 +295,10 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setBorderImageOutset(animatableValueToBorderImageLengthBox(value, state));
return;
case CSSPropertyBorderImageSlice:
- style->setBorderImageSlices(animatableValueToLengthBox(value, state, NonNegativeValues));
+ style->setBorderImageSlices(animatableValueToLengthBox(value, state, ValueRangeNonNegative));
return;
case CSSPropertyBorderImageSource:
- style->setBorderImageSource(toAnimatableImage(value)->toStyleImage());
+ style->setBorderImageSource(state.styleImage(property, toAnimatableImage(value)->toCSSValue()));
return;
case CSSPropertyBorderImageWidth:
style->setBorderImageWidth(animatableValueToBorderImageLengthBox(value, state));
@@ -299,10 +322,10 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setVisitedLinkBorderTopColor(toAnimatableColor(value)->visitedLinkColor());
return;
case CSSPropertyBorderTopLeftRadius:
- style->setBorderTopLeftRadius(animatableValueToLengthSize(value, state, NonNegativeValues));
+ style->setBorderTopLeftRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
return;
case CSSPropertyBorderTopRightRadius:
- style->setBorderTopRightRadius(animatableValueToLengthSize(value, state, NonNegativeValues));
+ style->setBorderTopRightRadius(animatableValueToLengthSize(value, state, ValueRangeNonNegative));
return;
case CSSPropertyBorderTopWidth:
style->setBorderTopWidth(animatableValueRoundClampTo<unsigned>(value));
@@ -323,13 +346,13 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setVisitedLinkColor(toAnimatableColor(value)->visitedLinkColor());
return;
case CSSPropertyFillOpacity:
- // Avoiding a value of 1 forces a layer to be created.
- style->setFillOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, nextafterf(1, 0)));
+ style->setFillOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
return;
case CSSPropertyFill:
{
const AnimatableSVGPaint* svgPaint = toAnimatableSVGPaint(value);
- style->accessSVGStyle()->setFillPaint(svgPaint->paintType(), svgPaint->color(), svgPaint->uri());
+ style->accessSVGStyle()->setFillPaint(svgPaint->paintType(), svgPaint->color(), svgPaint->uri(), true, false);
+ style->accessSVGStyle()->setFillPaint(svgPaint->visitedLinkPaintType(), svgPaint->visitedLinkColor(), svgPaint->visitedLinkURI(), false, true);
}
return;
case CSSPropertyFlexGrow:
@@ -339,7 +362,7 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setFlexShrink(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0));
return;
case CSSPropertyFlexBasis:
- style->setFlexBasis(animatableValueToLength(value, state, NonNegativeValues));
+ style->setFlexBasis(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyFloodColor:
style->setFloodColor(toAnimatableColor(value)->color());
@@ -350,11 +373,11 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
case CSSPropertyFontSize:
style->setFontSize(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0));
return;
- case CSSPropertyHeight:
- style->setHeight(animatableValueToLength(value, state, NonNegativeValues));
+ case CSSPropertyFontWeight:
+ style->setFontWeight(animatableValueToFontWeight(value));
return;
- case CSSPropertyKerning:
- style->setKerning(toAnimatableSVGLength(value)->toSVGLength());
+ case CSSPropertyHeight:
+ style->setHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyLeft:
style->setLeft(animatableValueToLength(value, state));
@@ -364,12 +387,12 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
return;
case CSSPropertyLineHeight:
if (value->isLength())
- style->setLineHeight(animatableValueToLength(value, state, NonNegativeValues));
+ style->setLineHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
else
style->setLineHeight(Length(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0), Percent));
return;
case CSSPropertyListStyleImage:
- style->setListStyleImage(toAnimatableImage(value)->toStyleImage());
+ style->setListStyleImage(state.styleImage(property, toAnimatableImage(value)->toCSSValue()));
return;
case CSSPropertyLetterSpacing:
style->setLetterSpacing(clampTo<float>(toAnimatableDouble(value)->toDouble()));
@@ -387,16 +410,16 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setMarginTop(animatableValueToLength(value, state));
return;
case CSSPropertyMaxHeight:
- style->setMaxHeight(animatableValueToLength(value, state, NonNegativeValues));
+ style->setMaxHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyMaxWidth:
- style->setMaxWidth(animatableValueToLength(value, state, NonNegativeValues));
+ style->setMaxWidth(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyMinHeight:
- style->setMinHeight(animatableValueToLength(value, state, NonNegativeValues));
+ style->setMinHeight(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyMinWidth:
- style->setMinWidth(animatableValueToLength(value, state, NonNegativeValues));
+ style->setMinWidth(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyObjectPosition:
style->setObjectPosition(animatableValueToLengthPoint(value, state));
@@ -419,16 +442,16 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setOutlineWidth(animatableValueRoundClampTo<unsigned short>(value));
return;
case CSSPropertyPaddingBottom:
- style->setPaddingBottom(animatableValueToLength(value, state, NonNegativeValues));
+ style->setPaddingBottom(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyPaddingLeft:
- style->setPaddingLeft(animatableValueToLength(value, state, NonNegativeValues));
+ style->setPaddingLeft(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyPaddingRight:
- style->setPaddingRight(animatableValueToLength(value, state, NonNegativeValues));
+ style->setPaddingRight(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyPaddingTop:
- style->setPaddingTop(animatableValueToLength(value, state, NonNegativeValues));
+ style->setPaddingTop(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyRight:
style->setRight(animatableValueToLength(value, state));
@@ -443,7 +466,7 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setStopOpacity(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
return;
case CSSPropertyStrokeDasharray:
- style->setStrokeDashArray(toAnimatableStrokeDasharrayList(value)->toSVGLengthVector());
+ style->setStrokeDashArray(toAnimatableStrokeDasharrayList(value)->toSVGLengthList());
return;
case CSSPropertyStrokeDashoffset:
style->setStrokeDashOffset(toAnimatableSVGLength(value)->toSVGLength());
@@ -457,7 +480,8 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
case CSSPropertyStroke:
{
const AnimatableSVGPaint* svgPaint = toAnimatableSVGPaint(value);
- style->accessSVGStyle()->setStrokePaint(svgPaint->paintType(), svgPaint->color(), svgPaint->uri());
+ style->accessSVGStyle()->setStrokePaint(svgPaint->paintType(), svgPaint->color(), svgPaint->uri(), true, false);
+ style->accessSVGStyle()->setStrokePaint(svgPaint->visitedLinkPaintType(), svgPaint->visitedLinkColor(), svgPaint->visitedLinkURI(), false, true);
}
return;
case CSSPropertyTextDecorationColor:
@@ -508,11 +532,11 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setMaskBoxImageOutset(animatableValueToBorderImageLengthBox(value, state));
return;
case CSSPropertyWebkitMaskBoxImageSlice:
- style->setMaskBoxImageSlices(animatableValueToLengthBox(toAnimatableLengthBoxAndBool(value)->box(), state, NonNegativeValues));
+ style->setMaskBoxImageSlices(animatableValueToLengthBox(toAnimatableLengthBoxAndBool(value)->box(), state, ValueRangeNonNegative));
style->setMaskBoxImageSlicesFill(toAnimatableLengthBoxAndBool(value)->flag());
return;
case CSSPropertyWebkitMaskBoxImageSource:
- style->setMaskBoxImageSource(toAnimatableImage(value)->toStyleImage());
+ style->setMaskBoxImageSource(state.styleImage(property, toAnimatableImage(value)->toCSSValue()));
return;
case CSSPropertyWebkitMaskBoxImageWidth:
style->setMaskBoxImageWidth(animatableValueToBorderImageLengthBox(value, state));
@@ -529,23 +553,29 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
case CSSPropertyWebkitMaskSize:
setOnFillLayers<CSSPropertyWebkitMaskSize>(style->accessMaskLayers(), value, state);
return;
- case CSSPropertyWebkitPerspective:
+ case CSSPropertyPerspective:
style->setPerspective(clampTo<float>(toAnimatableDouble(value)->toDouble()));
return;
+ case CSSPropertyPerspectiveOrigin: {
+ ASSERT(RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
+ const AnimatableLengthPoint* animatableLengthPoint = toAnimatableLengthPoint(value);
+ style->setPerspectiveOriginX(animatableValueToLength(animatableLengthPoint->x(), state));
+ style->setPerspectiveOriginY(animatableValueToLength(animatableLengthPoint->y(), state));
+ return;
+ }
case CSSPropertyWebkitPerspectiveOriginX:
+ ASSERT(!RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
style->setPerspectiveOriginX(animatableValueToLength(value, state));
return;
case CSSPropertyWebkitPerspectiveOriginY:
+ ASSERT(!RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
style->setPerspectiveOriginY(animatableValueToLength(value, state));
return;
- case CSSPropertyShapeInside:
- style->setShapeInside(toAnimatableShapeValue(value)->shapeValue());
- return;
case CSSPropertyShapeOutside:
style->setShapeOutside(toAnimatableShapeValue(value)->shapeValue());
return;
case CSSPropertyShapeMargin:
- style->setShapeMargin(animatableValueToLength(value, state, NonNegativeValues));
+ style->setShapeMargin(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyShapeImageThreshold:
style->setShapeImageThreshold(clampTo<float>(toAnimatableDouble(value)->toDouble(), 0, 1));
@@ -554,31 +584,44 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setTextStrokeColor(toAnimatableColor(value)->color());
style->setVisitedLinkTextStrokeColor(toAnimatableColor(value)->visitedLinkColor());
return;
- case CSSPropertyWebkitTransform: {
+ case CSSPropertyTransform: {
const TransformOperations& operations = toAnimatableTransform(value)->transformOperations();
- // FIXME: Using identity matrix here when the transform list is empty
- // forces a layer to be created in the presence of a transform animation.
+ // FIXME: This normalization (handling of 'none') should be performed at input in AnimatableValueFactory.
style->setTransform(operations.size() ? operations : TransformOperations(true));
return;
}
+ case CSSPropertyTransformOrigin: {
+ ASSERT(RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
+ const AnimatableLengthPoint3D* animatableLengthPoint3D = toAnimatableLengthPoint3D(value);
+ style->setTransformOriginX(animatableValueToLength(animatableLengthPoint3D->x(), state));
+ style->setTransformOriginY(animatableValueToLength(animatableLengthPoint3D->y(), state));
+ style->setTransformOriginZ(clampTo<float>(toAnimatableDouble(animatableLengthPoint3D->z())->toDouble()));
+ return;
+ }
case CSSPropertyWebkitTransformOriginX:
+ ASSERT(!RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
style->setTransformOriginX(animatableValueToLength(value, state));
return;
case CSSPropertyWebkitTransformOriginY:
+ ASSERT(!RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
style->setTransformOriginY(animatableValueToLength(value, state));
return;
case CSSPropertyWebkitTransformOriginZ:
+ ASSERT(!RuntimeEnabledFeatures::cssTransformsUnprefixedEnabled());
style->setTransformOriginZ(toAnimatableDouble(value)->toDouble());
return;
case CSSPropertyWidows:
style->setWidows(animatableValueRoundClampTo<unsigned short>(value, 1));
return;
case CSSPropertyWidth:
- style->setWidth(animatableValueToLength(value, state, NonNegativeValues));
+ style->setWidth(animatableValueToLength(value, state, ValueRangeNonNegative));
return;
case CSSPropertyWordSpacing:
style->setWordSpacing(clampTo<float>(toAnimatableDouble(value)->toDouble()));
return;
+ case CSSPropertyVerticalAlign:
+ style->setVerticalAlignLength(animatableValueToLength(value, state));
+ return;
case CSSPropertyVisibility:
style->setVisibility(toAnimatableVisibility(value)->visibility());
return;
@@ -589,7 +632,6 @@ void AnimatedStyleBuilder::applyProperty(CSSPropertyID property, StyleResolverSt
style->setZoom(clampTo<float>(toAnimatableDouble(value)->toDouble(), std::numeric_limits<float>::denorm_min()));
return;
default:
- ASSERT_WITH_MESSAGE(!CSSAnimations::isAnimatableProperty(property), "Web Animations not yet implemented: Unable to apply AnimatableValue to RenderStyle: %s", getPropertyNameString(property).utf8().data());
ASSERT_NOT_REACHED();
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.h b/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.h
index 3f91a145a4c..1139c524326 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/AnimatedStyleBuilder.h
@@ -31,7 +31,7 @@
#ifndef AnimatedStyleBuilder_h
#define AnimatedStyleBuilder_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.cpp
index 9eeec75b2c7..465a89e1bbf 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.cpp
@@ -28,7 +28,8 @@
#include "config.h"
#include "core/css/resolver/CSSToStyleMap.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
+#include "core/animation/css/CSSAnimationData.h"
#include "core/css/CSSBorderImageSliceValue.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSPrimitiveValueMappings.h"
@@ -36,7 +37,6 @@
#include "core/css/Pair.h"
#include "core/css/Rect.h"
#include "core/css/resolver/StyleResolverState.h"
-#include "core/platform/animation/CSSAnimationData.h"
#include "core/rendering/style/BorderImageLengthBox.h"
#include "core/rendering/style/FillLayer.h"
@@ -47,14 +47,9 @@ const CSSToLengthConversionData& CSSToStyleMap::cssToLengthConversionData() cons
return m_state.cssToLengthConversionData();
}
-bool CSSToStyleMap::useSVGZoomRules() const
-{
- return m_state.useSVGZoomRules();
-}
-
PassRefPtr<StyleImage> CSSToStyleMap::styleImage(CSSPropertyID propertyId, CSSValue* value)
{
- return m_elementStyleResources.styleImage(m_state.document().textLinkColors(), m_state.style()->color(), propertyId, value);
+ return m_elementStyleResources.styleImage(m_state.document(), m_state.document().textLinkColors(), m_state.style()->color(), propertyId, value);
}
void CSSToStyleMap::mapFillAttachment(CSSPropertyID, FillLayer* layer, CSSValue* value) const
@@ -215,9 +210,6 @@ void CSSToStyleMap::mapFillSize(CSSPropertyID, FillLayer* layer, CSSValue* value
secondLength = Length();
}
- if (firstLength.isUndefined() || secondLength.isUndefined())
- return;
-
b.setWidth(firstLength);
b.setHeight(secondLength);
layer->setSizeLength(b);
@@ -241,7 +233,6 @@ void CSSToStyleMap::mapFillXPosition(CSSPropertyID propertyID, FillLayer* layer,
}
Length length = primitiveValue->convertToLength<FixedConversion | PercentConversion>(cssToLengthConversionData());
- ASSERT(!length.isUndefined());
layer->setXPosition(length);
if (pair)
@@ -266,7 +257,6 @@ void CSSToStyleMap::mapFillYPosition(CSSPropertyID propertyID, FillLayer* layer,
}
Length length = primitiveValue->convertToLength<FixedConversion | PercentConversion>(cssToLengthConversionData());
- ASSERT(!length.isUndefined());
layer->setYPosition(length);
if (pair)
@@ -300,207 +290,150 @@ void CSSToStyleMap::mapFillMaskSourceType(CSSPropertyID, FillLayer* layer, CSSVa
layer->setMaskSourceType(type);
}
-void CSSToStyleMap::mapAnimationDelay(CSSAnimationData* animation, CSSValue* value) const
+double CSSToStyleMap::mapAnimationDelay(CSSValue* value)
{
- if (value->isInitialValue()) {
- animation->setDelay(CSSAnimationData::initialAnimationDelay());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
-
- animation->setDelay(toCSSPrimitiveValue(value)->computeTime<double, CSSPrimitiveValue::Seconds>());
+ if (value->isInitialValue())
+ return CSSTimingData::initialDelay();
+ return toCSSPrimitiveValue(value)->computeTime<double, CSSPrimitiveValue::Seconds>();
}
-void CSSToStyleMap::mapAnimationDirection(CSSAnimationData* layer, CSSValue* value) const
+Timing::PlaybackDirection CSSToStyleMap::mapAnimationDirection(CSSValue* value)
{
- if (value->isInitialValue()) {
- layer->setDirection(CSSAnimationData::initialAnimationDirection());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
+ if (value->isInitialValue())
+ return CSSAnimationData::initialDirection();
switch (toCSSPrimitiveValue(value)->getValueID()) {
case CSSValueNormal:
- layer->setDirection(CSSAnimationData::AnimationDirectionNormal);
- break;
+ return Timing::PlaybackDirectionNormal;
case CSSValueAlternate:
- layer->setDirection(CSSAnimationData::AnimationDirectionAlternate);
- break;
+ return Timing::PlaybackDirectionAlternate;
case CSSValueReverse:
- layer->setDirection(CSSAnimationData::AnimationDirectionReverse);
- break;
+ return Timing::PlaybackDirectionReverse;
case CSSValueAlternateReverse:
- layer->setDirection(CSSAnimationData::AnimationDirectionAlternateReverse);
- break;
+ return Timing::PlaybackDirectionAlternateReverse;
default:
- break;
+ ASSERT_NOT_REACHED();
+ return CSSAnimationData::initialDirection();
}
}
-void CSSToStyleMap::mapAnimationDuration(CSSAnimationData* animation, CSSValue* value) const
+double CSSToStyleMap::mapAnimationDuration(CSSValue* value)
{
- if (value->isInitialValue()) {
- animation->setDuration(CSSAnimationData::initialAnimationDuration());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
-
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- animation->setDuration(primitiveValue->computeTime<double, CSSPrimitiveValue::Seconds>());
+ if (value->isInitialValue())
+ return CSSTimingData::initialDuration();
+ return toCSSPrimitiveValue(value)->computeTime<double, CSSPrimitiveValue::Seconds>();
}
-void CSSToStyleMap::mapAnimationFillMode(CSSAnimationData* layer, CSSValue* value) const
+Timing::FillMode CSSToStyleMap::mapAnimationFillMode(CSSValue* value)
{
- if (value->isInitialValue()) {
- layer->setFillMode(CSSAnimationData::initialAnimationFillMode());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
+ if (value->isInitialValue())
+ return CSSAnimationData::initialFillMode();
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- switch (primitiveValue->getValueID()) {
+ switch (toCSSPrimitiveValue(value)->getValueID()) {
case CSSValueNone:
- layer->setFillMode(AnimationFillModeNone);
- break;
+ return Timing::FillModeNone;
case CSSValueForwards:
- layer->setFillMode(AnimationFillModeForwards);
- break;
+ return Timing::FillModeForwards;
case CSSValueBackwards:
- layer->setFillMode(AnimationFillModeBackwards);
- break;
+ return Timing::FillModeBackwards;
case CSSValueBoth:
- layer->setFillMode(AnimationFillModeBoth);
- break;
+ return Timing::FillModeBoth;
default:
- break;
+ ASSERT_NOT_REACHED();
+ return CSSAnimationData::initialFillMode();
}
}
-void CSSToStyleMap::mapAnimationIterationCount(CSSAnimationData* animation, CSSValue* value) const
+double CSSToStyleMap::mapAnimationIterationCount(CSSValue* value)
{
- if (value->isInitialValue()) {
- animation->setIterationCount(CSSAnimationData::initialAnimationIterationCount());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
-
+ if (value->isInitialValue())
+ return CSSAnimationData::initialIterationCount();
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->getValueID() == CSSValueInfinite)
- animation->setIterationCount(CSSAnimationData::IterationCountInfinite);
- else
- animation->setIterationCount(primitiveValue->getFloatValue());
+ return std::numeric_limits<double>::infinity();
+ return primitiveValue->getFloatValue();
}
-void CSSToStyleMap::mapAnimationName(CSSAnimationData* layer, CSSValue* value) const
+AtomicString CSSToStyleMap::mapAnimationName(CSSValue* value)
{
- if (value->isInitialValue()) {
- layer->setName(CSSAnimationData::initialAnimationName());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
-
+ if (value->isInitialValue())
+ return CSSAnimationData::initialName();
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->getValueID() == CSSValueNone)
- layer->setIsNoneAnimation(true);
- else
- layer->setName(AtomicString(primitiveValue->getStringValue()));
+ return CSSAnimationData::initialName();
+ return AtomicString(primitiveValue->getStringValue());
}
-void CSSToStyleMap::mapAnimationPlayState(CSSAnimationData* layer, CSSValue* value) const
+EAnimPlayState CSSToStyleMap::mapAnimationPlayState(CSSValue* value)
{
- if (value->isInitialValue()) {
- layer->setPlayState(CSSAnimationData::initialAnimationPlayState());
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
-
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- EAnimPlayState playState = (primitiveValue->getValueID() == CSSValuePaused) ? AnimPlayStatePaused : AnimPlayStatePlaying;
- layer->setPlayState(playState);
+ if (value->isInitialValue())
+ return CSSAnimationData::initialPlayState();
+ if (toCSSPrimitiveValue(value)->getValueID() == CSSValuePaused)
+ return AnimPlayStatePaused;
+ ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueRunning);
+ return AnimPlayStatePlaying;
}
-void CSSToStyleMap::mapAnimationProperty(CSSAnimationData* animation, CSSValue* value) const
+CSSTransitionData::TransitionProperty CSSToStyleMap::mapAnimationProperty(CSSValue* value)
{
- if (value->isInitialValue()) {
- animation->setAnimationMode(CSSAnimationData::AnimateAll);
- animation->setProperty(CSSPropertyInvalid);
- return;
- }
-
- if (!value->isPrimitiveValue())
- return;
-
+ if (value->isInitialValue())
+ return CSSTransitionData::initialProperty();
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (primitiveValue->getValueID() == CSSValueAll) {
- animation->setAnimationMode(CSSAnimationData::AnimateAll);
- animation->setProperty(CSSPropertyInvalid);
- } else if (primitiveValue->getValueID() == CSSValueNone) {
- animation->setAnimationMode(CSSAnimationData::AnimateNone);
- animation->setProperty(CSSPropertyInvalid);
- } else {
- animation->setAnimationMode(CSSAnimationData::AnimateSingleProperty);
- animation->setProperty(primitiveValue->getPropertyID());
- }
+ if (primitiveValue->isString())
+ return CSSTransitionData::TransitionProperty(primitiveValue->getStringValue());
+ if (primitiveValue->getValueID() == CSSValueAll)
+ return CSSTransitionData::TransitionProperty(CSSTransitionData::TransitionAll);
+ if (primitiveValue->getValueID() == CSSValueNone)
+ return CSSTransitionData::TransitionProperty(CSSTransitionData::TransitionNone);
+ return CSSTransitionData::TransitionProperty(primitiveValue->getPropertyID());
}
-void CSSToStyleMap::mapAnimationTimingFunction(CSSAnimationData* animation, CSSValue* value) const
+PassRefPtr<TimingFunction> CSSToStyleMap::mapAnimationTimingFunction(CSSValue* value, bool allowStepMiddle)
{
- if (value->isInitialValue()) {
- animation->setTimingFunction(CSSAnimationData::initialAnimationTimingFunction());
- return;
- }
+ // FIXME: We should probably only call into this function with a valid
+ // single timing function value which isn't initial or inherit. We can
+ // currently get into here with initial since the parser expands unset
+ // properties in shorthands to initial.
if (value->isPrimitiveValue()) {
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
switch (primitiveValue->getValueID()) {
case CSSValueLinear:
- animation->setTimingFunction(LinearTimingFunction::create());
- break;
+ return LinearTimingFunction::shared();
case CSSValueEase:
- animation->setTimingFunction(CubicBezierTimingFunction::preset(CubicBezierTimingFunction::Ease));
- break;
+ return CubicBezierTimingFunction::preset(CubicBezierTimingFunction::Ease);
case CSSValueEaseIn:
- animation->setTimingFunction(CubicBezierTimingFunction::preset(CubicBezierTimingFunction::EaseIn));
- break;
+ return CubicBezierTimingFunction::preset(CubicBezierTimingFunction::EaseIn);
case CSSValueEaseOut:
- animation->setTimingFunction(CubicBezierTimingFunction::preset(CubicBezierTimingFunction::EaseOut));
- break;
+ return CubicBezierTimingFunction::preset(CubicBezierTimingFunction::EaseOut);
case CSSValueEaseInOut:
- animation->setTimingFunction(CubicBezierTimingFunction::preset(CubicBezierTimingFunction::EaseInOut));
- break;
+ return CubicBezierTimingFunction::preset(CubicBezierTimingFunction::EaseInOut);
case CSSValueStepStart:
- animation->setTimingFunction(StepsTimingFunction::preset(StepsTimingFunction::Start));
- break;
+ return StepsTimingFunction::preset(StepsTimingFunction::Start);
+ case CSSValueStepMiddle:
+ if (allowStepMiddle)
+ return StepsTimingFunction::preset(StepsTimingFunction::Middle);
+ return CSSTimingData::initialTimingFunction();
case CSSValueStepEnd:
- animation->setTimingFunction(StepsTimingFunction::preset(StepsTimingFunction::End));
- break;
+ return StepsTimingFunction::preset(StepsTimingFunction::End);
default:
- break;
+ ASSERT_NOT_REACHED();
+ return CSSTimingData::initialTimingFunction();
}
- return;
}
if (value->isCubicBezierTimingFunctionValue()) {
CSSCubicBezierTimingFunctionValue* cubicTimingFunction = toCSSCubicBezierTimingFunctionValue(value);
- animation->setTimingFunction(CubicBezierTimingFunction::create(cubicTimingFunction->x1(), cubicTimingFunction->y1(), cubicTimingFunction->x2(), cubicTimingFunction->y2()));
- } else if (value->isStepsTimingFunctionValue()) {
- CSSStepsTimingFunctionValue* stepsTimingFunction = toCSSStepsTimingFunctionValue(value);
- animation->setTimingFunction(StepsTimingFunction::create(stepsTimingFunction->numberOfSteps(), stepsTimingFunction->stepAtStart()));
+ return CubicBezierTimingFunction::create(cubicTimingFunction->x1(), cubicTimingFunction->y1(), cubicTimingFunction->x2(), cubicTimingFunction->y2());
}
+
+ if (value->isInitialValue())
+ return CSSTimingData::initialTimingFunction();
+
+ CSSStepsTimingFunctionValue* stepsTimingFunction = toCSSStepsTimingFunctionValue(value);
+ if (stepsTimingFunction->stepAtPosition() == StepsTimingFunction::StepAtMiddle && !allowStepMiddle)
+ return CSSTimingData::initialTimingFunction();
+ return StepsTimingFunction::create(stepsTimingFunction->numberOfSteps(), stepsTimingFunction->stepAtPosition());
}
void CSSToStyleMap::mapNinePieceImage(RenderStyle* mutableStyle, CSSPropertyID property, CSSValue* value, NinePieceImage& image)
@@ -611,16 +544,14 @@ BorderImageLengthBox CSSToStyleMap::mapNinePieceImageQuad(CSSValue* value) const
if (!value || !value->isPrimitiveValue())
return BorderImageLengthBox(Length(Auto));
- float zoom = useSVGZoomRules() ? 1.0f : cssToLengthConversionData().zoom();
Quad* slices = toCSSPrimitiveValue(value)->getQuadValue();
// Set up a border image length box to represent our image slices.
- const CSSToLengthConversionData& conversionData = cssToLengthConversionData().copyWithAdjustedZoom(zoom);
return BorderImageLengthBox(
- toBorderImageLength(*slices->top(), conversionData),
- toBorderImageLength(*slices->right(), conversionData),
- toBorderImageLength(*slices->bottom(), conversionData),
- toBorderImageLength(*slices->left(), conversionData));
+ toBorderImageLength(*slices->top(), cssToLengthConversionData()),
+ toBorderImageLength(*slices->right(), cssToLengthConversionData()),
+ toBorderImageLength(*slices->bottom(), cssToLengthConversionData()),
+ toBorderImageLength(*slices->left(), cssToLengthConversionData()));
}
void CSSToStyleMap::mapNinePieceImageRepeat(CSSValue* value, NinePieceImage& image) const
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.h b/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.h
index b994b6f0a78..e539064f8ba 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/CSSToStyleMap.h
@@ -22,14 +22,17 @@
#ifndef CSSToStyleMap_h
#define CSSToStyleMap_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
+#include "core/animation/Timing.h"
+#include "core/animation/css/CSSTransitionData.h"
#include "core/css/resolver/ElementStyleResources.h"
+#include "core/rendering/style/RenderStyleConstants.h"
+#include "platform/animation/TimingFunction.h"
#include "wtf/Noncopyable.h"
namespace WebCore {
class FillLayer;
-class CSSAnimationData;
class CSSToLengthConversionData;
class CSSValue;
class RenderStyle;
@@ -43,10 +46,10 @@ class BorderImageLengthBox;
// CSSValue objects into their RenderStyle equivalents.
class CSSToStyleMap {
+ STACK_ALLOCATED();
WTF_MAKE_NONCOPYABLE(CSSToStyleMap);
public:
CSSToStyleMap(const StyleResolverState& state, ElementStyleResources& elementStyleResources) : m_state(state), m_elementStyleResources(elementStyleResources) { }
-
void mapFillAttachment(CSSPropertyID, FillLayer*, CSSValue*) const;
void mapFillClip(CSSPropertyID, FillLayer*, CSSValue*) const;
void mapFillComposite(CSSPropertyID, FillLayer*, CSSValue*) const;
@@ -60,15 +63,15 @@ public:
void mapFillYPosition(CSSPropertyID, FillLayer*, CSSValue*) const;
void mapFillMaskSourceType(CSSPropertyID, FillLayer*, CSSValue*);
- void mapAnimationDelay(CSSAnimationData*, CSSValue*) const;
- void mapAnimationDirection(CSSAnimationData*, CSSValue*) const;
- void mapAnimationDuration(CSSAnimationData*, CSSValue*) const;
- void mapAnimationFillMode(CSSAnimationData*, CSSValue*) const;
- void mapAnimationIterationCount(CSSAnimationData*, CSSValue*) const;
- void mapAnimationName(CSSAnimationData*, CSSValue*) const;
- void mapAnimationPlayState(CSSAnimationData*, CSSValue*) const;
- void mapAnimationProperty(CSSAnimationData*, CSSValue*) const;
- void mapAnimationTimingFunction(CSSAnimationData*, CSSValue*) const;
+ static double mapAnimationDelay(CSSValue*);
+ static Timing::PlaybackDirection mapAnimationDirection(CSSValue*);
+ static double mapAnimationDuration(CSSValue*);
+ static Timing::FillMode mapAnimationFillMode(CSSValue*);
+ static double mapAnimationIterationCount(CSSValue*);
+ static AtomicString mapAnimationName(CSSValue*);
+ static EAnimPlayState mapAnimationPlayState(CSSValue*);
+ static CSSTransitionData::TransitionProperty mapAnimationProperty(CSSValue*);
+ static PassRefPtr<TimingFunction> mapAnimationTimingFunction(CSSValue*, bool allowStepMiddle = false);
void mapNinePieceImage(RenderStyle* mutableStyle, CSSPropertyID, CSSValue*, NinePieceImage&);
void mapNinePieceImageSlice(CSSValue*, NinePieceImage&) const;
@@ -77,7 +80,6 @@ public:
private:
const CSSToLengthConversionData& cssToLengthConversionData() const;
- bool useSVGZoomRules() const;
PassRefPtr<StyleImage> styleImage(CSSPropertyID, CSSValue*);
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.cpp
index 75a1ab10f17..9d952b4363e 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.cpp
@@ -33,12 +33,10 @@ ElementResolveContext::ElementResolveContext(Element& element)
: m_element(&element)
, m_elementLinkState(element.document().visitedLinkState().determineLinkState(element))
, m_distributedToInsertionPoint(false)
- , m_resetStyleInheritance(false)
{
NodeRenderingTraversal::ParentDetails parentDetails;
m_parentNode = NodeRenderingTraversal::parent(&element, &parentDetails);
m_distributedToInsertionPoint = parentDetails.insertionPoint();
- m_resetStyleInheritance = parentDetails.resetStyleInheritance();
const Document& document = element.document();
Node* documentElement = document.documentElement();
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.h b/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.h
index f255e897425..f6c77bdbfc9 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ElementResolveContext.h
@@ -34,14 +34,14 @@ class RenderStyle;
// ElementResolveContext is immutable and serves as an input to the style resolve process.
class ElementResolveContext {
+ STACK_ALLOCATED();
public:
ElementResolveContext()
- : m_element(0)
- , m_parentNode(0)
+ : m_element(nullptr)
+ , m_parentNode(nullptr)
, m_rootElementStyle(0)
, m_elementLinkState(NotInsideLink)
, m_distributedToInsertionPoint(false)
- , m_resetStyleInheritance(false)
{
}
@@ -52,15 +52,13 @@ public:
const RenderStyle* rootElementStyle() const { return m_rootElementStyle; }
EInsideLink elementLinkState() const { return m_elementLinkState; }
bool distributedToInsertionPoint() const { return m_distributedToInsertionPoint; }
- bool resetStyleInheritance() const { return m_resetStyleInheritance; }
private:
- Element* m_element;
- ContainerNode* m_parentNode;
+ RawPtrWillBeMember<Element> m_element;
+ RawPtrWillBeMember<ContainerNode> m_parentNode;
RenderStyle* m_rootElementStyle;
EInsideLink m_elementLinkState;
bool m_distributedToInsertionPoint;
- bool m_resetStyleInheritance;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.cpp
index d8b081743c9..60643ae2a8e 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.cpp
@@ -33,15 +33,14 @@
namespace WebCore {
ElementStyleResources::ElementStyleResources()
- : m_hasNewCustomFilterProgram(false)
- , m_deviceScaleFactor(1)
+ : m_deviceScaleFactor(1)
{
}
-PassRefPtr<StyleImage> ElementStyleResources::styleImage(const TextLinkColors& textLinkColors, Color currentColor, CSSPropertyID property, CSSValue* value)
+PassRefPtr<StyleImage> ElementStyleResources::styleImage(Document& document, const TextLinkColors& textLinkColors, Color currentColor, CSSPropertyID property, CSSValue* value)
{
if (value->isImageValue())
- return cachedOrPendingFromValue(property, toCSSImageValue(value));
+ return cachedOrPendingFromValue(document, property, toCSSImageValue(value));
if (value->isImageGeneratorValue()) {
if (value->isGradientValue())
@@ -55,7 +54,7 @@ PassRefPtr<StyleImage> ElementStyleResources::styleImage(const TextLinkColors& t
if (value->isCursorImageValue())
return cursorOrPendingFromValue(property, toCSSCursorImageValue(value));
- return 0;
+ return nullptr;
}
PassRefPtr<StyleImage> ElementStyleResources::generatedOrPendingFromValue(CSSPropertyID property, CSSImageGeneratorValue* value)
@@ -75,11 +74,15 @@ PassRefPtr<StyleImage> ElementStyleResources::setOrPendingFromValue(CSSPropertyI
return image.release();
}
-PassRefPtr<StyleImage> ElementStyleResources::cachedOrPendingFromValue(CSSPropertyID property, CSSImageValue* value)
+PassRefPtr<StyleImage> ElementStyleResources::cachedOrPendingFromValue(Document& document, CSSPropertyID property, CSSImageValue* value)
{
RefPtr<StyleImage> image = value->cachedOrPendingImage();
- if (image && image->isPendingImage())
- m_pendingImageProperties.set(property, value);
+ if (image) {
+ if (image->isPendingImage())
+ m_pendingImageProperties.set(property, value);
+ else
+ value->restoreCachedResourceIfNeeded(document);
+ }
return image.release();
}
@@ -91,6 +94,16 @@ PassRefPtr<StyleImage> ElementStyleResources::cursorOrPendingFromValue(CSSProper
return image.release();
}
+void ElementStyleResources::clearPendingImageProperties()
+{
+ m_pendingImageProperties.clear();
+}
+
+void ElementStyleResources::clearPendingSVGDocuments()
+{
+ m_pendingSVGDocuments.clear();
+}
+
void ElementStyleResources::addPendingSVGDocument(FilterOperation* filterOperation, CSSSVGDocumentValue* cssSVGDocumentValue)
{
m_pendingSVGDocuments.set(filterOperation, cssSVGDocumentValue);
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.h b/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.h
index 354b022fe28..5d86c7d50f8 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ElementStyleResources.h
@@ -23,8 +23,9 @@
#ifndef ElementStyleResources_h
#define ElementStyleResources_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
#include "platform/graphics/Color.h"
+#include "platform/heap/Handle.h"
#include "wtf/HashMap.h"
#include "wtf/Noncopyable.h"
@@ -40,28 +41,29 @@ class FilterOperation;
class StyleImage;
class TextLinkColors;
-typedef HashMap<FilterOperation*, RefPtr<CSSSVGDocumentValue> > PendingSVGDocumentMap;
-typedef HashMap<CSSPropertyID, RefPtr<CSSValue> > PendingImagePropertyMap;
+typedef WillBeHeapHashMap<FilterOperation*, RefPtrWillBeMember<CSSSVGDocumentValue> > PendingSVGDocumentMap;
+typedef WillBeHeapHashMap<CSSPropertyID, RefPtrWillBeMember<CSSValue> > PendingImagePropertyMap;
// Holds information about resources, requested by stylesheets.
// Lifetime: per-element style resolve.
class ElementStyleResources {
+STACK_ALLOCATED();
WTF_MAKE_NONCOPYABLE(ElementStyleResources);
public:
ElementStyleResources();
- PassRefPtr<StyleImage> styleImage(const TextLinkColors&, Color currentColor, CSSPropertyID, CSSValue*);
+ PassRefPtr<StyleImage> styleImage(Document&, const TextLinkColors&, Color currentColor, CSSPropertyID, CSSValue*);
PassRefPtr<StyleImage> generatedOrPendingFromValue(CSSPropertyID, CSSImageGeneratorValue*);
- PassRefPtr<StyleImage> cachedOrPendingFromValue(CSSPropertyID, CSSImageValue*);
+ PassRefPtr<StyleImage> cachedOrPendingFromValue(Document&, CSSPropertyID, CSSImageValue*);
PassRefPtr<StyleImage> setOrPendingFromValue(CSSPropertyID, CSSImageSetValue*);
PassRefPtr<StyleImage> cursorOrPendingFromValue(CSSPropertyID, CSSCursorImageValue*);
const PendingImagePropertyMap& pendingImageProperties() const { return m_pendingImageProperties; }
const PendingSVGDocumentMap& pendingSVGDocuments() const { return m_pendingSVGDocuments; }
- void setHasNewCustomFilterProgram(bool hasNewCustomFilterProgram) { m_hasNewCustomFilterProgram = hasNewCustomFilterProgram; }
- bool hasNewCustomFilterProgram() const { return m_hasNewCustomFilterProgram; }
+ void clearPendingImageProperties();
+ void clearPendingSVGDocuments();
float deviceScaleFactor() const { return m_deviceScaleFactor; }
void setDeviceScaleFactor(float deviceScaleFactor) { m_deviceScaleFactor = deviceScaleFactor; }
@@ -71,7 +73,6 @@ public:
private:
PendingImagePropertyMap m_pendingImageProperties;
PendingSVGDocumentMap m_pendingSVGDocuments;
- bool m_hasNewCustomFilterProgram;
float m_deviceScaleFactor;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.cpp
index 37706e6818d..fdb2e957ab4 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.cpp
@@ -30,23 +30,12 @@
#include "core/css/resolver/FilterOperationResolver.h"
#include "core/css/CSSFilterValue.h"
-#include "core/css/CSSMixFunctionValue.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSPrimitiveValueMappings.h"
-#include "core/css/CSSShaderValue.h"
#include "core/css/CSSShadowValue.h"
#include "core/css/resolver/TransformBuilder.h"
-#include "core/rendering/style/StyleCustomFilterProgram.h"
-#include "core/rendering/style/StyleShader.h"
#include "core/rendering/svg/ReferenceFilterBuilder.h"
#include "core/svg/SVGURIReference.h"
-#include "platform/graphics/filters/custom/CustomFilterArrayParameter.h"
-#include "platform/graphics/filters/custom/CustomFilterConstants.h"
-#include "platform/graphics/filters/custom/CustomFilterNumberParameter.h"
-#include "platform/graphics/filters/custom/CustomFilterOperation.h"
-#include "platform/graphics/filters/custom/CustomFilterParameter.h"
-#include "platform/graphics/filters/custom/CustomFilterProgramInfo.h"
-#include "platform/graphics/filters/custom/CustomFilterTransformParameter.h"
namespace WebCore {
@@ -75,277 +64,12 @@ static FilterOperation::OperationType filterOperationForType(CSSFilterValue::Fil
return FilterOperation::BLUR;
case CSSFilterValue::DropShadowFilterOperation:
return FilterOperation::DROP_SHADOW;
- case CSSFilterValue::CustomFilterOperation:
- return FilterOperation::CUSTOM;
case CSSFilterValue::UnknownFilterOperation:
return FilterOperation::NONE;
}
return FilterOperation::NONE;
}
-static StyleShader* styleShader(CSSValue* value)
-{
- if (value->isShaderValue())
- return toCSSShaderValue(value)->cachedOrPendingShader();
- return 0;
-}
-
-static PassRefPtr<CustomFilterParameter> parseCustomFilterArrayParameter(const String& name, CSSValueList* values)
-{
- RefPtr<CustomFilterArrayParameter> arrayParameter = CustomFilterArrayParameter::create(name);
- for (unsigned i = 0, length = values->length(); i < length; ++i) {
- CSSValue* value = values->itemWithoutBoundsCheck(i);
- if (!value->isPrimitiveValue())
- return 0;
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (primitiveValue->primitiveType() != CSSPrimitiveValue::CSS_NUMBER)
- return 0;
- arrayParameter->addValue(primitiveValue->getDoubleValue());
- }
- return arrayParameter.release();
-}
-
-static PassRefPtr<CustomFilterParameter> parseCustomFilterNumberParameter(const String& name, CSSValueList* values)
-{
- RefPtr<CustomFilterNumberParameter> numberParameter = CustomFilterNumberParameter::create(name);
- for (unsigned i = 0; i < values->length(); ++i) {
- CSSValue* value = values->itemWithoutBoundsCheck(i);
- if (!value->isPrimitiveValue())
- return 0;
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (primitiveValue->primitiveType() != CSSPrimitiveValue::CSS_NUMBER)
- return 0;
- numberParameter->addValue(primitiveValue->getDoubleValue());
- }
- return numberParameter.release();
-}
-
-static PassRefPtr<CustomFilterParameter> parseCustomFilterTransformParameter(const String& name, CSSValueList* values, StyleResolverState& state)
-{
- RefPtr<CustomFilterTransformParameter> transformParameter = CustomFilterTransformParameter::create(name);
- TransformOperations operations;
- TransformBuilder::createTransformOperations(values, state.cssToLengthConversionData(), operations);
- transformParameter->setOperations(operations);
- return transformParameter.release();
-}
-
-static PassRefPtr<CustomFilterParameter> parseCustomFilterParameter(const String& name, CSSValue* parameterValue, StyleResolverState& state)
-{
- // FIXME: Implement other parameters types parsing.
- // booleans: https://bugs.webkit.org/show_bug.cgi?id=76438
- // textures: https://bugs.webkit.org/show_bug.cgi?id=71442
- // mat2, mat3, mat4: https://bugs.webkit.org/show_bug.cgi?id=71444
- // Number parameters are wrapped inside a CSSValueList and all
- // the other functions values inherit from CSSValueList.
- if (!parameterValue->isValueList())
- return 0;
-
- CSSValueList* values = toCSSValueList(parameterValue);
- if (!values->length())
- return 0;
-
- if (parameterValue->isArrayFunctionValue())
- return parseCustomFilterArrayParameter(name, values);
-
- // If the first value of the list is a transform function,
- // then we could safely assume that all the remaining items
- // are transforms. parseCustomFilterTransformParameter will
- // return 0 if that assumption is incorrect.
- if (values->itemWithoutBoundsCheck(0)->isTransformValue())
- return parseCustomFilterTransformParameter(name, values, state);
-
- // We can have only arrays of booleans or numbers, so use the first value to choose between those two.
- // We need up to 4 values (all booleans or all numbers).
- if (!values->itemWithoutBoundsCheck(0)->isPrimitiveValue() || values->length() > 4)
- return 0;
-
- CSSPrimitiveValue* firstPrimitiveValue = toCSSPrimitiveValue(values->itemWithoutBoundsCheck(0));
- if (firstPrimitiveValue->primitiveType() == CSSPrimitiveValue::CSS_NUMBER)
- return parseCustomFilterNumberParameter(name, values);
-
- // FIXME: Implement the boolean array parameter here.
- // https://bugs.webkit.org/show_bug.cgi?id=76438
-
- return 0;
-}
-
-static bool parseCustomFilterParameterList(CSSValue* parametersValue, CustomFilterParameterList& parameterList, StyleResolverState& state)
-{
- HashSet<String> knownParameterNames;
- CSSValueListIterator parameterIterator(parametersValue);
- for (; parameterIterator.hasMore(); parameterIterator.advance()) {
- if (!parameterIterator.value()->isValueList())
- return false;
- CSSValueListIterator iterator(parameterIterator.value());
- if (!iterator.isPrimitiveValue())
- return false;
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(iterator.value());
- if (primitiveValue->primitiveType() != CSSPrimitiveValue::CSS_STRING)
- return false;
-
- String name = primitiveValue->getStringValue();
- // Do not allow duplicate parameter names.
- if (!knownParameterNames.add(name).isNewEntry)
- return false;
-
- iterator.advance();
-
- if (!iterator.hasMore())
- return false;
-
- RefPtr<CustomFilterParameter> parameter = parseCustomFilterParameter(name, iterator.value(), state);
- if (!parameter)
- return false;
- parameterList.append(parameter.release());
- }
-
- // Make sure we sort the parameters before passing them down to the CustomFilterOperation.
- parameterList.sortParametersByName();
-
- return true;
-}
-
-static PassRefPtr<CustomFilterOperation> createCustomFilterOperationWithAtRuleReferenceSyntax(CSSFilterValue*)
-{
- // FIXME: Implement style resolution for the custom filter at-rule reference syntax.
- return 0;
-}
-
-static PassRefPtr<CustomFilterProgram> createCustomFilterProgram(CSSShaderValue* vertexShader, CSSShaderValue* fragmentShader,
- CustomFilterProgramType programType, const CustomFilterProgramMixSettings& mixSettings, CustomFilterMeshType meshType,
- StyleResolverState& state)
-{
- ResourceFetcher* fetcher = state.document().fetcher();
- KURL vertexShaderURL = vertexShader ? vertexShader->completeURL(fetcher) : KURL();
- KURL fragmentShaderURL = fragmentShader ? fragmentShader->completeURL(fetcher) : KURL();
- // We re-resolve the custom filter style after the shaders are loaded.
- // We always create a StyleCustomFilterProgram here, and later replace it with a program from the StyleCustomFilterProgramCache, if available.
- StyleShader* styleVertexShader = vertexShader ? styleShader(vertexShader) : 0;
- StyleShader* styleFragmentShader = fragmentShader ? styleShader(fragmentShader) : 0;
- RefPtr<StyleCustomFilterProgram> program = StyleCustomFilterProgram::create(vertexShaderURL, styleVertexShader,
- fragmentShaderURL, styleFragmentShader, programType, mixSettings, meshType);
- state.elementStyleResources().setHasNewCustomFilterProgram(true);
- return program.release();
-}
-
-static PassRefPtr<CustomFilterOperation> createCustomFilterOperationWithInlineSyntax(CSSFilterValue* filterValue, StyleResolverState& state)
-{
- CSSValue* shadersValue = filterValue->itemWithoutBoundsCheck(0);
- ASSERT_WITH_SECURITY_IMPLICATION(shadersValue->isValueList());
- CSSValueList* shadersList = toCSSValueList(shadersValue);
-
- unsigned shadersListLength = shadersList->length();
- ASSERT(shadersListLength);
-
- CSSShaderValue* vertexShader = 0;
- CSSShaderValue* fragmentShader = 0;
-
- if (shadersList->itemWithoutBoundsCheck(0)->isShaderValue())
- vertexShader = toCSSShaderValue(shadersList->itemWithoutBoundsCheck(0));
-
- CustomFilterProgramType programType = ProgramTypeBlendsElementTexture;
- CustomFilterProgramMixSettings mixSettings;
-
- if (shadersListLength > 1) {
- CSSValue* fragmentShaderOrMixFunction = shadersList->itemWithoutBoundsCheck(1);
- if (fragmentShaderOrMixFunction->isMixFunctionValue()) {
- CSSMixFunctionValue* mixFunction = toCSSMixFunctionValue(fragmentShaderOrMixFunction);
- CSSValueListIterator iterator(mixFunction);
-
- ASSERT(mixFunction->length());
- if (iterator.value()->isShaderValue())
- fragmentShader = toCSSShaderValue(iterator.value());
-
- iterator.advance();
-
- ASSERT(mixFunction->length() <= 3);
- while (iterator.hasMore()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(iterator.value());
- if (CSSParser::isBlendMode(primitiveValue->getValueID()))
- mixSettings.blendMode = *primitiveValue;
- else if (CSSParser::isCompositeOperator(primitiveValue->getValueID()))
- mixSettings.compositeOperator = *primitiveValue;
- else
- ASSERT_NOT_REACHED();
- iterator.advance();
- }
- } else {
- programType = ProgramTypeNoElementTexture;
- if (fragmentShaderOrMixFunction->isShaderValue())
- fragmentShader = toCSSShaderValue(fragmentShaderOrMixFunction);
- }
- }
-
- if (!vertexShader && !fragmentShader)
- return 0;
-
- unsigned meshRows = 1;
- unsigned meshColumns = 1;
- CustomFilterMeshType meshType = MeshTypeAttached;
-
- CSSValue* parametersValue = 0;
-
- if (filterValue->length() > 1) {
- CSSValueListIterator iterator(filterValue->itemWithoutBoundsCheck(1));
-
- // The second value might be the mesh box or the list of parameters:
- // If it starts with a number or any of the mesh-box identifiers it is
- // the mesh-box list, if not it means it is the parameters list.
-
- if (iterator.hasMore() && iterator.isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(iterator.value());
- if (primitiveValue->isNumber()) {
- // If only one integer value is specified, it will set both
- // the rows and the columns.
- meshColumns = meshRows = primitiveValue->getIntValue();
- iterator.advance();
-
- // Try to match another number for the rows.
- if (iterator.hasMore() && iterator.isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(iterator.value());
- if (primitiveValue->isNumber()) {
- meshRows = primitiveValue->getIntValue();
- iterator.advance();
- }
- }
- }
- }
-
- if (iterator.hasMore() && iterator.isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(iterator.value());
- if (primitiveValue->getValueID() == CSSValueDetached) {
- meshType = MeshTypeDetached;
- iterator.advance();
- }
- }
-
- if (!iterator.index()) {
- // If no value was consumed from the mesh value, then it is just a parameter list, meaning that we end up
- // having just two CSSListValues: list of shaders and list of parameters.
- ASSERT(filterValue->length() == 2);
- parametersValue = filterValue->itemWithoutBoundsCheck(1);
- }
- }
-
- if (filterValue->length() > 2 && !parametersValue)
- parametersValue = filterValue->itemWithoutBoundsCheck(2);
-
- CustomFilterParameterList parameterList;
- if (parametersValue && !parseCustomFilterParameterList(parametersValue, parameterList, state))
- return 0;
-
- RefPtr<CustomFilterProgram> program = createCustomFilterProgram(vertexShader, fragmentShader, programType, mixSettings, meshType, state);
- return CustomFilterOperation::create(program.release(), parameterList, meshRows, meshColumns, meshType);
-}
-
-static PassRefPtr<CustomFilterOperation> createCustomFilterOperation(CSSFilterValue* filterValue, StyleResolverState& state)
-{
- ASSERT(filterValue->length());
- bool isAtRuleReferenceSyntax = filterValue->itemWithoutBoundsCheck(0)->isPrimitiveValue();
- return isAtRuleReferenceSyntax ? createCustomFilterOperationWithAtRuleReferenceSyntax(filterValue) : createCustomFilterOperationWithInlineSyntax(filterValue, state);
-}
-
-
bool FilterOperationResolver::createFilterOperations(CSSValue* inValue, const CSSToLengthConversionData& unadjustedConversionData, FilterOperations& outOperations, StyleResolverState& state)
{
ASSERT(outOperations.isEmpty());
@@ -362,7 +86,11 @@ bool FilterOperationResolver::createFilterOperations(CSSValue* inValue, const CS
if (!inValue->isValueList())
return false;
+#ifdef BLINK_SCALE_FILTERS_AT_RECORD_TIME
float zoomFactor = unadjustedConversionData.zoom() * state.elementStyleResources().deviceScaleFactor();
+#else
+ float zoomFactor = unadjustedConversionData.zoom();
+#endif
const CSSToLengthConversionData& conversionData = unadjustedConversionData.copyWithAdjustedZoom(zoomFactor);
FilterOperations operations;
for (CSSValueListIterator i = inValue; i.hasMore(); i.advance()) {
@@ -373,19 +101,6 @@ bool FilterOperationResolver::createFilterOperations(CSSValue* inValue, const CS
CSSFilterValue* filterValue = toCSSFilterValue(i.value());
FilterOperation::OperationType operationType = filterOperationForType(filterValue->operationType());
- if (operationType == FilterOperation::VALIDATED_CUSTOM) {
- // ValidatedCustomFilterOperation is not supposed to end up in the RenderStyle.
- ASSERT_NOT_REACHED();
- continue;
- }
- if (operationType == FilterOperation::CUSTOM) {
- RefPtr<CustomFilterOperation> operation = createCustomFilterOperation(filterValue, state);
- if (!operation)
- return false;
-
- operations.operations().append(operation);
- continue;
- }
if (operationType == FilterOperation::REFERENCE) {
if (filterValue->length() != 1)
continue;
@@ -397,7 +112,7 @@ bool FilterOperationResolver::createFilterOperations(CSSValue* inValue, const CS
CSSSVGDocumentValue* svgDocumentValue = toCSSSVGDocumentValue(argument);
KURL url = state.document().completeURL(svgDocumentValue->url());
- RefPtr<ReferenceFilterOperation> operation = ReferenceFilterOperation::create(svgDocumentValue->url(), url.fragmentIdentifier());
+ RefPtr<ReferenceFilterOperation> operation = ReferenceFilterOperation::create(svgDocumentValue->url(), AtomicString(url.fragmentIdentifier()));
if (SVGURIReference::isExternalURIReference(svgDocumentValue->url(), state.document())) {
if (!svgDocumentValue->loadRequested())
state.elementStyleResources().addPendingSVGDocument(operation.get(), svgDocumentValue);
@@ -463,9 +178,6 @@ bool FilterOperationResolver::createFilterOperations(CSSValue* inValue, const CS
Length stdDeviation = Length(0, Fixed);
if (filterValue->length() >= 1)
stdDeviation = firstValue->convertToLength<FixedConversion | PercentConversion>(conversionData);
- if (stdDeviation.isUndefined())
- return false;
-
operations.operations().append(BlurFilterOperation::create(stdDeviation));
break;
}
@@ -480,11 +192,11 @@ bool FilterOperationResolver::createFilterOperations(CSSValue* inValue, const CS
CSSShadowValue* item = toCSSShadowValue(cssValue);
IntPoint location(item->x->computeLength<int>(conversionData), item->y->computeLength<int>(conversionData));
int blur = item->blur ? item->blur->computeLength<int>(conversionData) : 0;
- Color shadowColor;
+ Color shadowColor = Color::transparent;
if (item->color)
shadowColor = state.document().textLinkColors().colorFromPrimitiveValue(item->color.get(), state.style()->color());
- operations.operations().append(DropShadowFilterOperation::create(location, blur, shadowColor.isValid() ? shadowColor : Color::transparent));
+ operations.operations().append(DropShadowFilterOperation::create(location, blur, shadowColor));
break;
}
case CSSFilterValue::UnknownFilterOperation:
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.h b/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.h
index 4475ce31d63..494e0d98612 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/FilterOperationResolver.h
@@ -24,6 +24,7 @@
#include "core/css/resolver/StyleResolverState.h"
#include "platform/graphics/filters/FilterOperations.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -31,8 +32,7 @@ class CSSToLengthConversionData;
class CSSValue;
class FilterOperationResolver {
-private:
- FilterOperationResolver();
+ STATIC_ONLY(FilterOperationResolver);
public:
static bool createFilterOperations(CSSValue* inValue, const CSSToLengthConversionData&, FilterOperations& outOperations, StyleResolverState&);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.cpp
index 57eba497510..9de7131f88c 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.cpp
@@ -27,10 +27,11 @@
#include "core/css/CSSFontFeatureValue.h"
#include "core/css/CSSToLengthConversionData.h"
#include "core/css/FontSize.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
#include "core/rendering/RenderTheme.h"
#include "core/rendering/RenderView.h"
+#include "platform/fonts/FontDescription.h"
#include "platform/text/LocaleToScriptMapping.h"
namespace WebCore {
@@ -61,23 +62,35 @@ private:
FontBuilder::FontBuilder()
: m_document(0)
- , m_useSVGZoomRules(false)
+ , m_fontSizehasViewportUnits(false)
+ , m_style(0)
, m_fontDirty(false)
{
}
-void FontBuilder::initForStyleResolve(const Document& document, RenderStyle* style, bool useSVGZoomRules)
+void FontBuilder::initForStyleResolve(const Document& document, RenderStyle* style)
{
- // All documents need to be in a frame (and thus have access to Settings)
- // for style-resolution to make sense.
- // Unfortunately SVG Animations currently violate this: crbug.com/260966
- // ASSERT(m_document->frame());
+ ASSERT(document.frame());
m_document = &document;
- m_useSVGZoomRules = useSVGZoomRules;
m_style = style;
m_fontDirty = false;
}
+inline static void setFontFamilyToStandard(FontDescription& fontDescription, const Document* document)
+{
+ if (!document || !document->settings())
+ return;
+
+ fontDescription.setGenericFamily(FontDescription::StandardFamily);
+ const AtomicString& standardFontFamily = document->settings()->genericFontFamilySettings().standard();
+ if (standardFontFamily.isEmpty())
+ return;
+
+ fontDescription.firstFamily().setFamily(standardFontFamily);
+ // FIXME: Why is this needed here?
+ fontDescription.firstFamily().appendFamily(nullptr);
+}
+
void FontBuilder::setInitial(float effectiveZoom)
{
ASSERT(m_document && m_document->settings());
@@ -87,13 +100,7 @@ void FontBuilder::setInitial(float effectiveZoom)
FontDescriptionChangeScope scope(this);
scope.reset();
- scope.fontDescription().setGenericFamily(FontDescription::StandardFamily);
- scope.fontDescription().setUsePrinterFont(m_document->printing());
- const AtomicString& standardFontFamily = m_document->settings()->genericFontFamilySettings().standard();
- if (!standardFontFamily.isEmpty()) {
- scope.fontDescription().firstFamily().setFamily(standardFontFamily);
- scope.fontDescription().firstFamily().appendFamily(0);
- }
+ setFontFamilyToStandard(scope.fontDescription(), m_document);
scope.fontDescription().setKeywordSize(CSSValueMedium - CSSValueXxSmall + 1);
setSize(scope.fontDescription(), effectiveZoom, FontSize::fontSizeForKeyword(m_document, CSSValueMedium, false));
}
@@ -126,25 +133,17 @@ void FontBuilder::fromSystemFont(CSSValueID valueId, float effectiveZoom)
ASSERT(settings); // If we're doing style resolution, this document should always be in a frame and thus have settings
if (!settings)
return;
- fontDescription.setUsePrinterFont(m_document->printing());
// Handle the zoom factor.
fontDescription.setComputedSize(getComputedSizeFromSpecifiedSize(fontDescription, effectiveZoom, fontDescription.specifiedSize()));
scope.set(fontDescription);
}
-void FontBuilder::setFontFamilyInitial(float effectiveZoom)
+void FontBuilder::setFontFamilyInitial()
{
FontDescriptionChangeScope scope(this);
- FontDescription initialDesc = FontDescription();
-
- // We need to adjust the size to account for the generic family change from monospace to non-monospace.
- if (scope.fontDescription().keywordSize() && scope.fontDescription().useFixedDefaultSize())
- setSize(scope.fontDescription(), effectiveZoom, FontSize::fontSizeForKeyword(m_document, CSSValueXxSmall + scope.fontDescription().keywordSize() - 1, false));
- scope.fontDescription().setGenericFamily(initialDesc.genericFamily());
- if (!initialDesc.firstFamily().familyIsEmpty())
- scope.fontDescription().setFamily(initialDesc.firstFamily());
+ setFontFamilyToStandard(scope.fontDescription(), m_document);
}
void FontBuilder::setFontFamilyInherit(const FontDescription& parentFontDescription)
@@ -153,11 +152,10 @@ void FontBuilder::setFontFamilyInherit(const FontDescription& parentFontDescript
scope.fontDescription().setGenericFamily(parentFontDescription.genericFamily());
scope.fontDescription().setFamily(parentFontDescription.family());
- scope.fontDescription().setIsSpecifiedFont(parentFontDescription.isSpecifiedFont());
}
// FIXME: I am not convinced FontBuilder needs to know anything about CSSValues.
-void FontBuilder::setFontFamilyValue(CSSValue* value, float effectiveZoom)
+void FontBuilder::setFontFamilyValue(CSSValue* value)
{
FontDescriptionChangeScope scope(this);
@@ -218,9 +216,8 @@ void FontBuilder::setFontFamilyValue(CSSValue* value, float effectiveZoom)
if (!currFamily) {
// Filling in the first family.
firstFamily.setFamily(face);
- firstFamily.appendFamily(0); // Remove any inherited family-fallback list.
+ firstFamily.appendFamily(nullptr); // Remove any inherited family-fallback list.
currFamily = &firstFamily;
- scope.fontDescription().setIsSpecifiedFont(scope.fontDescription().genericFamily() == FontDescription::NoFamily);
} else {
RefPtr<SharedFontFamily> newFamily = SharedFontFamily::create();
newFamily->setFamily(face);
@@ -236,10 +233,10 @@ void FontBuilder::setFontFamilyValue(CSSValue* value, float effectiveZoom)
return;
if (scope.fontDescription().keywordSize() && scope.fontDescription().useFixedDefaultSize() != oldFamilyUsedFixedDefaultSize)
- setSize(scope.fontDescription(), effectiveZoom, FontSize::fontSizeForKeyword(m_document, CSSValueXxSmall + scope.fontDescription().keywordSize() - 1, !oldFamilyUsedFixedDefaultSize));
+ scope.fontDescription().setSpecifiedSize(FontSize::fontSizeForKeyword(m_document, CSSValueXxSmall + scope.fontDescription().keywordSize() - 1, !oldFamilyUsedFixedDefaultSize));
}
-void FontBuilder::setFontSizeInitial(float effectiveZoom)
+void FontBuilder::setFontSizeInitial()
{
FontDescriptionChangeScope scope(this);
@@ -249,10 +246,10 @@ void FontBuilder::setFontSizeInitial(float effectiveZoom)
return;
scope.fontDescription().setKeywordSize(CSSValueMedium - CSSValueXxSmall + 1);
- setSize(scope.fontDescription(), effectiveZoom, size);
+ scope.fontDescription().setSpecifiedSize(size);
}
-void FontBuilder::setFontSizeInherit(const FontDescription& parentFontDescription, float effectiveZoom)
+void FontBuilder::setFontSizeInherit(const FontDescription& parentFontDescription)
{
FontDescriptionChangeScope scope(this);
@@ -262,7 +259,7 @@ void FontBuilder::setFontSizeInherit(const FontDescription& parentFontDescriptio
return;
scope.fontDescription().setKeywordSize(parentFontDescription.keywordSize());
- setSize(scope.fontDescription(), effectiveZoom, size);
+ scope.fontDescription().setSpecifiedSize(size);
}
// FIXME: Figure out where we fall in the size ranges (xx-small to xxx-large)
@@ -278,7 +275,7 @@ static float smallerFontSize(float size)
}
// FIXME: Have to pass RenderStyles here for calc/computed values. This shouldn't be neecessary.
-void FontBuilder::setFontSizeValue(CSSValue* value, RenderStyle* parentStyle, const RenderStyle* rootElementStyle, float effectiveZoom)
+void FontBuilder::setFontSizeValue(CSSValue* value, RenderStyle* parentStyle, const RenderStyle* rootElementStyle)
{
if (!value->isPrimitiveValue())
return;
@@ -324,16 +321,22 @@ void FontBuilder::setFontSizeValue(CSSValue* value, RenderStyle* parentStyle, co
scope.fontDescription().setIsAbsoluteSize(parentIsAbsoluteSize && (valueID == CSSValueLarger || valueID == CSSValueSmaller));
} else {
scope.fontDescription().setIsAbsoluteSize(parentIsAbsoluteSize || !(primitiveValue->isPercentage() || primitiveValue->isFontRelativeLength()));
- if (primitiveValue->isLength())
- size = primitiveValue->computeLength<float>(CSSToLengthConversionData(parentStyle, rootElementStyle, 1.0, true));
- else if (primitiveValue->isPercentage())
+ if (primitiveValue->isPercentage()) {
size = (primitiveValue->getFloatValue() * parentSize) / 100.0f;
- else if (primitiveValue->isCalculatedPercentageWithLength())
- size = primitiveValue->cssCalcValue()->toCalcValue(CSSToLengthConversionData(parentStyle, rootElementStyle, 1.0f))->evaluate(parentSize);
- else if (primitiveValue->isViewportPercentageLength())
- size = valueForLength(primitiveValue->viewportPercentageLength(), 0, m_document->renderView());
- else
- return;
+ } else {
+ // If we have viewport units the conversion will mark the parent style as having viewport units.
+ bool parentHasViewportUnits = parentStyle->hasViewportUnits();
+ parentStyle->setHasViewportUnits(false);
+ CSSToLengthConversionData conversionData(parentStyle, rootElementStyle, m_document->renderView(), 1.0f, true);
+ if (primitiveValue->isLength())
+ size = primitiveValue->computeLength<float>(conversionData);
+ else if (primitiveValue->isCalculatedPercentageWithLength())
+ size = primitiveValue->cssCalcValue()->toCalcValue(conversionData)->evaluate(parentSize);
+ else
+ ASSERT_NOT_REACHED();
+ m_fontSizehasViewportUnits = parentStyle->hasViewportUnits();
+ parentStyle->setHasViewportUnits(parentHasViewportUnits);
+ }
}
if (size < 0)
@@ -343,7 +346,8 @@ void FontBuilder::setFontSizeValue(CSSValue* value, RenderStyle* parentStyle, co
// Cap font size here to make sure that doesn't happen.
size = std::min(maximumAllowedFontSize, size);
- setSize(scope.fontDescription(), effectiveZoom, size);
+
+ scope.fontDescription().setSpecifiedSize(size);
}
void FontBuilder::setWeight(FontWeight fontWeight)
@@ -374,6 +378,7 @@ void FontBuilder::setFontVariantLigaturesInitial()
scope.fontDescription().setCommonLigaturesState(FontDescription::NormalLigaturesState);
scope.fontDescription().setDiscretionaryLigaturesState(FontDescription::NormalLigaturesState);
scope.fontDescription().setHistoricalLigaturesState(FontDescription::NormalLigaturesState);
+ scope.fontDescription().setContextualLigaturesState(FontDescription::NormalLigaturesState);
}
void FontBuilder::setFontVariantLigaturesInherit(const FontDescription& parentFontDescription)
@@ -383,6 +388,7 @@ void FontBuilder::setFontVariantLigaturesInherit(const FontDescription& parentFo
scope.fontDescription().setCommonLigaturesState(parentFontDescription.commonLigaturesState());
scope.fontDescription().setDiscretionaryLigaturesState(parentFontDescription.discretionaryLigaturesState());
scope.fontDescription().setHistoricalLigaturesState(parentFontDescription.historicalLigaturesState());
+ scope.fontDescription().setContextualLigaturesState(parentFontDescription.historicalLigaturesState());
}
void FontBuilder::setFontVariantLigaturesValue(CSSValue* value)
@@ -392,6 +398,7 @@ void FontBuilder::setFontVariantLigaturesValue(CSSValue* value)
FontDescription::LigaturesState commonLigaturesState = FontDescription::NormalLigaturesState;
FontDescription::LigaturesState discretionaryLigaturesState = FontDescription::NormalLigaturesState;
FontDescription::LigaturesState historicalLigaturesState = FontDescription::NormalLigaturesState;
+ FontDescription::LigaturesState contextualLigaturesState = FontDescription::NormalLigaturesState;
if (value->isValueList()) {
CSSValueList* valueList = toCSSValueList(value);
@@ -419,6 +426,12 @@ void FontBuilder::setFontVariantLigaturesValue(CSSValue* value)
case CSSValueHistoricalLigatures:
historicalLigaturesState = FontDescription::EnabledLigaturesState;
break;
+ case CSSValueNoContextual:
+ contextualLigaturesState = FontDescription::DisabledLigaturesState;
+ break;
+ case CSSValueContextual:
+ contextualLigaturesState = FontDescription::EnabledLigaturesState;
+ break;
default:
ASSERT_NOT_REACHED();
break;
@@ -426,7 +439,7 @@ void FontBuilder::setFontVariantLigaturesValue(CSSValue* value)
}
}
}
-#if !ASSERT_DISABLED
+#if ASSERT_ENABLED
else {
ASSERT_WITH_SECURITY_IMPLICATION(value->isPrimitiveValue());
ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNormal);
@@ -436,34 +449,36 @@ void FontBuilder::setFontVariantLigaturesValue(CSSValue* value)
scope.fontDescription().setCommonLigaturesState(commonLigaturesState);
scope.fontDescription().setDiscretionaryLigaturesState(discretionaryLigaturesState);
scope.fontDescription().setHistoricalLigaturesState(historicalLigaturesState);
+ scope.fontDescription().setContextualLigaturesState(contextualLigaturesState);
}
void FontBuilder::setScript(const String& locale)
{
FontDescriptionChangeScope scope(this);
+ scope.fontDescription().setLocale(locale);
scope.fontDescription().setScript(localeToScriptCodeForFontSelection(locale));
}
-void FontBuilder::setItalic(FontItalic italic)
+void FontBuilder::setStyle(FontStyle italic)
{
FontDescriptionChangeScope scope(this);
- scope.fontDescription().setItalic(italic);
+ scope.fontDescription().setStyle(italic);
}
-void FontBuilder::setSmallCaps(FontSmallCaps smallCaps)
+void FontBuilder::setVariant(FontVariant smallCaps)
{
FontDescriptionChangeScope scope(this);
- scope.fontDescription().setSmallCaps(smallCaps);
+ scope.fontDescription().setVariant(smallCaps);
}
-void FontBuilder::setTextRenderingMode(TextRenderingMode textRenderingMode)
+void FontBuilder::setTextRendering(TextRenderingMode textRenderingMode)
{
FontDescriptionChangeScope scope(this);
- scope.fontDescription().setTextRenderingMode(textRenderingMode);
+ scope.fontDescription().setTextRendering(textRenderingMode);
}
void FontBuilder::setKerning(FontDescription::Kerning kerning)
@@ -513,13 +528,10 @@ void FontBuilder::setSize(FontDescription& fontDescription, float effectiveZoom,
float FontBuilder::getComputedSizeFromSpecifiedSize(FontDescription& fontDescription, float effectiveZoom, float specifiedSize)
{
- float zoomFactor = 1.0f;
- if (!m_useSVGZoomRules) {
- zoomFactor = effectiveZoom;
- // FIXME: Why is this here!!!!?!
- if (Frame* frame = m_document->frame())
- zoomFactor *= frame->textZoomFactor();
- }
+ float zoomFactor = effectiveZoom;
+ // FIXME: Why is this here!!!!?!
+ if (LocalFrame* frame = m_document->frame())
+ zoomFactor *= frame->textZoomFactor();
return FontSize::getComputedSizeFromSpecifiedSize(m_document, zoomFactor, fontDescription.isAbsoluteSize(), specifiedSize);
}
@@ -614,48 +626,36 @@ void FontBuilder::checkForGenericFamilyChange(RenderStyle* style, const RenderSt
setSize(scope.fontDescription(), style->effectiveZoom(), size);
}
-void FontBuilder::checkForZoomChange(RenderStyle* style, const RenderStyle* parentStyle)
+void FontBuilder::updateComputedSize(RenderStyle* style, const RenderStyle* parentStyle)
{
FontDescriptionChangeScope scope(this);
- if (style->effectiveZoom() == parentStyle->effectiveZoom())
- return;
-
- setSize(scope.fontDescription(), style->effectiveZoom(), scope.fontDescription().specifiedSize());
+ scope.fontDescription().setComputedSize(getComputedSizeFromSpecifiedSize(scope.fontDescription(), style->effectiveZoom(), scope.fontDescription().specifiedSize()));
}
// FIXME: style param should come first
-void FontBuilder::createFont(PassRefPtr<FontSelector> fontSelector, const RenderStyle* parentStyle, RenderStyle* style)
+void FontBuilder::createFont(PassRefPtrWillBeRawPtr<FontSelector> fontSelector, const RenderStyle* parentStyle, RenderStyle* style)
{
if (!m_fontDirty)
return;
+ updateComputedSize(style, parentStyle);
checkForGenericFamilyChange(style, parentStyle);
- checkForZoomChange(style, parentStyle);
checkForOrientationChange(style);
style->font().update(fontSelector);
m_fontDirty = false;
}
-void FontBuilder::createFontForDocument(PassRefPtr<FontSelector> fontSelector, RenderStyle* documentStyle)
+void FontBuilder::createFontForDocument(PassRefPtrWillBeRawPtr<FontSelector> fontSelector, RenderStyle* documentStyle)
{
FontDescription fontDescription = FontDescription();
fontDescription.setScript(localeToScriptCodeForFontSelection(documentStyle->locale()));
- if (Settings* settings = m_document->settings()) {
- fontDescription.setUsePrinterFont(m_document->printing());
- const AtomicString& standardFont = settings->genericFontFamilySettings().standard(fontDescription.script());
- if (!standardFont.isEmpty()) {
- fontDescription.setGenericFamily(FontDescription::StandardFamily);
- fontDescription.firstFamily().setFamily(standardFont);
- fontDescription.firstFamily().appendFamily(0);
- }
- fontDescription.setKeywordSize(CSSValueMedium - CSSValueXxSmall + 1);
- int size = FontSize::fontSizeForKeyword(m_document, CSSValueMedium, false);
- fontDescription.setSpecifiedSize(size);
- fontDescription.setComputedSize(getComputedSizeFromSpecifiedSize(fontDescription, documentStyle->effectiveZoom(), size));
- } else {
- fontDescription.setUsePrinterFont(m_document->printing());
- }
+
+ setFontFamilyToStandard(fontDescription, m_document);
+ fontDescription.setKeywordSize(CSSValueMedium - CSSValueXxSmall + 1);
+ int size = FontSize::fontSizeForKeyword(m_document, CSSValueMedium, false);
+ fontDescription.setSpecifiedSize(size);
+ fontDescription.setComputedSize(getComputedSizeFromSpecifiedSize(fontDescription, documentStyle->effectiveZoom(), size));
FontOrientation fontOrientation;
NonCJKGlyphOrientation glyphOrientation;
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.h b/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.h
index b573b5159fd..2a611a01b1c 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilder.h
@@ -23,9 +23,10 @@
#ifndef FontBuilder_h
#define FontBuilder_h
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
#include "platform/fonts/FontDescription.h"
+#include "platform/heap/Handle.h"
#include "wtf/PassRefPtr.h"
namespace WebCore {
@@ -42,7 +43,7 @@ public:
FontBuilder();
// FIXME: The name is probably wrong, but matches StyleResolverState callsite for consistency.
- void initForStyleResolve(const Document&, RenderStyle*, bool useSVGZoomRules);
+ void initForStyleResolve(const Document&, RenderStyle*);
void setInitial(float effectiveZoom);
@@ -51,13 +52,13 @@ public:
void inheritFrom(const FontDescription&);
void fromSystemFont(CSSValueID, float effectiveZoom);
- void setFontFamilyInitial(float effectiveZoom);
+ void setFontFamilyInitial();
void setFontFamilyInherit(const FontDescription&);
- void setFontFamilyValue(CSSValue*, float effectiveZoom);
+ void setFontFamilyValue(CSSValue*);
- void setFontSizeInitial(float effectiveZoom);
- void setFontSizeInherit(const FontDescription&, float effectiveZoom);
- void setFontSizeValue(CSSValue*, RenderStyle* parentStyle, const RenderStyle* rootElementStyle, float effectiveZoom);
+ void setFontSizeInitial();
+ void setFontSizeInherit(const FontDescription&);
+ void setFontSizeValue(CSSValue*, RenderStyle* parentStyle, const RenderStyle* rootElementStyle);
void setWeight(FontWeight);
void setWeightBolder();
@@ -71,24 +72,34 @@ public:
void setFeatureSettingsValue(CSSValue*);
void setScript(const String& locale);
- void setItalic(FontItalic);
- void setSmallCaps(FontSmallCaps);
- void setTextRenderingMode(TextRenderingMode);
+ void setStyle(FontStyle);
+ void setVariant(FontVariant);
+ void setTextRendering(TextRenderingMode);
void setKerning(FontDescription::Kerning);
void setFontSmoothing(FontSmoothingMode);
// FIXME: These need to just vend a Font object eventually.
- void createFont(PassRefPtr<FontSelector>, const RenderStyle* parentStyle, RenderStyle*);
+ void createFont(PassRefPtrWillBeRawPtr<FontSelector>, const RenderStyle* parentStyle, RenderStyle*);
// FIXME: This is nearly static, should either made fully static or decomposed into
// FontBuilder calls at the callsite.
- void createFontForDocument(PassRefPtr<FontSelector>, RenderStyle*);
+ void createFontForDocument(PassRefPtrWillBeRawPtr<FontSelector>, RenderStyle*);
+
+ bool fontSizeHasViewportUnits() { return m_fontSizehasViewportUnits; }
// FIXME: These should not be necessary eventually.
void setFontDirty(bool fontDirty) { m_fontDirty = fontDirty; }
// FIXME: This is only used by an ASSERT in StyleResolver. Remove?
bool fontDirty() const { return m_fontDirty; }
+ static FontDescription::GenericFamilyType initialGenericFamily() { return FontDescription::NoFamily; }
+ static TextRenderingMode initialTextRendering() { return AutoTextRendering; }
+ static FontVariant initialVariant() { return FontVariantNormal; }
+ static FontStyle initialStyle() { return FontStyleNormal; }
+ static FontDescription::Kerning initialKerning() { return FontDescription::AutoKerning; }
+ static FontSmoothingMode initialFontSmoothing() { return AutoSmoothing; }
+
friend class FontDescriptionChangeScope;
+
private:
// FIXME: "size" arg should be first for consistency with other similar functions.
@@ -96,12 +107,12 @@ private:
void checkForOrientationChange(RenderStyle*);
// This function fixes up the default font size if it detects that the current generic font family has changed. -dwh
void checkForGenericFamilyChange(RenderStyle*, const RenderStyle* parentStyle);
- void checkForZoomChange(RenderStyle*, const RenderStyle* parentStyle);
+ void updateComputedSize(RenderStyle*, const RenderStyle* parentStyle);
float getComputedSizeFromSpecifiedSize(FontDescription&, float effectiveZoom, float specifiedSize);
const Document* m_document;
- bool m_useSVGZoomRules;
+ bool m_fontSizehasViewportUnits;
// FIXME: This member is here on a short-term lease. The plan is to remove
// any notion of RenderStyle from here, allowing FontBuilder to build Font objects
// directly, rather than as a byproduct of calling RenderStyle::setFontDescription.
@@ -115,6 +126,8 @@ private:
// is changed, FontBuilder tracks the need to update
// style->font() with this bool.
bool m_fontDirty;
+
+ friend class FontBuilderTest;
};
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilderTest.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilderTest.cpp
new file mode 100644
index 00000000000..231dc93627a
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/FontBuilderTest.cpp
@@ -0,0 +1,26 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "core/css/resolver/FontBuilder.h"
+
+#include <gtest/gtest.h>
+
+namespace WebCore {
+
+class FontBuilderTest : public ::testing::Test {
+protected:
+ RenderStyle* getStyle(const FontBuilder& builder)
+ {
+ return builder.m_style;
+ }
+};
+
+TEST_F(FontBuilderTest, StylePointerInitialisation)
+{
+ FontBuilder builder;
+ EXPECT_EQ(0, getStyle(builder));
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/MatchRequest.h b/chromium/third_party/WebKit/Source/core/css/resolver/MatchRequest.h
index df0207f4038..04c587eb623 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/MatchRequest.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/MatchRequest.h
@@ -23,6 +23,7 @@
#ifndef MatchRequest_h
#define MatchRequest_h
+#include "core/css/CSSStyleSheet.h"
#include "core/css/RuleSet.h"
namespace WebCore {
@@ -30,11 +31,13 @@ namespace WebCore {
class ContainerNode;
class MatchRequest {
+ STACK_ALLOCATED();
public:
- MatchRequest(RuleSet* ruleSet, bool includeEmptyRules = false, const ContainerNode* scope = 0, bool elementApplyAuthorStyles = true, unsigned styleSheetIndex = 0)
+ MatchRequest(RuleSet* ruleSet, bool includeEmptyRules = false, const ContainerNode* scope = 0, const CSSStyleSheet* cssSheet = 0, bool elementApplyAuthorStyles = true, unsigned styleSheetIndex = 0)
: ruleSet(ruleSet)
, includeEmptyRules(includeEmptyRules)
, scope(scope)
+ , styleSheet(cssSheet)
, elementApplyAuthorStyles(elementApplyAuthorStyles)
, styleSheetIndex(styleSheetIndex)
{
@@ -43,9 +46,10 @@ public:
ruleSet->compactRulesIfNeeded();
}
- const RuleSet* ruleSet;
+ RawPtrWillBeMember<const RuleSet> ruleSet;
const bool includeEmptyRules;
- const ContainerNode* scope;
+ RawPtrWillBeMember<const ContainerNode> scope;
+ RawPtrWillBeMember<const CSSStyleSheet> styleSheet;
const bool elementApplyAuthorStyles;
const unsigned styleSheetIndex;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/MatchResult.h b/chromium/third_party/WebKit/Source/core/css/resolver/MatchResult.h
index bbcae30bdb5..25d9b91900a 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/MatchResult.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/MatchResult.h
@@ -67,10 +67,12 @@ struct MatchedProperties {
};
};
-struct MatchResult {
+class MatchResult {
+ STACK_ALLOCATED();
+public:
MatchResult() : isCacheable(true) { }
Vector<MatchedProperties, 64> matchedProperties;
- Vector<StyleRule*, 64> matchedRules;
+ WillBeHeapVector<RawPtrWillBeMember<StyleRule>, 64> matchedRules;
MatchRanges ranges;
bool isCacheable;
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.cpp
index d3c222a1f1e..469fa3c9c2f 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.cpp
@@ -37,7 +37,7 @@ namespace WebCore {
void CachedMatchedProperties::set(const RenderStyle* style, const RenderStyle* parentStyle, const MatchResult& matchResult)
{
- matchedProperties.append(matchResult.matchedProperties);
+ matchedProperties.appendVector(matchResult.matchedProperties);
ranges = matchResult.ranges;
// Note that we don't cache the original RenderStyle instance. It may be further modified.
@@ -49,8 +49,8 @@ void CachedMatchedProperties::set(const RenderStyle* style, const RenderStyle* p
void CachedMatchedProperties::clear()
{
matchedProperties.clear();
- renderStyle = 0;
- parentRenderStyle = 0;
+ renderStyle = nullptr;
+ parentRenderStyle = nullptr;
}
MatchedPropertiesCache::MatchedPropertiesCache()
@@ -89,15 +89,15 @@ void MatchedPropertiesCache::add(const RenderStyle* style, const RenderStyle* pa
if (++m_additionsSinceLastSweep >= maxAdditionsBetweenSweeps
&& !m_sweepTimer.isActive()) {
static const unsigned sweepTimeInSeconds = 60;
- m_sweepTimer.startOneShot(sweepTimeInSeconds);
+ m_sweepTimer.startOneShot(sweepTimeInSeconds, FROM_HERE);
}
ASSERT(hash);
Cache::AddResult addResult = m_cache.add(hash, nullptr);
if (addResult.isNewEntry)
- addResult.iterator->value = adoptPtr(new CachedMatchedProperties);
+ addResult.storedValue->value = adoptPtr(new CachedMatchedProperties);
- CachedMatchedProperties* cacheItem = addResult.iterator->value.get();
+ CachedMatchedProperties* cacheItem = addResult.storedValue->value.get();
if (!addResult.isNewEntry)
cacheItem->clear();
@@ -109,6 +109,17 @@ void MatchedPropertiesCache::clear()
m_cache.clear();
}
+void MatchedPropertiesCache::clearViewportDependent()
+{
+ Vector<unsigned, 16> toRemove;
+ for (Cache::iterator it = m_cache.begin(); it != m_cache.end(); ++it) {
+ CachedMatchedProperties* cacheItem = it->value.get();
+ if (cacheItem->renderStyle->hasViewportUnits())
+ toRemove.append(it->key);
+ }
+ m_cache.removeAll(toRemove);
+}
+
void MatchedPropertiesCache::sweep(Timer<MatchedPropertiesCache>*)
{
// Look for cache entries containing a style declaration with a single ref and remove them.
@@ -127,9 +138,7 @@ void MatchedPropertiesCache::sweep(Timer<MatchedPropertiesCache>*)
}
}
}
- for (size_t i = 0; i < toRemove.size(); ++i)
- m_cache.remove(toRemove[i]);
-
+ m_cache.removeAll(toRemove);
m_additionsSinceLastSweep = 0;
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.h b/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.h
index 2e5297d5acd..d86bf01f856 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/MatchedPropertiesCache.h
@@ -54,6 +54,7 @@ public:
void add(const RenderStyle*, const RenderStyle* parentStyle, unsigned hash, const MatchResult&);
void clear();
+ void clearViewportDependent();
static bool isCacheable(const Element*, const RenderStyle*, const RenderStyle* parentStyle);
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/MediaQueryResult.h b/chromium/third_party/WebKit/Source/core/css/resolver/MediaQueryResult.h
index 1dc00f42dc3..86adebd50d4 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/MediaQueryResult.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/MediaQueryResult.h
@@ -29,16 +29,38 @@
namespace WebCore {
-class MediaQueryResult : public RefCounted<MediaQueryResult> {
- WTF_MAKE_NONCOPYABLE(MediaQueryResult); WTF_MAKE_FAST_ALLOCATED;
+class MediaQueryResult : public RefCountedWillBeGarbageCollectedFinalized<MediaQueryResult> {
+ WTF_MAKE_NONCOPYABLE(MediaQueryResult); WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
MediaQueryResult(const MediaQueryExp& expr, bool result)
+#if ENABLE(OILPAN)
+ : m_expression(&expr)
+#else
: m_expression(expr)
+#endif
, m_result(result)
{
}
+ void trace(Visitor* visitor) { visitor->trace(m_expression); }
+
+ const MediaQueryExp* expression() const
+ {
+#if ENABLE(OILPAN)
+ return m_expression;
+#else
+ return &m_expression;
+#endif
+ }
+
+ bool result() const { return m_result; }
+
+private:
+#if ENABLE(OILPAN)
+ Member<const MediaQueryExp> m_expression;
+#else
MediaQueryExp m_expression;
+#endif
bool m_result;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.cpp
index 706f5d827ab..7aea947d29f 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.cpp
@@ -27,7 +27,7 @@
#include "config.h"
#include "core/css/resolver/ScopedStyleResolver.h"
-#include "HTMLNames.h"
+#include "core/HTMLNames.h"
#include "core/css/CSSStyleSheet.h"
#include "core/css/PageRuleCollector.h"
#include "core/css/RuleFeature.h"
@@ -49,38 +49,35 @@ ContainerNode* ScopedStyleResolver::scopingNodeFor(Document& document, const CSS
Document* sheetDocument = sheet->ownerDocument();
if (!sheetDocument)
return 0;
- Node* ownerNode = sheet->ownerNode();
- if (!ownerNode || !isHTMLStyleElement(ownerNode))
- return &document;
- HTMLStyleElement* styleElement = toHTMLStyleElement(ownerNode);
- if (!styleElement->scoped()) {
- if (styleElement->isInShadowTree())
- return styleElement->containingShadowRoot();
+ Node* ownerNode = sheet->ownerNode();
+ if (!isHTMLStyleElement(ownerNode))
return &document;
- }
- ContainerNode* parent = styleElement->parentNode();
- if (!parent)
- return 0;
-
- return (parent->isElementNode() || parent->isShadowRoot()) ? parent : 0;
+ HTMLStyleElement& styleElement = toHTMLStyleElement(*ownerNode);
+ if (styleElement.isInShadowTree())
+ return styleElement.containingShadowRoot();
+ return &document;
}
-void ScopedStyleResolver::addRulesFromSheet(StyleSheetContents* sheet, const MediaQueryEvaluator& medium, StyleResolver* resolver)
+void ScopedStyleResolver::addRulesFromSheet(CSSStyleSheet* cssSheet, const MediaQueryEvaluator& medium, StyleResolver* resolver)
{
- m_authorStyleSheets.append(sheet);
+ m_authorStyleSheets.append(cssSheet);
+ StyleSheetContents* sheet = cssSheet->contents();
AddRuleFlags addRuleFlags = resolver->document().securityOrigin()->canRequest(sheet->baseURL()) ? RuleHasDocumentSecurityOrigin : RuleHasNoSpecialState;
const RuleSet& ruleSet = sheet->ensureRuleSet(medium, addRuleFlags);
resolver->addMediaQueryResults(ruleSet.viewportDependentMediaQueryResults());
- resolver->processScopedRules(ruleSet, sheet->baseURL(), &m_scopingNode);
+ resolver->processScopedRules(ruleSet, cssSheet, m_scopingNode);
}
-void ScopedStyleResolver::collectFeaturesTo(RuleFeatureSet& features)
+void ScopedStyleResolver::collectFeaturesTo(RuleFeatureSet& features, HashSet<const StyleSheetContents*>& visitedSharedStyleSheetContents)
{
- for (size_t i = 0; i < m_authorStyleSheets.size(); ++i)
- features.add(m_authorStyleSheets[i]->ruleSet().features());
+ for (size_t i = 0; i < m_authorStyleSheets.size(); ++i) {
+ StyleSheetContents* contents = m_authorStyleSheets[i]->contents();
+ if (contents->hasOneClient() || visitedSharedStyleSheetContents.add(contents).isNewEntry)
+ features.add(contents->ruleSet().features());
+ }
}
void ScopedStyleResolver::resetAuthorStyle()
@@ -89,19 +86,6 @@ void ScopedStyleResolver::resetAuthorStyle()
m_keyframesRuleMap.clear();
}
-bool ScopedStyleResolver::checkRegionStyle(Element* regionElement)
-{
- for (size_t i = 0; i < m_authorStyleSheets.size(); ++i) {
- const RuleSet& ruleSet = m_authorStyleSheets[i]->ruleSet();
- for (unsigned i = 0; i < ruleSet.m_regionSelectorsAndRuleSets.size(); ++i) {
- ASSERT(ruleSet.m_regionSelectorsAndRuleSets.at(i).ruleSet.get());
- if (checkRegionSelector(ruleSet.m_regionSelectorsAndRuleSets.at(i).selector, regionElement))
- return true;
- }
- }
- return false;
-}
-
const StyleRuleKeyframes* ScopedStyleResolver::keyframeStylesForAnimation(const StringImpl* animationName)
{
if (m_keyframesRuleMap.isEmpty())
@@ -114,7 +98,7 @@ const StyleRuleKeyframes* ScopedStyleResolver::keyframeStylesForAnimation(const
return it->value.get();
}
-void ScopedStyleResolver::addKeyframeStyle(PassRefPtr<StyleRuleKeyframes> rule)
+void ScopedStyleResolver::addKeyframeStyle(PassRefPtrWillBeRawPtr<StyleRuleKeyframes> rule)
{
AtomicString s(rule->name());
if (rule->isVendorPrefixed()) {
@@ -136,16 +120,13 @@ void ScopedStyleResolver::collectMatchingAuthorRules(ElementRuleCollector& colle
if (!applyAuthorStyles)
behaviorAtBoundary |= SelectorChecker::ScopeContainsLastMatchedElement;
- if (m_scopingNode.isShadowRoot()) {
- scopingNode = toShadowRoot(m_scopingNode).host();
- behaviorAtBoundary |= SelectorChecker::ScopeIsShadowHost;
- }
+ if (m_scopingNode.isShadowRoot())
+ behaviorAtBoundary |= SelectorChecker::ScopeIsShadowRoot;
RuleRange ruleRange = collector.matchedResult().ranges.authorRuleRange();
for (size_t i = 0; i < m_authorStyleSheets.size(); ++i) {
- MatchRequest matchRequest(&m_authorStyleSheets[i]->ruleSet(), includeEmptyRules, scopingNode, applyAuthorStyles, i);
+ MatchRequest matchRequest(&m_authorStyleSheets[i]->contents()->ruleSet(), includeEmptyRules, scopingNode, m_authorStyleSheets[i], applyAuthorStyles, i);
collector.collectMatchingRules(matchRequest, ruleRange, static_cast<SelectorChecker::BehaviorAtBoundary>(behaviorAtBoundary), cascadeScope, cascadeOrder);
- collector.collectMatchingRulesForRegion(matchRequest, ruleRange, static_cast<SelectorChecker::BehaviorAtBoundary>(behaviorAtBoundary), cascadeScope, cascadeOrder);
}
}
@@ -154,7 +135,7 @@ void ScopedStyleResolver::matchPageRules(PageRuleCollector& collector)
// Only consider the global author RuleSet for @page rules, as per the HTML5 spec.
ASSERT(m_scopingNode.isDocumentNode());
for (size_t i = 0; i < m_authorStyleSheets.size(); ++i)
- collector.matchPageRules(&m_authorStyleSheets[i]->ruleSet());
+ collector.matchPageRules(&m_authorStyleSheets[i]->contents()->ruleSet());
}
void ScopedStyleResolver::collectViewportRulesTo(StyleResolver* resolver) const
@@ -162,7 +143,7 @@ void ScopedStyleResolver::collectViewportRulesTo(StyleResolver* resolver) const
if (!m_scopingNode.isDocumentNode())
return;
for (size_t i = 0; i < m_authorStyleSheets.size(); ++i)
- resolver->viewportStyleResolver()->collectViewportRules(&m_authorStyleSheets[i]->ruleSet(), ViewportStyleResolver::AuthorOrigin);
+ resolver->viewportStyleResolver()->collectViewportRules(&m_authorStyleSheets[i]->contents()->ruleSet(), ViewportStyleResolver::AuthorOrigin);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.h b/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.h
index 7aa1a1a18dd..64e7b7df54a 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleResolver.h
@@ -31,6 +31,7 @@
#include "core/css/RuleSet.h"
#include "core/dom/ContainerNode.h"
#include "wtf/HashMap.h"
+#include "wtf/HashSet.h"
#include "wtf/OwnPtr.h"
#include "wtf/PassOwnPtr.h"
@@ -38,7 +39,6 @@ namespace WebCore {
class MediaQueryEvaluator;
class PageRuleCollector;
-class ShadowRoot;
class StyleSheetContents;
// This class selects a RenderStyle for a given element based on a collection of stylesheets.
@@ -55,28 +55,25 @@ public:
ScopedStyleResolver* parent() { return m_parent; }
public:
- bool checkRegionStyle(Element*);
const StyleRuleKeyframes* keyframeStylesForAnimation(const StringImpl* animationName);
- void addKeyframeStyle(PassRefPtr<StyleRuleKeyframes>);
+ void addKeyframeStyle(PassRefPtrWillBeRawPtr<StyleRuleKeyframes>);
void collectMatchingAuthorRules(ElementRuleCollector&, bool includeEmptyRules, bool applyAuthorStyles, CascadeScope, CascadeOrder = ignoreCascadeOrder);
void matchPageRules(PageRuleCollector&);
- void addRulesFromSheet(StyleSheetContents*, const MediaQueryEvaluator&, StyleResolver*);
- void collectFeaturesTo(RuleFeatureSet&);
+ void addRulesFromSheet(CSSStyleSheet*, const MediaQueryEvaluator&, StyleResolver*);
+ void collectFeaturesTo(RuleFeatureSet&, HashSet<const StyleSheetContents*>& visitedSharedStyleSheetContents);
void resetAuthorStyle();
void collectViewportRulesTo(StyleResolver*) const;
private:
explicit ScopedStyleResolver(ContainerNode& scopingNode) : m_scopingNode(scopingNode), m_parent(0) { }
- RuleSet* ensureAuthorStyle();
-
ContainerNode& m_scopingNode;
ScopedStyleResolver* m_parent;
- Vector<StyleSheetContents*> m_authorStyleSheets;
+ WillBePersistentHeapVector<RawPtrWillBeMember<CSSStyleSheet> > m_authorStyleSheets;
- typedef HashMap<const StringImpl*, RefPtr<StyleRuleKeyframes> > KeyframesRuleMap;
+ typedef WillBePersistentHeapHashMap<const StringImpl*, RefPtrWillBeMember<StyleRuleKeyframes> > KeyframesRuleMap;
KeyframesRuleMap m_keyframesRuleMap;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleTree.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleTree.cpp
index 729faf15e8f..3b27951217e 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleTree.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ScopedStyleTree.cpp
@@ -34,6 +34,8 @@
namespace WebCore {
+class StyleSheetContents;
+
ScopedStyleResolver* ScopedStyleTree::ensureScopedStyleResolver(ContainerNode& scopingNode)
{
bool isNewEntry;
@@ -45,8 +47,7 @@ ScopedStyleResolver* ScopedStyleTree::ensureScopedStyleResolver(ContainerNode& s
ScopedStyleResolver* ScopedStyleTree::scopedStyleResolverFor(const ContainerNode& scopingNode)
{
- if (!scopingNode.hasScopedHTMLStyleChild()
- && !isShadowHost(&scopingNode)
+ if (!isShadowHost(&scopingNode)
&& !scopingNode.isDocumentNode()
&& !scopingNode.isShadowRoot())
return 0;
@@ -58,12 +59,12 @@ ScopedStyleResolver* ScopedStyleTree::addScopedStyleResolver(ContainerNode& scop
HashMap<const ContainerNode*, OwnPtr<ScopedStyleResolver> >::AddResult addResult = m_authorStyles.add(&scopingNode, nullptr);
if (addResult.isNewEntry) {
- addResult.iterator->value = ScopedStyleResolver::create(scopingNode);
+ addResult.storedValue->value = ScopedStyleResolver::create(scopingNode);
if (scopingNode.isDocumentNode())
- m_scopedResolverForDocument = addResult.iterator->value.get();
+ m_scopedResolverForDocument = addResult.storedValue->value.get();
}
isNewEntry = addResult.isNewEntry;
- return addResult.iterator->value.get();
+ return addResult.storedValue->value.get();
}
void ScopedStyleTree::setupScopedStylesTree(ScopedStyleResolver* target)
@@ -123,12 +124,10 @@ void ScopedStyleTree::collectScopedResolversForHostedShadowTrees(const Element*
// Adding scoped resolver for active shadow roots for shadow host styling.
for (ShadowRoot* shadowRoot = shadow->youngestShadowRoot(); shadowRoot; shadowRoot = shadowRoot->olderShadowRoot()) {
- if (shadowRoot->hasScopedHTMLStyleChild()) {
+ if (shadowRoot->numberOfStyles() > 0) {
if (ScopedStyleResolver* resolver = scopedStyleResolverFor(*shadowRoot))
resolvers.append(resolver);
}
- if (!shadowRoot->containsShadowElements())
- break;
}
}
@@ -138,6 +137,10 @@ void ScopedStyleTree::resolveScopedKeyframesRules(const Element* element, Vector
TreeScope& treeScope = element->treeScope();
bool applyAuthorStyles = treeScope.applyAuthorStyles();
+ // Add resolvers for shadow roots hosted by the given element.
+ collectScopedResolversForHostedShadowTrees(element, resolvers);
+
+ // Add resolvers while walking up DOM tree from the given element.
for (ScopedStyleResolver* scopedResolver = scopedResolverFor(element); scopedResolver; scopedResolver = scopedResolver->parent()) {
if (scopedResolver->treeScope() == treeScope || (applyAuthorStyles && scopedResolver->treeScope() == document))
resolvers.append(scopedResolver);
@@ -187,8 +190,9 @@ void ScopedStyleTree::popStyleCache(const ContainerNode& scopingNode)
void ScopedStyleTree::collectFeaturesTo(RuleFeatureSet& features)
{
+ HashSet<const StyleSheetContents*> visitedSharedStyleSheetContents;
for (HashMap<const ContainerNode*, OwnPtr<ScopedStyleResolver> >::iterator it = m_authorStyles.begin(); it != m_authorStyles.end(); ++it)
- it->value->collectFeaturesTo(features);
+ it->value->collectFeaturesTo(features, visitedSharedStyleSheetContents);
}
inline void ScopedStyleTree::reparentNodes(const ScopedStyleResolver* oldParent, ScopedStyleResolver* newParent)
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.cpp
index 92890d6c3af..4589e71bf6f 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.cpp
@@ -29,8 +29,8 @@
#include "config.h"
#include "core/css/resolver/SharedStyleFinder.h"
-#include "HTMLNames.h"
-#include "XMLNames.h"
+#include "core/HTMLNames.h"
+#include "core/XMLNames.h"
#include "core/css/resolver/StyleResolver.h"
#include "core/css/resolver/StyleResolverStats.h"
#include "core/dom/ContainerNode.h"
@@ -42,9 +42,11 @@
#include "core/dom/QualifiedName.h"
#include "core/dom/SpaceSplitString.h"
#include "core/dom/shadow/ElementShadow.h"
+#include "core/dom/shadow/InsertionPoint.h"
#include "core/html/HTMLElement.h"
#include "core/html/HTMLInputElement.h"
#include "core/html/HTMLOptGroupElement.h"
+#include "core/html/HTMLOptionElement.h"
#include "core/rendering/style/RenderStyle.h"
#include "core/svg/SVGElement.h"
#include "wtf/HashSet.h"
@@ -56,7 +58,7 @@ using namespace HTMLNames;
bool SharedStyleFinder::canShareStyleWithControl(Element& candidate) const
{
- if (!candidate.hasTagName(inputTag) || !element().hasTagName(inputTag))
+ if (!isHTMLInputElement(candidate) || !isHTMLInputElement(element()))
return false;
HTMLInputElement& candidateInput = toHTMLInputElement(candidate);
@@ -100,7 +102,7 @@ bool SharedStyleFinder::classNamesAffectedByRules(const SpaceSplitString& classN
{
unsigned count = classNames.size();
for (unsigned i = 0; i < count; ++i) {
- if (m_features.classesInRules.contains(classNames[i]))
+ if (m_features.hasSelectorForClass(classNames[i]))
return true;
}
return false;
@@ -121,7 +123,7 @@ bool SharedStyleFinder::sharingCandidateHasIdenticalStyleAffectingAttributes(Ele
if (element().fastGetAttribute(langAttr) != candidate.fastGetAttribute(langAttr))
return false;
- // These two checks must be here since RuleSet has a specail case to allow style sharing between elements
+ // These two checks must be here since RuleSet has a special case to allow style sharing between elements
// with type and readonly attributes whereas other attribute selectors prevent sharing.
if (typeAttributeValue(element()) != typeAttributeValue(candidate))
return false;
@@ -149,11 +151,46 @@ bool SharedStyleFinder::sharingCandidateHasIdenticalStyleAffectingAttributes(Ele
// FIXME: Consider removing this, it's unlikely we'll have so many progress elements
// that sharing the style makes sense. Instead we should just not support style sharing
// for them.
- if (element().hasTagName(progressTag)) {
+ if (isHTMLProgressElement(element())) {
if (element().shouldAppearIndeterminate() != candidate.shouldAppearIndeterminate())
return false;
}
+ if (isHTMLOptGroupElement(element()) || isHTMLOptionElement(element())) {
+ if (element().isDisabledFormControl() != candidate.isDisabledFormControl())
+ return false;
+ if (isHTMLOptionElement(element()) && toHTMLOptionElement(element()).selected() != toHTMLOptionElement(candidate).selected())
+ return false;
+ }
+
+ return true;
+}
+
+bool SharedStyleFinder::sharingCandidateCanShareHostStyles(Element& candidate) const
+{
+ const ElementShadow* elementShadow = element().shadow();
+ const ElementShadow* candidateShadow = candidate.shadow();
+
+ if (!elementShadow && !candidateShadow)
+ return true;
+
+ if (static_cast<bool>(elementShadow) != static_cast<bool>(candidateShadow))
+ return false;
+
+ return elementShadow->hasSameStyles(candidateShadow);
+}
+
+bool SharedStyleFinder::sharingCandidateDistributedToSameInsertionPoint(Element& candidate) const
+{
+ WillBeHeapVector<RawPtrWillBeMember<InsertionPoint>, 8> insertionPoints, candidateInsertionPoints;
+ collectDestinationInsertionPoints(element(), insertionPoints);
+ collectDestinationInsertionPoints(candidate, candidateInsertionPoints);
+ if (insertionPoints.size() != candidateInsertionPoints.size())
+ return false;
+ for (size_t i = 0; i < insertionPoints.size(); ++i) {
+ if (insertionPoints[i] != candidateInsertionPoints[i])
+ return false;
+ }
return true;
}
@@ -161,7 +198,7 @@ bool SharedStyleFinder::canShareStyleWithElement(Element& candidate) const
{
if (element() == candidate)
return false;
- Element* parent = candidate.parentElement();
+ Element* parent = candidate.parentOrShadowHostElement();
RenderStyle* style = candidate.renderStyle();
if (!style)
return false;
@@ -169,7 +206,7 @@ bool SharedStyleFinder::canShareStyleWithElement(Element& candidate) const
return false;
if (!parent)
return false;
- if (element().parentElement()->renderStyle() != parent->renderStyle())
+ if (element().parentOrShadowHostElement()->renderStyle() != parent->renderStyle())
return false;
if (candidate.tagQName() != element().tagQName())
return false;
@@ -181,26 +218,20 @@ bool SharedStyleFinder::canShareStyleWithElement(Element& candidate) const
return false;
if (candidate.isLink() != element().isLink())
return false;
- if (candidate.hovered() != element().hovered())
- return false;
- if (candidate.active() != element().active())
- return false;
- if (candidate.focused() != element().focused())
- return false;
if (candidate.shadowPseudoId() != element().shadowPseudoId())
return false;
- if (candidate == document().cssTarget())
- return false;
if (!sharingCandidateHasIdenticalStyleAffectingAttributes(candidate))
return false;
if (candidate.additionalPresentationAttributeStyle() != element().additionalPresentationAttributeStyle())
return false;
- if (candidate.hasID() && m_features.idsInRules.contains(candidate.idForStyleResolution()))
+ if (candidate.hasID() && m_features.hasSelectorForId(candidate.idForStyleResolution()))
return false;
- if (candidate.hasScopedHTMLStyleChild())
+ if (!sharingCandidateCanShareHostStyles(candidate))
+ return false;
+ if (!sharingCandidateDistributedToSameInsertionPoint(candidate))
+ return false;
+ if (candidate.isInTopLayer() != element().isInTopLayer())
return false;
- if (candidate.shadow() && candidate.shadow()->containsActiveStyles())
- return 0;
bool isControl = candidate.isFormControlElement();
@@ -220,16 +251,14 @@ bool SharedStyleFinder::canShareStyleWithElement(Element& candidate) const
if (candidate.isUnresolvedCustomElement() != element().isUnresolvedCustomElement())
return false;
- if (element().parentElement() != parent) {
+ if (element().parentOrShadowHostElement() != parent) {
if (!parent->isStyledElement())
return false;
- if (parent->hasScopedHTMLStyleChild())
- return false;
if (parent->inlineStyle())
return false;
if (parent->isSVGElement() && toSVGElement(parent)->animatedSMILStyleProperties())
return false;
- if (parent->hasID() && m_features.idsInRules.contains(parent->idForStyleResolution()))
+ if (parent->hasID() && m_features.hasSelectorForId(parent->idForStyleResolution()))
return false;
if (!parent->childrenSupportStyleSharing())
return false;
@@ -304,7 +333,7 @@ RenderStyle* SharedStyleFinder::findSharedStyle()
}
// Tracking child index requires unique style for each node. This may get set by the sibling rule match above.
- if (!element().parentElement()->childrenSupportStyleSharing()) {
+ if (!element().parentElementOrShadowRoot()->childrenSupportStyleSharing()) {
INCREMENT_STYLE_STATS_COUNTER(m_styleResolver, sharedStyleRejectedByParent);
return 0;
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.h b/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.h
index e65c5c07cd0..5af9a95711f 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/SharedStyleFinder.h
@@ -36,6 +36,7 @@ class SpaceSplitString;
class StyleResolver;
class SharedStyleFinder {
+ STACK_ALLOCATED();
public:
// RuleSets are passed non-const as the act of matching against them can cause them
// to be compacted. :(
@@ -63,6 +64,8 @@ private:
bool canShareStyleWithElement(Element& candidate) const;
bool canShareStyleWithControl(Element& candidate) const;
bool sharingCandidateHasIdenticalStyleAffectingAttributes(Element& candidate) const;
+ bool sharingCandidateCanShareHostStyles(Element& candidate) const;
+ bool sharingCandidateDistributedToSameInsertionPoint(Element& candidate) const;
bool matchesRuleSet(RuleSet*);
Element& element() const { return *m_context.element(); }
@@ -70,8 +73,8 @@ private:
bool m_elementAffectedByClassRules;
const RuleFeatureSet& m_features;
- RuleSet* m_siblingRuleSet;
- RuleSet* m_uncommonAttributeRuleSet;
+ RawPtrWillBeMember<RuleSet> m_siblingRuleSet;
+ RawPtrWillBeMember<RuleSet> m_uncommonAttributeRuleSet;
StyleResolver& m_styleResolver;
const ElementResolveContext& m_context;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.cpp
index 4b1fe76c082..060f53f8eb0 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.cpp
@@ -29,24 +29,26 @@
#include "config.h"
#include "core/css/resolver/StyleAdjuster.h"
-#include "HTMLNames.h"
-#include "SVGNames.h"
+#include "core/HTMLNames.h"
+#include "core/SVGNames.h"
#include "core/dom/ContainerNode.h"
#include "core/dom/Document.h"
#include "core/dom/Element.h"
-#include "core/html/HTMLHtmlElement.h"
+#include "core/dom/NodeRenderStyle.h"
#include "core/html/HTMLIFrameElement.h"
#include "core/html/HTMLInputElement.h"
-#include "core/html/HTMLTableElement.h"
+#include "core/html/HTMLPlugInElement.h"
+#include "core/html/HTMLTableCellElement.h"
#include "core/html/HTMLTextAreaElement.h"
#include "core/frame/FrameView.h"
#include "core/frame/Settings.h"
-#include "core/rendering/Pagination.h"
#include "core/rendering/RenderTheme.h"
#include "core/rendering/style/GridPosition.h"
#include "core/rendering/style/RenderStyle.h"
#include "core/rendering/style/RenderStyleConstants.h"
+#include "core/svg/SVGSVGElement.h"
#include "platform/Length.h"
+#include "platform/transforms/TransformOperations.h"
#include "wtf/Assertions.h"
namespace WebCore {
@@ -161,63 +163,44 @@ static bool parentStyleForcesZIndexToCreateStackingContext(const RenderStyle* pa
return isDisplayFlexibleBox(parentStyle->display()) || isDisplayGridBox(parentStyle->display());
}
-void StyleAdjuster::adjustRenderStyle(RenderStyle* style, RenderStyle* parentStyle, Element *e)
+static bool hasWillChangeThatCreatesStackingContext(const RenderStyle* style)
{
- ASSERT(parentStyle);
-
- // Cache our original display.
- style->setOriginalDisplay(style->display());
-
- if (style->display() != NONE) {
- // If we have a <td> that specifies a float property, in quirks mode we just drop the float
- // property.
- // Sites also commonly use display:inline/block on <td>s and <table>s. In quirks mode we force
- // these tags to retain their display types.
- if (m_useQuirksModeStyles && e) {
- if (e->hasTagName(tdTag)) {
- style->setDisplay(TABLE_CELL);
- style->setFloating(NoFloat);
- } else if (isHTMLTableElement(e)) {
- style->setDisplay(style->isDisplayInlineType() ? INLINE_TABLE : TABLE);
- }
- }
-
- if (e && (e->hasTagName(tdTag) || e->hasTagName(thTag))) {
- if (style->whiteSpace() == KHTML_NOWRAP) {
- // Figure out if we are really nowrapping or if we should just
- // use normal instead. If the width of the cell is fixed, then
- // we don't actually use NOWRAP.
- if (style->width().isFixed())
- style->setWhiteSpace(NORMAL);
- else
- style->setWhiteSpace(NOWRAP);
- }
- }
-
- // Tables never support the -webkit-* values for text-align and will reset back to the default.
- if (e && isHTMLTableElement(e) && (style->textAlign() == WEBKIT_LEFT || style->textAlign() == WEBKIT_CENTER || style->textAlign() == WEBKIT_RIGHT))
- style->setTextAlign(TASTART);
-
- // Frames and framesets never honor position:relative or position:absolute. This is necessary to
- // fix a crash where a site tries to position these objects. They also never honor display.
- if (e && (e->hasTagName(frameTag) || e->hasTagName(framesetTag))) {
- style->setPosition(StaticPosition);
- style->setDisplay(BLOCK);
- }
-
- // Ruby text does not support float or position. This might change with evolution of the specification.
- if (e && e->hasTagName(rtTag)) {
- style->setPosition(StaticPosition);
- style->setFloating(NoFloat);
+ for (size_t i = 0; i < style->willChangeProperties().size(); ++i) {
+ switch (style->willChangeProperties()[i]) {
+ case CSSPropertyOpacity:
+ case CSSPropertyTransform:
+ case CSSPropertyWebkitTransform:
+ case CSSPropertyTransformStyle:
+ case CSSPropertyWebkitTransformStyle:
+ case CSSPropertyPerspective:
+ case CSSPropertyWebkitPerspective:
+ case CSSPropertyWebkitMask:
+ case CSSPropertyWebkitMaskBoxImage:
+ case CSSPropertyWebkitClipPath:
+ case CSSPropertyWebkitBoxReflect:
+ case CSSPropertyWebkitFilter:
+ case CSSPropertyZIndex:
+ case CSSPropertyPosition:
+ return true;
+ case CSSPropertyMixBlendMode:
+ case CSSPropertyIsolation:
+ if (RuntimeEnabledFeatures::cssCompositingEnabled())
+ return true;
+ break;
+ default:
+ break;
}
+ }
+ return false;
+}
- // FIXME: We shouldn't be overriding start/-webkit-auto like this. Do it in html.css instead.
- // Table headers with a text-align of -webkit-auto will change the text-align to center.
- if (e && e->hasTagName(thTag) && style->textAlign() == TASTART)
- style->setTextAlign(CENTER);
+void StyleAdjuster::adjustRenderStyle(RenderStyle* style, RenderStyle* parentStyle, Element *e, const CachedUAStyle* cachedUAStyle)
+{
+ ASSERT(parentStyle);
- if (e && e->hasTagName(legendTag))
- style->setDisplay(BLOCK);
+ if (style->display() != NONE) {
+ if (e)
+ adjustStyleForTagName(style, parentStyle, *e);
// Per the spec, position 'static' and 'relative' in the top layer compute to 'absolute'.
if (isInTopLayer(e, style) && (style->position() == StaticPosition || style->position() == RelativePosition))
@@ -227,36 +210,7 @@ void StyleAdjuster::adjustRenderStyle(RenderStyle* style, RenderStyle* parentSty
if (style->hasOutOfFlowPosition() || style->isFloating() || (e && e->document().documentElement() == e))
style->setDisplay(equivalentBlockDisplay(style->display(), style->isFloating(), !m_useQuirksModeStyles));
- // FIXME: Don't support this mutation for pseudo styles like first-letter or first-line, since it's not completely
- // clear how that should work.
- if (style->display() == INLINE && style->styleType() == NOPSEUDO && style->writingMode() != parentStyle->writingMode())
- style->setDisplay(INLINE_BLOCK);
-
- // After performing the display mutation, check table rows. We do not honor position:relative or position:sticky on
- // table rows or cells. This has been established for position:relative in CSS2.1 (and caused a crash in containingBlock()
- // on some sites).
- if ((style->display() == TABLE_HEADER_GROUP || style->display() == TABLE_ROW_GROUP
- || style->display() == TABLE_FOOTER_GROUP || style->display() == TABLE_ROW)
- && style->hasInFlowPosition())
- style->setPosition(StaticPosition);
-
- // writing-mode does not apply to table row groups, table column groups, table rows, and table columns.
- // FIXME: Table cells should be allowed to be perpendicular or flipped with respect to the table, though.
- if (style->display() == TABLE_COLUMN || style->display() == TABLE_COLUMN_GROUP || style->display() == TABLE_FOOTER_GROUP
- || style->display() == TABLE_HEADER_GROUP || style->display() == TABLE_ROW || style->display() == TABLE_ROW_GROUP
- || style->display() == TABLE_CELL)
- style->setWritingMode(parentStyle->writingMode());
-
- // FIXME: Since we don't support block-flow on flexible boxes yet, disallow setting
- // of block-flow to anything other than TopToBottomWritingMode.
- // https://bugs.webkit.org/show_bug.cgi?id=46418 - Flexible box support.
- if (style->writingMode() != TopToBottomWritingMode && (style->display() == BOX || style->display() == INLINE_BOX))
- style->setWritingMode(TopToBottomWritingMode);
-
- if (isDisplayFlexibleBox(parentStyle->display()) || isDisplayGridBox(parentStyle->display())) {
- style->setFloating(NoFloat);
- style->setDisplay(equivalentBlockDisplay(style->display(), style->isFloating(), !m_useQuirksModeStyles));
- }
+ adjustStyleForDisplay(style, parentStyle);
}
// Make sure our z-index value is only applied if the object is positioned.
@@ -276,80 +230,36 @@ void StyleAdjuster::adjustRenderStyle(RenderStyle* style, RenderStyle* parentSty
|| style->hasBlendMode()
|| style->hasIsolation()
|| style->position() == StickyPosition
- || (style->position() == FixedPosition && e && e->document().settings() && e->document().settings()->fixedPositionCreatesStackingContext())
+ || style->position() == FixedPosition
|| isInTopLayer(e, style)
- || style->hasFlowFrom()
- ))
+ || hasWillChangeThatCreatesStackingContext(style)))
style->setZIndex(0);
- // Textarea considers overflow visible as auto.
- if (e && isHTMLTextAreaElement(e)) {
- style->setOverflowX(style->overflowX() == OVISIBLE ? OAUTO : style->overflowX());
- style->setOverflowY(style->overflowY() == OVISIBLE ? OAUTO : style->overflowY());
- }
-
- // For now, <marquee> requires an overflow clip to work properly.
- if (e && e->hasTagName(marqueeTag)) {
- style->setOverflowX(OHIDDEN);
- style->setOverflowY(OHIDDEN);
+ // will-change:transform should result in the same rendering behavior as having a transform,
+ // including the creation of a containing block for fixed position descendants.
+ if (!style->hasTransform() && (style->willChangeProperties().contains(CSSPropertyWebkitTransform) || style->willChangeProperties().contains(CSSPropertyTransform))) {
+ bool makeIdentity = true;
+ style->setTransform(TransformOperations(makeIdentity));
}
if (doesNotInheritTextDecoration(style, e))
- style->setTextDecorationsInEffect(style->textDecoration());
- else
- style->addToTextDecorationsInEffect(style->textDecoration());
+ style->clearAppliedTextDecorations();
- // If either overflow value is not visible, change to auto.
- if (style->overflowX() == OVISIBLE && style->overflowY() != OVISIBLE) {
- // FIXME: Once we implement pagination controls, overflow-x should default to hidden
- // if overflow-y is set to -webkit-paged-x or -webkit-page-y. For now, we'll let it
- // default to auto so we can at least scroll through the pages.
- style->setOverflowX(OAUTO);
- } else if (style->overflowY() == OVISIBLE && style->overflowX() != OVISIBLE) {
- style->setOverflowY(OAUTO);
- }
+ style->applyTextDecorations();
- // Call setStylesForPaginationMode() if a pagination mode is set for any non-root elements. If these
- // styles are specified on a root element, then they will be incorporated in
- // StyleAdjuster::styleForDocument().
- if ((style->overflowY() == OPAGEDX || style->overflowY() == OPAGEDY) && !(e && (isHTMLHtmlElement(e) || e->hasTagName(bodyTag))))
- Pagination::setStylesForPaginationMode(WebCore::paginationModeForRenderStyle(style), style);
-
- // Table rows, sections and the table itself will support overflow:hidden and will ignore scroll/auto.
- // FIXME: Eventually table sections will support auto and scroll.
- if (style->display() == TABLE || style->display() == INLINE_TABLE
- || style->display() == TABLE_ROW_GROUP || style->display() == TABLE_ROW) {
- if (style->overflowX() != OVISIBLE && style->overflowX() != OHIDDEN)
- style->setOverflowX(OVISIBLE);
- if (style->overflowY() != OVISIBLE && style->overflowY() != OHIDDEN)
- style->setOverflowY(OVISIBLE);
- }
-
- // Menulists should have visible overflow
- if (style->appearance() == MenulistPart) {
- style->setOverflowX(OVISIBLE);
- style->setOverflowY(OVISIBLE);
- }
+ if (style->overflowX() != OVISIBLE || style->overflowY() != OVISIBLE)
+ adjustOverflow(style);
// Cull out any useless layers and also repeat patterns into additional layers.
style->adjustBackgroundLayers();
style->adjustMaskLayers();
- // Important: Intrinsic margins get added to controls before the theme has adjusted the style, since the theme will
- // alter fonts and heights/widths.
- if (e && e->isFormControlElement() && style->fontSize() >= 11) {
- // Don't apply intrinsic margins to image buttons. The designer knows how big the images are,
- // so we have to treat all image buttons as though they were explicitly sized.
- if (!e->hasTagName(inputTag) || !toHTMLInputElement(e)->isImageButton())
- addIntrinsicMargins(style);
- }
-
// Let the theme also have a crack at adjusting the style.
if (style->hasAppearance())
- RenderTheme::theme().adjustStyle(style, e, m_cachedUAStyle);
+ RenderTheme::theme().adjustStyle(style, e, cachedUAStyle);
- // If we have first-letter pseudo style, do not share this style.
- if (style->hasPseudoStyle(FIRST_LETTER))
+ // If we have first-letter pseudo style, transitions, or animations, do not share this style.
+ if (style->hasPseudoStyle(FIRST_LETTER) || style->transitions() || style->animations())
style->setUnique();
// FIXME: when dropping the -webkit prefix on transform-style, we should also have opacity < 1 cause flattening.
@@ -358,68 +268,186 @@ void StyleAdjuster::adjustRenderStyle(RenderStyle* style, RenderStyle* parentSty
|| style->hasFilter()))
style->setTransformStyle3D(TransformStyle3DFlat);
- // Seamless iframes behave like blocks. Map their display to inline-block when marked inline.
- if (e && e->hasTagName(iframeTag) && style->display() == INLINE && toHTMLIFrameElement(e)->shouldDisplaySeamlessly())
- style->setDisplay(INLINE_BLOCK);
-
- adjustGridItemPosition(style, parentStyle);
-
if (e && e->isSVGElement()) {
- // Spec: http://www.w3.org/TR/SVG/masking.html#OverflowProperty
- if (style->overflowY() == OSCROLL)
- style->setOverflowY(OHIDDEN);
- else if (style->overflowY() == OAUTO)
- style->setOverflowY(OVISIBLE);
-
- if (style->overflowX() == OSCROLL)
- style->setOverflowX(OHIDDEN);
- else if (style->overflowX() == OAUTO)
- style->setOverflowX(OVISIBLE);
-
// Only the root <svg> element in an SVG document fragment tree honors css position
- if (!(e->hasTagName(SVGNames::svgTag) && e->parentNode() && !e->parentNode()->isSVGElement()))
+ if (!(isSVGSVGElement(*e) && e->parentNode() && !e->parentNode()->isSVGElement()))
style->setPosition(RenderStyle::initialPosition());
- // RenderSVGRoot handles zooming for the whole SVG subtree, so foreignObject content should
- // not be scaled again.
- if (e->hasTagName(SVGNames::foreignObjectTag))
- style->setEffectiveZoom(RenderStyle::initialZoom());
-
// SVG text layout code expects us to be a block-level style element.
- if ((e->hasTagName(SVGNames::foreignObjectTag) || e->hasTagName(SVGNames::textTag)) && style->isDisplayInlineType())
+ if ((isSVGForeignObjectElement(*e) || isSVGTextElement(*e)) && style->isDisplayInlineType())
style->setDisplay(BLOCK);
}
+
+ if (e && e->renderStyle() && e->renderStyle()->textAutosizingMultiplier() != 1) {
+ // Preserve the text autosizing multiplier on style recalc.
+ // (The autosizer will update it during layout if it needs to be changed.)
+ style->setTextAutosizingMultiplier(e->renderStyle()->textAutosizingMultiplier());
+ style->setUnique();
+ }
+}
+
+void StyleAdjuster::adjustStyleForTagName(RenderStyle* style, RenderStyle* parentStyle, Element& element)
+{
+ // <div> and <span> are the most common elements on the web, we skip all the work for them.
+ if (isHTMLDivElement(element) || isHTMLSpanElement(element))
+ return;
+
+ if (isHTMLTableCellElement(element)) {
+ // If we have a <td> that specifies a float property, in quirks mode we just drop the float property.
+ // FIXME: Why is this only <td> and not <th>?
+ if (element.hasTagName(tdTag) && m_useQuirksModeStyles) {
+ style->setDisplay(TABLE_CELL);
+ style->setFloating(NoFloat);
+ }
+ // FIXME: We shouldn't be overriding start/-webkit-auto like this. Do it in html.css instead.
+ // Table headers with a text-align of -webkit-auto will change the text-align to center.
+ if (element.hasTagName(thTag) && style->textAlign() == TASTART)
+ style->setTextAlign(CENTER);
+ if (style->whiteSpace() == KHTML_NOWRAP) {
+ // Figure out if we are really nowrapping or if we should just
+ // use normal instead. If the width of the cell is fixed, then
+ // we don't actually use NOWRAP.
+ if (style->width().isFixed())
+ style->setWhiteSpace(NORMAL);
+ else
+ style->setWhiteSpace(NOWRAP);
+ }
+ return;
+ }
+
+ if (isHTMLTableElement(element)) {
+ // Sites commonly use display:inline/block on <td>s and <table>s. In quirks mode we force
+ // these tags to retain their display types.
+ if (m_useQuirksModeStyles)
+ style->setDisplay(style->isDisplayInlineType() ? INLINE_TABLE : TABLE);
+ // Tables never support the -webkit-* values for text-align and will reset back to the default.
+ if (style->textAlign() == WEBKIT_LEFT || style->textAlign() == WEBKIT_CENTER || style->textAlign() == WEBKIT_RIGHT)
+ style->setTextAlign(TASTART);
+ return;
+ }
+
+ if (isHTMLFrameElement(element) || isHTMLFrameSetElement(element)) {
+ // Frames and framesets never honor position:relative or position:absolute. This is necessary to
+ // fix a crash where a site tries to position these objects. They also never honor display.
+ style->setPosition(StaticPosition);
+ style->setDisplay(BLOCK);
+ return;
+ }
+
+ if (isHTMLRTElement(element)) {
+ // Ruby text does not support float or position. This might change with evolution of the specification.
+ style->setPosition(StaticPosition);
+ style->setFloating(NoFloat);
+ return;
+ }
+
+ if (isHTMLLegendElement(element)) {
+ style->setDisplay(BLOCK);
+ return;
+ }
+
+ if (isHTMLMarqueeElement(element)) {
+ // For now, <marquee> requires an overflow clip to work properly.
+ style->setOverflowX(OHIDDEN);
+ style->setOverflowY(OHIDDEN);
+ return;
+ }
+
+ if (element.isFormControlElement()) {
+ if (isHTMLTextAreaElement(element)) {
+ // Textarea considers overflow visible as auto.
+ style->setOverflowX(style->overflowX() == OVISIBLE ? OAUTO : style->overflowX());
+ style->setOverflowY(style->overflowY() == OVISIBLE ? OAUTO : style->overflowY());
+ }
+
+ // Important: Intrinsic margins get added to controls before the theme has adjusted the style,
+ // since the theme will alter fonts and heights/widths.
+ //
+ // Don't apply intrinsic margins to image buttons. The designer knows how big the images are,
+ // so we have to treat all image buttons as though they were explicitly sized.
+ if (style->fontSize() >= 11 && (!isHTMLInputElement(element) || !toHTMLInputElement(element).isImageButton()))
+ addIntrinsicMargins(style);
+ return;
+ }
+
+ if (isHTMLPlugInElement(element)) {
+ style->setRequiresAcceleratedCompositingForExternalReasons(toHTMLPlugInElement(element).shouldAccelerate());
+ return;
+ }
}
-void StyleAdjuster::adjustGridItemPosition(RenderStyle* style, RenderStyle* parentStyle) const
+void StyleAdjuster::adjustOverflow(RenderStyle* style)
{
- const GridPosition& columnStartPosition = style->gridColumnStart();
- const GridPosition& columnEndPosition = style->gridColumnEnd();
- const GridPosition& rowStartPosition = style->gridRowStart();
- const GridPosition& rowEndPosition = style->gridRowEnd();
-
- // If opposing grid-placement properties both specify a grid span, they both compute to ‘auto’.
- if (columnStartPosition.isSpan() && columnEndPosition.isSpan()) {
- style->setGridColumnStart(GridPosition());
- style->setGridColumnEnd(GridPosition());
+ ASSERT(style->overflowX() != OVISIBLE || style->overflowY() != OVISIBLE);
+
+ // If either overflow value is not visible, change to auto.
+ if (style->overflowX() == OVISIBLE && style->overflowY() != OVISIBLE) {
+ // FIXME: Once we implement pagination controls, overflow-x should default to hidden
+ // if overflow-y is set to -webkit-paged-x or -webkit-page-y. For now, we'll let it
+ // default to auto so we can at least scroll through the pages.
+ style->setOverflowX(OAUTO);
+ } else if (style->overflowY() == OVISIBLE && style->overflowX() != OVISIBLE) {
+ style->setOverflowY(OAUTO);
}
- if (rowStartPosition.isSpan() && rowEndPosition.isSpan()) {
- style->setGridRowStart(GridPosition());
- style->setGridRowEnd(GridPosition());
+ // Table rows, sections and the table itself will support overflow:hidden and will ignore scroll/auto.
+ // FIXME: Eventually table sections will support auto and scroll.
+ if (style->display() == TABLE || style->display() == INLINE_TABLE
+ || style->display() == TABLE_ROW_GROUP || style->display() == TABLE_ROW) {
+ if (style->overflowX() != OVISIBLE && style->overflowX() != OHIDDEN)
+ style->setOverflowX(OVISIBLE);
+ if (style->overflowY() != OVISIBLE && style->overflowY() != OHIDDEN)
+ style->setOverflowY(OVISIBLE);
}
- // Unknown named grid area compute to 'auto'.
- const NamedGridAreaMap& map = parentStyle->namedGridArea();
+ // Menulists should have visible overflow
+ if (style->appearance() == MenulistPart) {
+ style->setOverflowX(OVISIBLE);
+ style->setOverflowY(OVISIBLE);
+ }
+}
-#define CLEAR_UNKNOWN_NAMED_AREA(prop, Prop) \
- if (prop.isNamedGridArea() && !map.contains(prop.namedGridLine())) \
- style->setGrid##Prop(GridPosition());
+void StyleAdjuster::adjustStyleForDisplay(RenderStyle* style, RenderStyle* parentStyle)
+{
+ if (style->display() == BLOCK && !style->isFloating())
+ return;
+
+ // FIXME: Don't support this mutation for pseudo styles like first-letter or first-line, since it's not completely
+ // clear how that should work.
+ if (style->display() == INLINE && style->styleType() == NOPSEUDO && style->writingMode() != parentStyle->writingMode())
+ style->setDisplay(INLINE_BLOCK);
- CLEAR_UNKNOWN_NAMED_AREA(columnStartPosition, ColumnStart);
- CLEAR_UNKNOWN_NAMED_AREA(columnEndPosition, ColumnEnd);
- CLEAR_UNKNOWN_NAMED_AREA(rowStartPosition, RowStart);
- CLEAR_UNKNOWN_NAMED_AREA(rowEndPosition, RowEnd);
+ // After performing the display mutation, check table rows. We do not honor position: relative table rows or cells.
+ // This has been established for position: relative in CSS2.1 (and caused a crash in containingBlock()
+ // on some sites).
+ if ((style->display() == TABLE_HEADER_GROUP || style->display() == TABLE_ROW_GROUP
+ || style->display() == TABLE_FOOTER_GROUP || style->display() == TABLE_ROW)
+ && style->position() == RelativePosition)
+ style->setPosition(StaticPosition);
+
+ // Cannot support position: sticky for table columns and column groups because current code is only doing
+ // background painting through columns / column groups
+ if ((style->display() == TABLE_COLUMN_GROUP || style->display() == TABLE_COLUMN)
+ && style->position() == StickyPosition)
+ style->setPosition(StaticPosition);
+
+ // writing-mode does not apply to table row groups, table column groups, table rows, and table columns.
+ // FIXME: Table cells should be allowed to be perpendicular or flipped with respect to the table, though.
+ if (style->display() == TABLE_COLUMN || style->display() == TABLE_COLUMN_GROUP || style->display() == TABLE_FOOTER_GROUP
+ || style->display() == TABLE_HEADER_GROUP || style->display() == TABLE_ROW || style->display() == TABLE_ROW_GROUP
+ || style->display() == TABLE_CELL)
+ style->setWritingMode(parentStyle->writingMode());
+
+ // FIXME: Since we don't support block-flow on flexible boxes yet, disallow setting
+ // of block-flow to anything other than TopToBottomWritingMode.
+ // https://bugs.webkit.org/show_bug.cgi?id=46418 - Flexible box support.
+ if (style->writingMode() != TopToBottomWritingMode && (style->display() == BOX || style->display() == INLINE_BOX))
+ style->setWritingMode(TopToBottomWritingMode);
+
+ if (isDisplayFlexibleBox(parentStyle->display()) || isDisplayGridBox(parentStyle->display())) {
+ style->setFloating(NoFloat);
+ style->setDisplay(equivalentBlockDisplay(style->display(), style->isFloating(), !m_useQuirksModeStyles));
+ }
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.h
index 96e5927bc37..b83ff9b0648 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleAdjuster.h
@@ -22,6 +22,8 @@
#ifndef StyleAdjuster_h
#define StyleAdjuster_h
+#include "platform/heap/Handle.h"
+
namespace WebCore {
class CachedUAStyle;
@@ -32,18 +34,19 @@ class RenderStyle;
// and the web expects that we expose "adjusted" values when
// for those property/element pairs.
class StyleAdjuster {
+ STACK_ALLOCATED();
public:
- StyleAdjuster(const CachedUAStyle& cachedUAStyle, bool useQuirksModeStyles)
- : m_cachedUAStyle(cachedUAStyle)
- , m_useQuirksModeStyles(useQuirksModeStyles)
+ StyleAdjuster(bool useQuirksModeStyles)
+ : m_useQuirksModeStyles(useQuirksModeStyles)
{ }
- void adjustRenderStyle(RenderStyle* styleToAdjust, RenderStyle* parentStyle, Element*);
+ void adjustRenderStyle(RenderStyle* styleToAdjust, RenderStyle* parentStyle, Element*, const CachedUAStyle*);
private:
- void adjustGridItemPosition(RenderStyle*, RenderStyle*) const;
+ void adjustStyleForDisplay(RenderStyle* styleToAdjust, RenderStyle* parentStyle);
+ void adjustStyleForTagName(RenderStyle* styleToAdjust, RenderStyle* parentStyle, Element&);
+ void adjustOverflow(RenderStyle* styleToAdjust);
- const CachedUAStyle& m_cachedUAStyle;
bool m_useQuirksModeStyles;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilder.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilder.h
index 82214e7980b..f3557a2044c 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilder.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilder.h
@@ -31,7 +31,8 @@
#ifndef StyleBuilder_h
#define StyleBuilder_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
+#include "platform/heap/Handle.h"
namespace WebCore {
@@ -41,16 +42,12 @@ class RenderStyle;
class StyleResolverState;
class StyleBuilder {
+ STATIC_ONLY(StyleBuilder);
public:
static void applyProperty(CSSPropertyID, StyleResolverState&, CSSValue*);
- // This function contains the gigantic old switch-statement of properties inherited from
- // StyleResolver. Each property should be migrated over to a new StyleBuilder templated
- // function and removed from this code. Once they're all moved, this function can die.
- static void oldApplyProperty(CSSPropertyID, StyleResolverState&, CSSValue*, bool isInitial, bool isInherit);
-
private:
- static bool applyProperty(CSSPropertyID, StyleResolverState&, CSSValue*, bool isInitial, bool isInherit);
+ static void applyProperty(CSSPropertyID, StyleResolverState&, CSSValue*, bool isInitial, bool isInherit);
};
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
index d3ffb158dce..fe94e10930e 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.cpp
@@ -27,26 +27,210 @@
#include "config.h"
#include "core/css/resolver/StyleBuilderConverter.h"
+#include "core/css/CSSFunctionValue.h"
+#include "core/css/CSSGridLineNamesValue.h"
#include "core/css/CSSPrimitiveValueMappings.h"
+#include "core/css/CSSReflectValue.h"
#include "core/css/CSSShadowValue.h"
#include "core/css/Pair.h"
#include "core/svg/SVGURIReference.h"
namespace WebCore {
-String StyleBuilderConverter::convertFragmentIdentifier(StyleResolverState& state, CSSValue* value)
+namespace {
+
+static GridLength convertGridTrackBreadth(const StyleResolverState& state, CSSPrimitiveValue* primitiveValue)
+{
+ if (primitiveValue->getValueID() == CSSValueMinContent)
+ return Length(MinContent);
+
+ if (primitiveValue->getValueID() == CSSValueMaxContent)
+ return Length(MaxContent);
+
+ // Fractional unit.
+ if (primitiveValue->isFlex())
+ return GridLength(primitiveValue->getDoubleValue());
+
+ return primitiveValue->convertToLength<FixedConversion | PercentConversion | AutoConversion>(state.cssToLengthConversionData());
+}
+
+} // namespace
+
+PassRefPtr<StyleReflection> StyleBuilderConverter::convertBoxReflect(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue()) {
+ ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNone);
+ return RenderStyle::initialBoxReflect();
+ }
+
+ CSSReflectValue* reflectValue = toCSSReflectValue(value);
+ RefPtr<StyleReflection> reflection = StyleReflection::create();
+ reflection->setDirection(*reflectValue->direction());
+ if (reflectValue->offset())
+ reflection->setOffset(reflectValue->offset()->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData()));
+ NinePieceImage mask;
+ mask.setMaskDefaults();
+ state.styleMap().mapNinePieceImage(state.style(), CSSPropertyWebkitBoxReflect, reflectValue->mask(), mask);
+ reflection->setMask(mask);
+
+ return reflection.release();
+}
+
+AtomicString StyleBuilderConverter::convertFragmentIdentifier(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->isURI())
- return SVGURIReference::fragmentIdentifierFromIRIString(primitiveValue->getStringValue(), state.document());
- return String();
+ return SVGURIReference::fragmentIdentifierFromIRIString(primitiveValue->getStringValue(), state.element()->treeScope());
+ return nullAtom;
+}
+
+EGlyphOrientation StyleBuilderConverter::convertGlyphOrientation(StyleResolverState&, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
+ return GO_0DEG;
+
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->primitiveType() != CSSPrimitiveValue::CSS_DEG)
+ return GO_0DEG;
+
+ float angle = fabsf(fmodf(primitiveValue->getFloatValue(), 360.0f));
+
+ if (angle <= 45.0f || angle > 315.0f)
+ return GO_0DEG;
+ if (angle > 45.0f && angle <= 135.0f)
+ return GO_90DEG;
+ if (angle > 135.0f && angle <= 225.0f)
+ return GO_180DEG;
+ return GO_270DEG;
+}
+
+GridPosition StyleBuilderConverter::convertGridPosition(StyleResolverState&, CSSValue* value)
+{
+ // We accept the specification's grammar:
+ // 'auto' | [ <integer> || <custom-ident> ] | [ span && [ <integer> || <custom-ident> ] ] | <custom-ident>
+
+ GridPosition position;
+
+ if (value->isPrimitiveValue()) {
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ // We translate <custom-ident> to <string> during parsing as it
+ // makes handling it more simple.
+ if (primitiveValue->isString()) {
+ position.setNamedGridArea(primitiveValue->getStringValue());
+ return position;
+ }
+
+ ASSERT(primitiveValue->getValueID() == CSSValueAuto);
+ return position;
+ }
+
+ CSSValueList* values = toCSSValueList(value);
+ ASSERT(values->length());
+
+ bool isSpanPosition = false;
+ // The specification makes the <integer> optional, in which case it default to '1'.
+ int gridLineNumber = 1;
+ String gridLineName;
+
+ CSSValueListIterator it = values;
+ CSSPrimitiveValue* currentValue = toCSSPrimitiveValue(it.value());
+ if (currentValue->getValueID() == CSSValueSpan) {
+ isSpanPosition = true;
+ it.advance();
+ currentValue = it.hasMore() ? toCSSPrimitiveValue(it.value()) : 0;
+ }
+
+ if (currentValue && currentValue->isNumber()) {
+ gridLineNumber = currentValue->getIntValue();
+ it.advance();
+ currentValue = it.hasMore() ? toCSSPrimitiveValue(it.value()) : 0;
+ }
+
+ if (currentValue && currentValue->isString()) {
+ gridLineName = currentValue->getStringValue();
+ it.advance();
+ }
+
+ ASSERT(!it.hasMore());
+ if (isSpanPosition)
+ position.setSpanPosition(gridLineNumber, gridLineName);
+ else
+ position.setExplicitPosition(gridLineNumber, gridLineName);
+
+ return position;
+}
+
+GridTrackSize StyleBuilderConverter::convertGridTrackSize(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue())
+ return GridTrackSize(convertGridTrackBreadth(state, toCSSPrimitiveValue(value)));
+
+ CSSFunctionValue* minmaxFunction = toCSSFunctionValue(value);
+ CSSValueList* arguments = minmaxFunction->arguments();
+ ASSERT_WITH_SECURITY_IMPLICATION(arguments->length() == 2);
+ GridLength minTrackBreadth(convertGridTrackBreadth(state, toCSSPrimitiveValue(arguments->itemWithoutBoundsCheck(0))));
+ GridLength maxTrackBreadth(convertGridTrackBreadth(state, toCSSPrimitiveValue(arguments->itemWithoutBoundsCheck(1))));
+ return GridTrackSize(minTrackBreadth, maxTrackBreadth);
+}
+
+bool StyleBuilderConverter::convertGridTrackList(CSSValue* value, Vector<GridTrackSize>& trackSizes, NamedGridLinesMap& namedGridLines, OrderedNamedGridLines& orderedNamedGridLines, StyleResolverState& state)
+{
+ // Handle 'none'.
+ if (value->isPrimitiveValue()) {
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ return primitiveValue->getValueID() == CSSValueNone;
+ }
+
+ if (!value->isValueList())
+ return false;
+
+ size_t currentNamedGridLine = 0;
+ for (CSSValueListIterator i = value; i.hasMore(); i.advance()) {
+ CSSValue* currValue = i.value();
+ if (currValue->isGridLineNamesValue()) {
+ CSSGridLineNamesValue* lineNamesValue = toCSSGridLineNamesValue(currValue);
+ for (CSSValueListIterator j = lineNamesValue; j.hasMore(); j.advance()) {
+ String namedGridLine = toCSSPrimitiveValue(j.value())->getStringValue();
+ NamedGridLinesMap::AddResult result = namedGridLines.add(namedGridLine, Vector<size_t>());
+ result.storedValue->value.append(currentNamedGridLine);
+ OrderedNamedGridLines::AddResult orderedInsertionResult = orderedNamedGridLines.add(currentNamedGridLine, Vector<String>());
+ orderedInsertionResult.storedValue->value.append(namedGridLine);
+ }
+ continue;
+ }
+
+ ++currentNamedGridLine;
+ trackSizes.append(convertGridTrackSize(state, currValue));
+ }
+
+ // The parser should have rejected any <track-list> without any <track-size> as
+ // this is not conformant to the syntax.
+ ASSERT(!trackSizes.isEmpty());
+ return true;
+}
+
+void StyleBuilderConverter::createImplicitNamedGridLinesFromGridArea(const NamedGridAreaMap& namedGridAreas, NamedGridLinesMap& namedGridLines, GridTrackSizingDirection direction)
+{
+ NamedGridAreaMap::const_iterator end = namedGridAreas.end();
+ for (NamedGridAreaMap::const_iterator it = namedGridAreas.begin(); it != end; ++it) {
+ GridSpan areaSpan = direction == ForRows ? it->value.rows : it->value.columns;
+ {
+ NamedGridLinesMap::AddResult startResult = namedGridLines.add(it->key + "-start", Vector<size_t>());
+ startResult.storedValue->value.append(areaSpan.resolvedInitialPosition.toInt());
+ std::sort(startResult.storedValue->value.begin(), startResult.storedValue->value.end());
+ }
+ {
+ NamedGridLinesMap::AddResult endResult = namedGridLines.add(it->key + "-end", Vector<size_t>());
+ endResult.storedValue->value.append(areaSpan.resolvedFinalPosition.toInt() + 1);
+ std::sort(endResult.storedValue->value.begin(), endResult.storedValue->value.end());
+ }
+ }
}
Length StyleBuilderConverter::convertLength(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
Length result = primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData());
- ASSERT(!result.isUndefined());
result.setQuirk(primitiveValue->isQuirkValue());
return result;
}
@@ -55,7 +239,6 @@ Length StyleBuilderConverter::convertLengthOrAuto(StyleResolverState& state, CSS
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
Length result = primitiveValue->convertToLength<FixedConversion | PercentConversion | AutoConversion>(state.cssToLengthConversionData());
- ASSERT(!result.isUndefined());
result.setQuirk(primitiveValue->isQuirkValue());
return result;
}
@@ -103,6 +286,16 @@ LengthPoint StyleBuilderConverter::convertLengthPoint(StyleResolverState& state,
return LengthPoint(x, y);
}
+LineBoxContain StyleBuilderConverter::convertLineBoxContain(StyleResolverState&, CSSValue* value)
+{
+ if (value->isPrimitiveValue()) {
+ ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNone);
+ return LineBoxContainNone;
+ }
+
+ return toCSSLineBoxContainValue(value)->value();
+}
+
float StyleBuilderConverter::convertNumberOrPercentage(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
@@ -112,6 +305,59 @@ float StyleBuilderConverter::convertNumberOrPercentage(StyleResolverState& state
return primitiveValue->getFloatValue() / 100.0f;
}
+EPaintOrder StyleBuilderConverter::convertPaintOrder(StyleResolverState&, CSSValue* cssPaintOrder)
+{
+ if (cssPaintOrder->isValueList()) {
+ int paintOrder = 0;
+ CSSValueListInspector iter(cssPaintOrder);
+ for (size_t i = 0; i < iter.length(); i++) {
+ CSSPrimitiveValue* value = toCSSPrimitiveValue(iter.item(i));
+
+ EPaintOrderType paintOrderType = PT_NONE;
+ switch (value->getValueID()) {
+ case CSSValueFill:
+ paintOrderType = PT_FILL;
+ break;
+ case CSSValueStroke:
+ paintOrderType = PT_STROKE;
+ break;
+ case CSSValueMarkers:
+ paintOrderType = PT_MARKERS;
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+
+ paintOrder |= (paintOrderType << kPaintOrderBitwidth*i);
+ }
+ return (EPaintOrder)paintOrder;
+ }
+
+ return PO_NORMAL;
+}
+
+PassRefPtr<QuotesData> StyleBuilderConverter::convertQuotes(StyleResolverState&, CSSValue* value)
+{
+ if (value->isValueList()) {
+ CSSValueList* list = toCSSValueList(value);
+ RefPtr<QuotesData> quotes = QuotesData::create();
+ for (size_t i = 0; i < list->length(); i += 2) {
+ CSSValue* first = list->itemWithoutBoundsCheck(i);
+ // item() returns null if out of bounds so this is safe.
+ CSSValue* second = list->item(i + 1);
+ if (!second)
+ continue;
+ String startQuote = toCSSPrimitiveValue(first)->getStringValue();
+ String endQuote = toCSSPrimitiveValue(second)->getStringValue();
+ quotes->addPair(std::make_pair(startQuote, endQuote));
+ }
+ return quotes.release();
+ }
+ // FIXME: We should assert we're a primitive value with valueID = CSSValueNone
+ return QuotesData::create();
+}
+
LengthSize StyleBuilderConverter::convertRadius(StyleResolverState& state, CSSValue* value)
{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
@@ -138,20 +384,17 @@ PassRefPtr<ShadowList> StyleBuilderConverter::convertShadow(StyleResolverState&
ShadowDataVector shadows;
for (size_t i = 0; i < shadowCount; ++i) {
const CSSShadowValue* item = toCSSShadowValue(valueList->item(i));
- int x = item->x->computeLength<int>(state.cssToLengthConversionData());
- int y = item->y->computeLength<int>(state.cssToLengthConversionData());
- int blur = item->blur ? item->blur->computeLength<int>(state.cssToLengthConversionData()) : 0;
- int spread = item->spread ? item->spread->computeLength<int>(state.cssToLengthConversionData()) : 0;
+ float x = item->x->computeLength<float>(state.cssToLengthConversionData());
+ float y = item->y->computeLength<float>(state.cssToLengthConversionData());
+ float blur = item->blur ? item->blur->computeLength<float>(state.cssToLengthConversionData()) : 0;
+ float spread = item->spread ? item->spread->computeLength<float>(state.cssToLengthConversionData()) : 0;
ShadowStyle shadowStyle = item->style && item->style->getValueID() == CSSValueInset ? Inset : Normal;
Color color;
if (item->color)
color = state.document().textLinkColors().colorFromPrimitiveValue(item->color.get(), state.style()->color());
else
color = state.style()->color();
-
- if (!color.isValid())
- color = Color::transparent;
- shadows.append(ShadowData(IntPoint(x, y), blur, spread, shadowStyle, color));
+ shadows.append(ShadowData(FloatPoint(x, y), blur, spread, shadowStyle, color));
}
return ShadowList::adopt(shadows);
}
@@ -161,14 +404,53 @@ float StyleBuilderConverter::convertSpacing(StyleResolverState& state, CSSValue*
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->getValueID() == CSSValueNormal)
return 0;
- if (state.useSVGZoomRules())
- return primitiveValue->computeLength<float>(state.cssToLengthConversionData().copyWithAdjustedZoom(1));
return primitiveValue->computeLength<float>(state.cssToLengthConversionData());
}
-SVGLength StyleBuilderConverter::convertSVGLength(StyleResolverState&, CSSValue* value)
+PassRefPtr<SVGLengthList> StyleBuilderConverter::convertStrokeDasharray(StyleResolverState&, CSSValue* value)
+{
+ if (!value->isValueList()) {
+ return SVGRenderStyle::initialStrokeDashArray();
+ }
+
+ CSSValueList* dashes = toCSSValueList(value);
+
+ RefPtr<SVGLengthList> array = SVGLengthList::create();
+ size_t length = dashes->length();
+ for (size_t i = 0; i < length; ++i) {
+ CSSValue* currValue = dashes->itemWithoutBoundsCheck(i);
+ if (!currValue->isPrimitiveValue())
+ continue;
+
+ CSSPrimitiveValue* dash = toCSSPrimitiveValue(dashes->itemWithoutBoundsCheck(i));
+ array->append(SVGLength::fromCSSPrimitiveValue(dash));
+ }
+
+ return array.release();
+}
+
+Color StyleBuilderConverter::convertSVGColor(StyleResolverState& state, CSSValue* value)
+{
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->isRGBColor())
+ return primitiveValue->getRGBA32Value();
+ ASSERT(primitiveValue->getValueID() == CSSValueCurrentcolor);
+ return state.style()->color();
+}
+
+PassRefPtr<SVGLength> StyleBuilderConverter::convertSVGLength(StyleResolverState&, CSSValue* value)
{
return SVGLength::fromCSSPrimitiveValue(toCSSPrimitiveValue(value));
}
+float StyleBuilderConverter::convertTextStrokeWidth(StyleResolverState& state, CSSValue* value)
+{
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->getValueID()) {
+ float multiplier = convertLineWidth<float>(state, value);
+ return CSSPrimitiveValue::create(multiplier / 48, CSSPrimitiveValue::CSS_EMS)->computeLength<float>(state.cssToLengthConversionData());
+ }
+ return primitiveValue->computeLength<float>(state.cssToLengthConversionData());
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.h
index 12f03ecfdcc..e2f92ccea97 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderConverter.h
@@ -30,7 +30,9 @@
#include "core/css/CSSValue.h"
#include "core/css/resolver/StyleResolverState.h"
#include "core/rendering/RenderView.h"
+#include "core/rendering/style/QuotesData.h"
#include "core/rendering/style/ShadowList.h"
+#include "core/rendering/style/StyleReflection.h"
#include "core/svg/SVGLength.h"
#include "platform/LengthSize.h"
@@ -40,20 +42,33 @@ namespace WebCore {
class StyleBuilderConverter {
public:
- static String convertFragmentIdentifier(StyleResolverState&, CSSValue*);
+ static PassRefPtr<StyleReflection> convertBoxReflect(StyleResolverState&, CSSValue*);
+ static AtomicString convertFragmentIdentifier(StyleResolverState&, CSSValue*);
template <typename T> static T convertComputedLength(StyleResolverState&, CSSValue*);
+ static EGlyphOrientation convertGlyphOrientation(StyleResolverState&, CSSValue*);
+ static GridPosition convertGridPosition(StyleResolverState&, CSSValue*);
+ static GridTrackSize convertGridTrackSize(StyleResolverState&, CSSValue*);
template <typename T> static T convertLineWidth(StyleResolverState&, CSSValue*);
static Length convertLength(StyleResolverState&, CSSValue*);
static Length convertLengthOrAuto(StyleResolverState&, CSSValue*);
static Length convertLengthSizing(StyleResolverState&, CSSValue*);
static Length convertLengthMaxSizing(StyleResolverState&, CSSValue*);
static LengthPoint convertLengthPoint(StyleResolverState&, CSSValue*);
+ static LineBoxContain convertLineBoxContain(StyleResolverState&, CSSValue*);
static float convertNumberOrPercentage(StyleResolverState&, CSSValue*);
+ static PassRefPtr<QuotesData> convertQuotes(StyleResolverState&, CSSValue*);
static LengthSize convertRadius(StyleResolverState&, CSSValue*);
+ static EPaintOrder convertPaintOrder(StyleResolverState&, CSSValue*);
static PassRefPtr<ShadowList> convertShadow(StyleResolverState&, CSSValue*);
static float convertSpacing(StyleResolverState&, CSSValue*);
template <CSSValueID IdForNone> static AtomicString convertString(StyleResolverState&, CSSValue*);
- static SVGLength convertSVGLength(StyleResolverState&, CSSValue*);
+ static PassRefPtr<SVGLengthList> convertStrokeDasharray(StyleResolverState&, CSSValue*);
+ static Color convertSVGColor(StyleResolverState&, CSSValue*);
+ static PassRefPtr<SVGLength> convertSVGLength(StyleResolverState&, CSSValue*);
+ static float convertTextStrokeWidth(StyleResolverState&, CSSValue*);
+
+ static bool convertGridTrackList(CSSValue*, Vector<GridTrackSize>&, NamedGridLinesMap&, OrderedNamedGridLines&, StyleResolverState&);
+ static void createImplicitNamedGridLinesFromGridArea(const NamedGridAreaMap&, NamedGridLinesMap&, GridTrackSizingDirection);
};
template <typename T>
@@ -73,8 +88,6 @@ T StyleBuilderConverter::convertLineWidth(StyleResolverState& state, CSSValue* v
return 3;
if (valueID == CSSValueThick)
return 5;
- if (primitiveValue->isViewportPercentageLength())
- return intValueForLength(primitiveValue->viewportPercentageLength(), 0, state.document().renderView());
if (valueID == CSSValueInvalid) {
// Any original result that was >= 1 should not be allowed to fall below 1.
// This keeps border lines from vanishing.
@@ -96,7 +109,7 @@ AtomicString StyleBuilderConverter::convertString(StyleResolverState&, CSSValue*
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->getValueID() == IdForNone)
return nullAtom;
- return primitiveValue->getStringValue();
+ return AtomicString(primitiveValue->getStringValue());
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderCustom.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderCustom.cpp
index 8f239d8cb64..c9e9af60fb0 100755..100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderCustom.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleBuilderCustom.cpp
@@ -37,28 +37,25 @@
*/
#include "config.h"
-#include "StyleBuilderFunctions.h"
-#include "CSSPropertyNames.h"
-#include "CSSValueKeywords.h"
-#include "StylePropertyShorthand.h"
+#include "core/CSSPropertyNames.h"
+#include "core/CSSValueKeywords.h"
+#include "core/StyleBuilderFunctions.h"
+#include "core/StylePropertyShorthand.h"
#include "core/css/BasicShapeFunctions.h"
#include "core/css/CSSAspectRatioValue.h"
#include "core/css/CSSCursorImageValue.h"
#include "core/css/CSSFontValue.h"
-#include "core/css/CSSFunctionValue.h"
#include "core/css/CSSGradientValue.h"
-#include "core/css/CSSGridLineNamesValue.h"
-#include "core/css/CSSGridTemplateValue.h"
+#include "core/css/CSSGridTemplateAreasValue.h"
#include "core/css/CSSHelper.h"
#include "core/css/CSSImageSetValue.h"
#include "core/css/CSSLineBoxContainValue.h"
-#include "core/css/CSSParser.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSPrimitiveValueMappings.h"
#include "core/css/CSSProperty.h"
-#include "core/css/CSSReflectValue.h"
-#include "core/css/CSSVariableValue.h"
#include "core/css/Counter.h"
+#include "core/css/Pair.h"
#include "core/css/Rect.h"
#include "core/css/StylePropertySet.h"
#include "core/css/StyleRule.h"
@@ -67,18 +64,14 @@
#include "core/css/resolver/FontBuilder.h"
#include "core/css/resolver/StyleBuilder.h"
#include "core/css/resolver/TransformBuilder.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
#include "core/rendering/style/CounterContent.h"
-#include "core/rendering/style/CursorList.h"
#include "core/rendering/style/QuotesData.h"
#include "core/rendering/style/RenderStyle.h"
#include "core/rendering/style/RenderStyleConstants.h"
#include "core/rendering/style/SVGRenderStyle.h"
-#include "core/rendering/style/SVGRenderStyleDefs.h"
#include "core/rendering/style/StyleGeneratedImage.h"
-#include "core/svg/SVGColor.h"
-#include "core/svg/SVGPaint.h"
#include "platform/fonts/FontDescription.h"
#include "wtf/MathExtras.h"
#include "wtf/StdLibExtras.h"
@@ -86,6 +79,58 @@
namespace WebCore {
+namespace {
+
+static inline bool isValidVisitedLinkProperty(CSSPropertyID id)
+{
+ switch (id) {
+ case CSSPropertyBackgroundColor:
+ case CSSPropertyBorderLeftColor:
+ case CSSPropertyBorderRightColor:
+ case CSSPropertyBorderTopColor:
+ case CSSPropertyBorderBottomColor:
+ case CSSPropertyColor:
+ case CSSPropertyFill:
+ case CSSPropertyOutlineColor:
+ case CSSPropertyStroke:
+ case CSSPropertyTextDecorationColor:
+ case CSSPropertyWebkitColumnRuleColor:
+ case CSSPropertyWebkitTextEmphasisColor:
+ case CSSPropertyWebkitTextFillColor:
+ case CSSPropertyWebkitTextStrokeColor:
+ return true;
+ default:
+ return false;
+ }
+}
+
+} // namespace
+
+void StyleBuilder::applyProperty(CSSPropertyID id, StyleResolverState& state, CSSValue* value)
+{
+ ASSERT_WITH_MESSAGE(!isExpandedShorthand(id), "Shorthand property id = %d wasn't expanded at parsing time", id);
+
+ bool isInherit = state.parentNode() && value->isInheritedValue();
+ bool isInitial = value->isInitialValue() || (!state.parentNode() && value->isInheritedValue());
+
+ ASSERT(!isInherit || !isInitial); // isInherit -> !isInitial && isInitial -> !isInherit
+ ASSERT(!isInherit || (state.parentNode() && state.parentStyle())); // isInherit -> (state.parentNode() && state.parentStyle())
+
+ if (!state.applyPropertyToRegularStyle() && (!state.applyPropertyToVisitedLinkStyle() || !isValidVisitedLinkProperty(id))) {
+ // Limit the properties that can be applied to only the ones honored by :visited.
+ return;
+ }
+
+ CSSPrimitiveValue* primitiveValue = value->isPrimitiveValue() ? toCSSPrimitiveValue(value) : 0;
+ if (primitiveValue && primitiveValue->getValueID() == CSSValueCurrentcolor)
+ state.style()->setHasCurrentColor();
+
+ if (isInherit && !state.parentStyle()->hasExplicitlyInheritedProperties() && !CSSProperty::isInheritedProperty(id))
+ state.parentStyle()->setHasExplicitlyInheritedProperties();
+
+ StyleBuilder::applyProperty(id, state, value, isInitial, isInherit);
+}
+
static Length clipConvertToLength(StyleResolverState& state, CSSPrimitiveValue* value)
{
return value->convertToLength<FixedConversion | PercentConversion | AutoConversion>(state.cssToLengthConversionData());
@@ -108,22 +153,54 @@ void StyleBuilderFunctions::applyInheritCSSPropertyClip(StyleResolverState& stat
void StyleBuilderFunctions::applyValueCSSPropertyClip(StyleResolverState& state, CSSValue* value)
{
- if (!value->isPrimitiveValue())
- return;
-
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (Rect* rect = primitiveValue->getRectValue()) {
- Length top = clipConvertToLength(state, rect->top());
- Length right = clipConvertToLength(state, rect->right());
- Length bottom = clipConvertToLength(state, rect->bottom());
- Length left = clipConvertToLength(state, rect->left());
- state.style()->setClip(top, right, bottom, left);
- state.style()->setHasClip(true);
- } else if (primitiveValue->getValueID() == CSSValueAuto) {
+ if (primitiveValue->getValueID() == CSSValueAuto) {
state.style()->setClip(Length(), Length(), Length(), Length());
state.style()->setHasClip(false);
+ return;
+ }
+
+ Rect* rect = primitiveValue->getRectValue();
+ Length top = clipConvertToLength(state, rect->top());
+ Length right = clipConvertToLength(state, rect->right());
+ Length bottom = clipConvertToLength(state, rect->bottom());
+ Length left = clipConvertToLength(state, rect->left());
+ state.style()->setClip(top, right, bottom, left);
+ state.style()->setHasClip(true);
+}
+
+void StyleBuilderFunctions::applyInitialCSSPropertyColor(StyleResolverState& state)
+{
+ Color color = RenderStyle::initialColor();
+ if (state.applyPropertyToRegularStyle())
+ state.style()->setColor(color);
+ if (state.applyPropertyToVisitedLinkStyle())
+ state.style()->setVisitedLinkColor(color);
+}
+
+void StyleBuilderFunctions::applyInheritCSSPropertyColor(StyleResolverState& state)
+{
+ Color color = state.parentStyle()->color();
+ if (state.applyPropertyToRegularStyle())
+ state.style()->setColor(color);
+ if (state.applyPropertyToVisitedLinkStyle())
+ state.style()->setVisitedLinkColor(color);
+}
+
+void StyleBuilderFunctions::applyValueCSSPropertyColor(StyleResolverState& state, CSSValue* value)
+{
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ // As per the spec, 'color: currentColor' is treated as 'color: inherit'
+ if (primitiveValue->getValueID() == CSSValueCurrentcolor) {
+ applyInheritCSSPropertyColor(state);
+ return;
}
+
+ if (state.applyPropertyToRegularStyle())
+ state.style()->setColor(state.document().textLinkColors().colorFromPrimitiveValue(primitiveValue, state.style()->color()));
+ if (state.applyPropertyToVisitedLinkStyle())
+ state.style()->setVisitedLinkColor(state.document().textLinkColors().colorFromPrimitiveValue(primitiveValue, state.style()->color(), true));
}
void StyleBuilderFunctions::applyInitialCSSPropertyCursor(StyleResolverState& state)
@@ -152,16 +229,12 @@ void StyleBuilderFunctions::applyValueCSSPropertyCursor(StyleResolverState& stat
if (image->updateIfSVGCursorIsUsed(state.element())) // Elements with SVG cursors are not allowed to share style.
state.style()->setUnique();
state.style()->addCursor(state.styleImage(CSSPropertyCursor, image), image->hotSpot());
- } else if (item->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(item);
- if (primitiveValue->isValueID())
- state.style()->setCursor(*primitiveValue);
+ } else {
+ state.style()->setCursor(*toCSSPrimitiveValue(item));
}
}
- } else if (value->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (primitiveValue->isValueID() && state.style()->cursor() != ECursor(*primitiveValue))
- state.style()->setCursor(*primitiveValue);
+ } else {
+ state.style()->setCursor(*toCSSPrimitiveValue(value));
}
}
@@ -190,20 +263,15 @@ void StyleBuilderFunctions::applyInheritCSSPropertyDisplay(StyleResolverState& s
void StyleBuilderFunctions::applyValueCSSPropertyDisplay(StyleResolverState& state, CSSValue* value)
{
- if (!value->isPrimitiveValue())
- return;
-
EDisplay display = *toCSSPrimitiveValue(value);
-
if (!isValidDisplayValue(state, display))
return;
-
state.style()->setDisplay(display);
}
void StyleBuilderFunctions::applyInitialCSSPropertyFontFamily(StyleResolverState& state)
{
- state.fontBuilder().setFontFamilyInitial(state.style()->effectiveZoom());
+ state.fontBuilder().setFontFamilyInitial();
}
void StyleBuilderFunctions::applyInheritCSSPropertyFontFamily(StyleResolverState& state)
@@ -213,22 +281,22 @@ void StyleBuilderFunctions::applyInheritCSSPropertyFontFamily(StyleResolverState
void StyleBuilderFunctions::applyValueCSSPropertyFontFamily(StyleResolverState& state, CSSValue* value)
{
- state.fontBuilder().setFontFamilyValue(value, state.style()->effectiveZoom());
+ state.fontBuilder().setFontFamilyValue(value);
}
void StyleBuilderFunctions::applyInitialCSSPropertyFontSize(StyleResolverState& state)
{
- state.fontBuilder().setFontSizeInitial(state.style()->effectiveZoom());
+ state.fontBuilder().setFontSizeInitial();
}
void StyleBuilderFunctions::applyInheritCSSPropertyFontSize(StyleResolverState& state)
{
- state.fontBuilder().setFontSizeInherit(state.parentFontDescription(), state.style()->effectiveZoom());
+ state.fontBuilder().setFontSizeInherit(state.parentFontDescription());
}
void StyleBuilderFunctions::applyValueCSSPropertyFontSize(StyleResolverState& state, CSSValue* value)
{
- state.fontBuilder().setFontSizeValue(value, state.parentStyle(), state.rootElementStyle(), state.style()->effectiveZoom());
+ state.fontBuilder().setFontSizeValue(value, state.parentStyle(), state.rootElementStyle());
}
void StyleBuilderFunctions::applyInitialCSSPropertyFontWeight(StyleResolverState& state)
@@ -243,17 +311,17 @@ void StyleBuilderFunctions::applyInheritCSSPropertyFontWeight(StyleResolverState
void StyleBuilderFunctions::applyValueCSSPropertyFontWeight(StyleResolverState& state, CSSValue* value)
{
- if (!value->isPrimitiveValue())
- return;
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
switch (primitiveValue->getValueID()) {
case CSSValueInvalid:
ASSERT_NOT_REACHED();
break;
case CSSValueBolder:
+ state.fontBuilder().setWeight(state.parentStyle()->fontDescription().weight());
state.fontBuilder().setWeightBolder();
break;
case CSSValueLighter:
+ state.fontBuilder().setWeight(state.parentStyle()->fontDescription().weight());
state.fontBuilder().setWeightLighter();
break;
default:
@@ -261,11 +329,53 @@ void StyleBuilderFunctions::applyValueCSSPropertyFontWeight(StyleResolverState&
}
}
-void StyleBuilderFunctions::applyValueCSSPropertyLineHeight(StyleResolverState& state, CSSValue* value)
+void StyleBuilderFunctions::applyValueCSSPropertyGlyphOrientationVertical(StyleResolverState& state, CSSValue* value)
{
- if (!value->isPrimitiveValue())
+ if (value->isPrimitiveValue() && toCSSPrimitiveValue(value)->getValueID() == CSSValueAuto)
+ state.style()->accessSVGStyle()->setGlyphOrientationVertical(GO_AUTO);
+ else
+ state.style()->accessSVGStyle()->setGlyphOrientationVertical(StyleBuilderConverter::convertGlyphOrientation(state, value));
+}
+
+void StyleBuilderFunctions::applyInitialCSSPropertyGridTemplateAreas(StyleResolverState& state)
+{
+ state.style()->setNamedGridArea(RenderStyle::initialNamedGridArea());
+ state.style()->setNamedGridAreaRowCount(RenderStyle::initialNamedGridAreaCount());
+ state.style()->setNamedGridAreaColumnCount(RenderStyle::initialNamedGridAreaCount());
+}
+
+void StyleBuilderFunctions::applyInheritCSSPropertyGridTemplateAreas(StyleResolverState& state)
+{
+ state.style()->setNamedGridArea(state.parentStyle()->namedGridArea());
+ state.style()->setNamedGridAreaRowCount(state.parentStyle()->namedGridAreaRowCount());
+ state.style()->setNamedGridAreaColumnCount(state.parentStyle()->namedGridAreaColumnCount());
+}
+
+void StyleBuilderFunctions::applyValueCSSPropertyGridTemplateAreas(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue()) {
+ // FIXME: Shouldn't we clear the grid-area values
+ ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNone);
return;
+ }
+ CSSGridTemplateAreasValue* gridTemplateAreasValue = toCSSGridTemplateAreasValue(value);
+ const NamedGridAreaMap& newNamedGridAreas = gridTemplateAreasValue->gridAreaMap();
+
+ NamedGridLinesMap namedGridColumnLines = state.style()->namedGridColumnLines();
+ NamedGridLinesMap namedGridRowLines = state.style()->namedGridRowLines();
+ StyleBuilderConverter::createImplicitNamedGridLinesFromGridArea(newNamedGridAreas, namedGridColumnLines, ForColumns);
+ StyleBuilderConverter::createImplicitNamedGridLinesFromGridArea(newNamedGridAreas, namedGridRowLines, ForRows);
+ state.style()->setNamedGridColumnLines(namedGridColumnLines);
+ state.style()->setNamedGridRowLines(namedGridRowLines);
+
+ state.style()->setNamedGridArea(newNamedGridAreas);
+ state.style()->setNamedGridAreaRowCount(gridTemplateAreasValue->rowCount());
+ state.style()->setNamedGridAreaColumnCount(gridTemplateAreasValue->columnCount());
+}
+
+void StyleBuilderFunctions::applyValueCSSPropertyLineHeight(StyleResolverState& state, CSSValue* value)
+{
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
Length lineHeight;
@@ -273,18 +383,16 @@ void StyleBuilderFunctions::applyValueCSSPropertyLineHeight(StyleResolverState&
lineHeight = RenderStyle::initialLineHeight();
} else if (primitiveValue->isLength()) {
float multiplier = state.style()->effectiveZoom();
- if (Frame* frame = state.document().frame())
+ if (LocalFrame* frame = state.document().frame())
multiplier *= frame->textZoomFactor();
lineHeight = primitiveValue->computeLength<Length>(state.cssToLengthConversionData().copyWithAdjustedZoom(multiplier));
} else if (primitiveValue->isPercentage()) {
lineHeight = Length((state.style()->computedFontSize() * primitiveValue->getIntValue()) / 100.0, Fixed);
} else if (primitiveValue->isNumber()) {
lineHeight = Length(primitiveValue->getDoubleValue() * 100.0, Percent);
- } else if (primitiveValue->isViewportPercentageLength()) {
- lineHeight = primitiveValue->viewportPercentageLength();
} else if (primitiveValue->isCalculated()) {
double multiplier = state.style()->effectiveZoom();
- if (Frame* frame = state.document().frame())
+ if (LocalFrame* frame = state.document().frame())
multiplier *= frame->textZoomFactor();
Length zoomedLength = Length(primitiveValue->cssCalcValue()->toCalcValue(state.cssToLengthConversionData().copyWithAdjustedZoom(multiplier)));
lineHeight = Length(valueForLength(zoomedLength, state.style()->fontSize()), Fixed);
@@ -320,20 +428,13 @@ void StyleBuilderFunctions::applyValueCSSPropertyOutlineStyle(StyleResolverState
void StyleBuilderFunctions::applyValueCSSPropertyResize(StyleResolverState& state, CSSValue* value)
{
- if (!value->isPrimitiveValue())
- return;
-
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
EResize r = RESIZE_NONE;
- switch (primitiveValue->getValueID()) {
- case 0:
- return;
- case CSSValueAuto:
+ if (primitiveValue->getValueID() == CSSValueAuto) {
if (Settings* settings = state.document().settings())
r = settings->textAreasAreResizable() ? RESIZE_BOTH : RESIZE_NONE;
- break;
- default:
+ } else {
r = *primitiveValue;
}
state.style()->setResize(r);
@@ -439,7 +540,7 @@ void StyleBuilderFunctions::applyValueCSSPropertySize(StyleResolverState& state,
height = second->computeLength<Length>(state.cssToLengthConversionData().copyWithAdjustedZoom(1.0));
} else {
// <page-size> <orientation>
- // The value order is guaranteed. See CSSParser::parseSizeParameter.
+ // The value order is guaranteed. See BisonCSSParser::parseSizeParameter.
if (!getPageSizeFromName(first, second, width, height))
return;
}
@@ -519,12 +620,14 @@ void StyleBuilderFunctions::applyInheritCSSPropertyTextIndent(StyleResolverState
{
state.style()->setTextIndent(state.parentStyle()->textIndent());
state.style()->setTextIndentLine(state.parentStyle()->textIndentLine());
+ state.style()->setTextIndentType(state.parentStyle()->textIndentType());
}
void StyleBuilderFunctions::applyInitialCSSPropertyTextIndent(StyleResolverState& state)
{
state.style()->setTextIndent(RenderStyle::initialTextIndent());
state.style()->setTextIndentLine(RenderStyle::initialTextIndentLine());
+ state.style()->setTextIndentType(RenderStyle::initialTextIndentType());
}
void StyleBuilderFunctions::applyValueCSSPropertyTextIndent(StyleResolverState& state, CSSValue* value)
@@ -532,23 +635,155 @@ void StyleBuilderFunctions::applyValueCSSPropertyTextIndent(StyleResolverState&
if (!value->isValueList())
return;
- // [ <length> | <percentage> ] each-line
- // The order is guaranteed. See CSSParser::parseTextIndent.
- // The second value, each-line is handled only when css3TextEnabled() returns true.
+ Length lengthOrPercentageValue;
+ TextIndentLine textIndentLineValue = RenderStyle::initialTextIndentLine();
+ TextIndentType textIndentTypeValue = RenderStyle::initialTextIndentType();
+
+ for (CSSValueListIterator i(value); i.hasMore(); i.advance()) {
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(i.value());
+ if (!primitiveValue->getValueID())
+ lengthOrPercentageValue = primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData());
+ else if (primitiveValue->getValueID() == CSSValueEachLine)
+ textIndentLineValue = TextIndentEachLine;
+ else if (primitiveValue->getValueID() == CSSValueHanging)
+ textIndentTypeValue = TextIndentHanging;
+ else
+ ASSERT_NOT_REACHED();
+ }
- CSSValueList* valueList = toCSSValueList(value);
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(valueList->itemWithoutBoundsCheck(0));
- Length lengthOrPercentageValue = primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData());
- ASSERT(!lengthOrPercentageValue.isUndefined());
state.style()->setTextIndent(lengthOrPercentageValue);
+ state.style()->setTextIndentLine(textIndentLineValue);
+ state.style()->setTextIndentType(textIndentTypeValue);
+}
+
+void StyleBuilderFunctions::applyValueCSSPropertyTransform(StyleResolverState& state, CSSValue* value)
+{
+ TransformOperations operations;
+ TransformBuilder::createTransformOperations(value, state.cssToLengthConversionData(), operations);
+ state.style()->setTransform(operations);
+}
+
+void StyleBuilderFunctions::applyInitialCSSPropertyTransformOrigin(StyleResolverState& state)
+{
+ applyInitialCSSPropertyWebkitTransformOriginX(state);
+ applyInitialCSSPropertyWebkitTransformOriginY(state);
+ applyInitialCSSPropertyWebkitTransformOriginZ(state);
+}
+
+void StyleBuilderFunctions::applyInheritCSSPropertyTransformOrigin(StyleResolverState& state)
+{
+ applyInheritCSSPropertyWebkitTransformOriginX(state);
+ applyInheritCSSPropertyWebkitTransformOriginY(state);
+ applyInheritCSSPropertyWebkitTransformOriginZ(state);
+}
+
+void StyleBuilderFunctions::applyValueCSSPropertyTransformOrigin(StyleResolverState& state, CSSValue* value)
+{
+ CSSValueList* list = toCSSValueList(value);
+ ASSERT(list->length() == 3);
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(list->item(0));
+ if (primitiveValue->isValueID()) {
+ switch (primitiveValue->getValueID()) {
+ case CSSValueLeft:
+ state.style()->setTransformOriginX(Length(0, Percent));
+ break;
+ case CSSValueRight:
+ state.style()->setTransformOriginX(Length(100, Percent));
+ break;
+ case CSSValueCenter:
+ state.style()->setTransformOriginX(Length(50, Percent));
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ }
+ } else {
+ state.style()->setTransformOriginX(StyleBuilderConverter::convertLength(state, primitiveValue));
+ }
+
+ primitiveValue = toCSSPrimitiveValue(list->item(1));
+ if (primitiveValue->isValueID()) {
+ switch (primitiveValue->getValueID()) {
+ case CSSValueTop:
+ state.style()->setTransformOriginY(Length(0, Percent));
+ break;
+ case CSSValueBottom:
+ state.style()->setTransformOriginY(Length(100, Percent));
+ break;
+ case CSSValueCenter:
+ state.style()->setTransformOriginY(Length(50, Percent));
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ }
+ } else {
+ state.style()->setTransformOriginY(StyleBuilderConverter::convertLength(state, primitiveValue));
+ }
+
+ primitiveValue = toCSSPrimitiveValue(list->item(2));
+ state.style()->setTransformOriginZ(StyleBuilderConverter::convertComputedLength<float>(state, primitiveValue));
+}
+
+void StyleBuilderFunctions::applyInitialCSSPropertyPerspectiveOrigin(StyleResolverState& state)
+{
+ applyInitialCSSPropertyWebkitPerspectiveOriginX(state);
+ applyInitialCSSPropertyWebkitPerspectiveOriginY(state);
+}
- ASSERT(valueList->length() <= 2);
- CSSPrimitiveValue* eachLineValue = toCSSPrimitiveValue(valueList->item(1));
- if (eachLineValue) {
- ASSERT(eachLineValue->getValueID() == CSSValueEachLine);
- state.style()->setTextIndentLine(TextIndentEachLine);
- } else
- state.style()->setTextIndentLine(TextIndentFirstLine);
+void StyleBuilderFunctions::applyInheritCSSPropertyPerspectiveOrigin(StyleResolverState& state)
+{
+ applyInheritCSSPropertyWebkitPerspectiveOriginX(state);
+ applyInheritCSSPropertyWebkitPerspectiveOriginY(state);
+}
+
+void StyleBuilderFunctions::applyValueCSSPropertyPerspectiveOrigin(StyleResolverState& state, CSSValue* value)
+{
+ CSSValueList* list = toCSSValueList(value);
+ ASSERT(list->length() == 2);
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(list->item(0));
+ if (primitiveValue->isValueID()) {
+ switch (primitiveValue->getValueID()) {
+ case CSSValueLeft:
+ state.style()->setPerspectiveOriginX(Length(0, Percent));
+ break;
+ case CSSValueRight:
+ state.style()->setPerspectiveOriginX(Length(100, Percent));
+ break;
+ case CSSValueCenter:
+ state.style()->setPerspectiveOriginX(Length(50, Percent));
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ }
+ } else {
+ state.style()->setPerspectiveOriginX(StyleBuilderConverter::convertLength(state, primitiveValue));
+ }
+
+ primitiveValue = toCSSPrimitiveValue(list->item(1));
+ if (primitiveValue->isValueID()) {
+ switch (primitiveValue->getValueID()) {
+ case CSSValueTop:
+ state.style()->setPerspectiveOriginY(Length(0, Percent));
+ break;
+ case CSSValueBottom:
+ state.style()->setPerspectiveOriginY(Length(100, Percent));
+ break;
+ case CSSValueCenter:
+ state.style()->setPerspectiveOriginY(Length(50, Percent));
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ }
+ } else {
+ state.style()->setPerspectiveOriginY(StyleBuilderConverter::convertLength(state, primitiveValue));
+ }
+}
+
+void StyleBuilderFunctions::applyInheritCSSPropertyVerticalAlign(StyleResolverState& state)
+{
+ EVerticalAlign verticalAlign = state.parentStyle()->verticalAlign();
+ state.style()->setVerticalAlign(verticalAlign);
+ if (verticalAlign == LENGTH)
+ state.style()->setVerticalAlignLength(state.parentStyle()->verticalAlignLength());
}
void StyleBuilderFunctions::applyValueCSSPropertyVerticalAlign(StyleResolverState& state, CSSValue* value)
@@ -558,8 +793,10 @@ void StyleBuilderFunctions::applyValueCSSPropertyVerticalAlign(StyleResolverStat
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- if (primitiveValue->getValueID())
- return state.style()->setVerticalAlign(*primitiveValue);
+ if (primitiveValue->getValueID()) {
+ state.style()->setVerticalAlign(*primitiveValue);
+ return;
+ }
state.style()->setVerticalAlignLength(primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData()));
}
@@ -657,29 +894,36 @@ void StyleBuilderFunctions::applyValueCSSPropertyWebkitClipPath(StyleResolverSta
if (value->isPrimitiveValue()) {
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
if (primitiveValue->getValueID() == CSSValueNone) {
- state.style()->setClipPath(0);
+ state.style()->setClipPath(nullptr);
} else if (primitiveValue->isShape()) {
state.style()->setClipPath(ShapeClipPathOperation::create(basicShapeForValue(state, primitiveValue->getShapeValue())));
} else if (primitiveValue->primitiveType() == CSSPrimitiveValue::CSS_URI) {
String cssURLValue = primitiveValue->getStringValue();
KURL url = state.document().completeURL(cssURLValue);
// FIXME: It doesn't work with forward or external SVG references (see https://bugs.webkit.org/show_bug.cgi?id=90405)
- state.style()->setClipPath(ReferenceClipPathOperation::create(cssURLValue, url.fragmentIdentifier()));
+ state.style()->setClipPath(ReferenceClipPathOperation::create(cssURLValue, AtomicString(url.fragmentIdentifier())));
}
}
}
-void StyleBuilderFunctions::applyInitialCSSPropertyWebkitFontVariantLigatures(StyleResolverState& state)
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitFilter(StyleResolverState& state, CSSValue* value)
+{
+ FilterOperations operations;
+ if (FilterOperationResolver::createFilterOperations(value, state.cssToLengthConversionData(), operations, state))
+ state.style()->setFilter(operations);
+}
+
+void StyleBuilderFunctions::applyInitialCSSPropertyFontVariantLigatures(StyleResolverState& state)
{
state.fontBuilder().setFontVariantLigaturesInitial();
}
-void StyleBuilderFunctions::applyInheritCSSPropertyWebkitFontVariantLigatures(StyleResolverState& state)
+void StyleBuilderFunctions::applyInheritCSSPropertyFontVariantLigatures(StyleResolverState& state)
{
state.fontBuilder().setFontVariantLigaturesInherit(state.parentFontDescription());
}
-void StyleBuilderFunctions::applyValueCSSPropertyWebkitFontVariantLigatures(StyleResolverState& state, CSSValue* value)
+void StyleBuilderFunctions::applyValueCSSPropertyFontVariantLigatures(StyleResolverState& state, CSSValue* value)
{
state.fontBuilder().setFontVariantLigaturesValue(value);
}
@@ -705,9 +949,8 @@ void StyleBuilderFunctions::applyValueCSSPropertyInternalMarqueeIncrement(StyleR
break;
}
} else {
- Length marqueeLength = primitiveValue ? primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData()) : Length(Undefined);
- if (!marqueeLength.isUndefined())
- state.style()->setMarqueeIncrement(marqueeLength);
+ Length marqueeLength = primitiveValue->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData());
+ state.style()->setMarqueeIncrement(marqueeLength);
}
}
@@ -757,6 +1000,14 @@ void StyleBuilderFunctions::applyValueCSSPropertyWebkitPerspectiveOrigin(StyleRe
ASSERT_NOT_REACHED();
}
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitTapHighlightColor(StyleResolverState& state, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
+ return;
+ Color color = state.document().textLinkColors().colorFromPrimitiveValue(toCSSPrimitiveValue(value), state.style()->color());
+ state.style()->setTapHighlightColor(color);
+}
+
void StyleBuilderFunctions::applyInitialCSSPropertyWebkitTextEmphasisStyle(StyleResolverState& state)
{
state.style()->setTextEmphasisFill(RenderStyle::initialTextEmphasisFill());
@@ -833,1355 +1084,310 @@ void StyleBuilderFunctions::applyValueCSSPropertyTextUnderlinePosition(StyleReso
state.style()->setTextUnderlinePosition(static_cast<TextUnderlinePosition>(t));
}
-// Everything below this line is from the old StyleResolver::applyProperty
-// and eventually needs to move into new StyleBuilderFunctions calls intead.
-
-#define HANDLE_INHERIT(prop, Prop) \
-if (isInherit) { \
- state.style()->set##Prop(state.parentStyle()->prop()); \
- return; \
-}
-
-#define HANDLE_INHERIT_AND_INITIAL(prop, Prop) \
-HANDLE_INHERIT(prop, Prop) \
-if (isInitial) { \
- state.style()->set##Prop(RenderStyle::initial##Prop()); \
- return; \
-}
-
-#define HANDLE_SVG_INHERIT(prop, Prop) \
-if (isInherit) { \
- state.style()->accessSVGStyle()->set##Prop(state.parentStyle()->svgStyle()->prop()); \
- return; \
+void StyleBuilderFunctions::applyInitialCSSPropertyWillChange(StyleResolverState& state)
+{
+ state.style()->setWillChangeContents(false);
+ state.style()->setWillChangeScrollPosition(false);
+ state.style()->setWillChangeProperties(Vector<CSSPropertyID>());
+ state.style()->setSubtreeWillChangeContents(state.parentStyle()->subtreeWillChangeContents());
}
-#define HANDLE_SVG_INHERIT_AND_INITIAL(prop, Prop) \
-HANDLE_SVG_INHERIT(prop, Prop) \
-if (isInitial) { \
- state.style()->accessSVGStyle()->set##Prop(SVGRenderStyle::initial##Prop()); \
- return; \
+void StyleBuilderFunctions::applyInheritCSSPropertyWillChange(StyleResolverState& state)
+{
+ state.style()->setWillChangeContents(state.parentStyle()->willChangeContents());
+ state.style()->setWillChangeScrollPosition(state.parentStyle()->willChangeScrollPosition());
+ state.style()->setWillChangeProperties(state.parentStyle()->willChangeProperties());
+ state.style()->setSubtreeWillChangeContents(state.parentStyle()->subtreeWillChangeContents());
}
-static bool createGridTrackBreadth(CSSPrimitiveValue* primitiveValue, const StyleResolverState& state, GridLength& workingLength)
+void StyleBuilderFunctions::applyValueCSSPropertyWillChange(StyleResolverState& state, CSSValue* value)
{
- if (primitiveValue->getValueID() == CSSValueMinContent) {
- workingLength = Length(MinContent);
- return true;
- }
+ ASSERT(value->isValueList());
+ bool willChangeContents = false;
+ bool willChangeScrollPosition = false;
+ Vector<CSSPropertyID> willChangeProperties;
- if (primitiveValue->getValueID() == CSSValueMaxContent) {
- workingLength = Length(MaxContent);
- return true;
- }
-
- if (primitiveValue->isFlex()) {
- // Fractional unit.
- workingLength.setFlex(primitiveValue->getDoubleValue());
- return true;
+ for (CSSValueListIterator i(value); i.hasMore(); i.advance()) {
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(i.value());
+ if (CSSPropertyID propertyID = primitiveValue->getPropertyID())
+ willChangeProperties.append(propertyID);
+ else if (primitiveValue->getValueID() == CSSValueContents)
+ willChangeContents = true;
+ else if (primitiveValue->getValueID() == CSSValueScrollPosition)
+ willChangeScrollPosition = true;
+ else
+ ASSERT_NOT_REACHED();
}
-
- workingLength = primitiveValue->convertToLength<FixedConversion | PercentConversion | AutoConversion>(state.cssToLengthConversionData());
- if (workingLength.length().isUndefined())
- return false;
-
- if (primitiveValue->isLength())
- workingLength.length().setQuirk(primitiveValue->isQuirkValue());
-
- return true;
+ state.style()->setWillChangeContents(willChangeContents);
+ state.style()->setWillChangeScrollPosition(willChangeScrollPosition);
+ state.style()->setWillChangeProperties(willChangeProperties);
+ state.style()->setSubtreeWillChangeContents(willChangeContents || state.parentStyle()->subtreeWillChangeContents());
}
-static bool createGridTrackSize(CSSValue* value, GridTrackSize& trackSize, const StyleResolverState& state)
+void StyleBuilderFunctions::applyInitialCSSPropertyContent(StyleResolverState& state)
{
- if (value->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- GridLength workingLength;
- if (!createGridTrackBreadth(primitiveValue, state, workingLength))
- return false;
-
- trackSize.setLength(workingLength);
- return true;
- }
-
- CSSFunctionValue* minmaxFunction = toCSSFunctionValue(value);
- CSSValueList* arguments = minmaxFunction->arguments();
- ASSERT_WITH_SECURITY_IMPLICATION(arguments->length() == 2);
- GridLength minTrackBreadth;
- GridLength maxTrackBreadth;
- if (!createGridTrackBreadth(toCSSPrimitiveValue(arguments->itemWithoutBoundsCheck(0)), state, minTrackBreadth) || !createGridTrackBreadth(toCSSPrimitiveValue(arguments->itemWithoutBoundsCheck(1)), state, maxTrackBreadth))
- return false;
+ state.style()->clearContent();
+}
- trackSize.setMinMax(minTrackBreadth, maxTrackBreadth);
- return true;
+void StyleBuilderFunctions::applyInheritCSSPropertyContent(StyleResolverState&)
+{
+ // FIXME: In CSS3, it will be possible to inherit content. In CSS2 it is not. This
+ // note is a reminder that eventually "inherit" needs to be supported.
}
-static bool createGridTrackList(CSSValue* value, Vector<GridTrackSize>& trackSizes, NamedGridLinesMap& namedGridLines, OrderedNamedGridLines& orderedNamedGridLines, const StyleResolverState& state)
+void StyleBuilderFunctions::applyValueCSSPropertyContent(StyleResolverState& state, CSSValue* value)
{
- // Handle 'none'.
- if (value->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- return primitiveValue->getValueID() == CSSValueNone;
- }
+ // list of string, uri, counter, attr, i
if (!value->isValueList())
- return false;
+ return;
- size_t currentNamedGridLine = 0;
+ bool didSet = false;
for (CSSValueListIterator i = value; i.hasMore(); i.advance()) {
- CSSValue* currValue = i.value();
- if (currValue->isGridLineNamesValue()) {
- CSSGridLineNamesValue* lineNamesValue = toCSSGridLineNamesValue(currValue);
- for (CSSValueListIterator j = lineNamesValue; j.hasMore(); j.advance()) {
- String namedGridLine = toCSSPrimitiveValue(j.value())->getStringValue();
- NamedGridLinesMap::AddResult result = namedGridLines.add(namedGridLine, Vector<size_t>());
- result.iterator->value.append(currentNamedGridLine);
- OrderedNamedGridLines::AddResult orderedInsertionResult = orderedNamedGridLines.add(currentNamedGridLine, Vector<String>());
- orderedInsertionResult.iterator->value.append(namedGridLine);
- }
- continue;
+ CSSValue* item = i.value();
+ if (item->isImageGeneratorValue()) {
+ if (item->isGradientValue())
+ state.style()->setContent(StyleGeneratedImage::create(toCSSGradientValue(item)->gradientWithStylesResolved(state.document().textLinkColors(), state.style()->color()).get()), didSet);
+ else
+ state.style()->setContent(StyleGeneratedImage::create(toCSSImageGeneratorValue(item)), didSet);
+ didSet = true;
+ } else if (item->isImageSetValue()) {
+ state.style()->setContent(state.elementStyleResources().setOrPendingFromValue(CSSPropertyContent, toCSSImageSetValue(item)), didSet);
+ didSet = true;
}
- ++currentNamedGridLine;
- GridTrackSize trackSize;
- if (!createGridTrackSize(currValue, trackSize, state))
- return false;
-
- trackSizes.append(trackSize);
- }
-
- // The parser should have rejected any <track-list> without any <track-size> as
- // this is not conformant to the syntax.
- ASSERT(!trackSizes.isEmpty());
- return true;
-}
-
-static bool createGridPosition(CSSValue* value, GridPosition& position)
-{
- // We accept the specification's grammar:
- // 'auto' | [ <integer> || <string> ] | [ span && [ <integer> || string ] ] | <ident>
-
- if (value->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- // We translate <ident> to <string> during parsing as it
- // makes handling it more simple.
- if (primitiveValue->isString()) {
- position.setNamedGridArea(primitiveValue->getStringValue());
- return true;
+ if (item->isImageValue()) {
+ state.style()->setContent(state.elementStyleResources().cachedOrPendingFromValue(state.document(), CSSPropertyContent, toCSSImageValue(item)), didSet);
+ didSet = true;
+ continue;
}
- ASSERT(primitiveValue->getValueID() == CSSValueAuto);
- return true;
- }
-
- CSSValueList* values = toCSSValueList(value);
- ASSERT(values->length());
-
- bool isSpanPosition = false;
- // The specification makes the <integer> optional, in which case it default to '1'.
- int gridLineNumber = 1;
- String gridLineName;
-
- CSSValueListIterator it = values;
- CSSPrimitiveValue* currentValue = toCSSPrimitiveValue(it.value());
- if (currentValue->getValueID() == CSSValueSpan) {
- isSpanPosition = true;
- it.advance();
- currentValue = it.hasMore() ? toCSSPrimitiveValue(it.value()) : 0;
- }
-
- if (currentValue && currentValue->isNumber()) {
- gridLineNumber = currentValue->getIntValue();
- it.advance();
- currentValue = it.hasMore() ? toCSSPrimitiveValue(it.value()) : 0;
- }
-
- if (currentValue && currentValue->isString()) {
- gridLineName = currentValue->getStringValue();
- it.advance();
- }
-
- ASSERT(!it.hasMore());
- if (isSpanPosition)
- position.setSpanPosition(gridLineNumber, gridLineName);
- else
- position.setExplicitPosition(gridLineNumber, gridLineName);
-
- return true;
-}
-
-static bool degreeToGlyphOrientation(CSSPrimitiveValue* primitiveValue, EGlyphOrientation& orientation)
-{
- if (!primitiveValue)
- return false;
-
- if (primitiveValue->primitiveType() != CSSPrimitiveValue::CSS_DEG)
- return false;
-
- float angle = fabsf(fmodf(primitiveValue->getFloatValue(), 360.0f));
-
- if (angle <= 45.0f || angle > 315.0f) {
- orientation = GO_0DEG;
- return true;
- }
- if (angle > 45.0f && angle <= 135.0f) {
- orientation = GO_90DEG;
- return true;
- }
- if (angle > 135.0f && angle <= 225.0f) {
- orientation = GO_180DEG;
- return true;
- }
- orientation = GO_270DEG;
- return true;
-}
-
-static Color colorFromSVGColorCSSValue(SVGColor* svgColor, const Color& fgColor)
-{
- Color color;
- if (svgColor->colorType() == SVGColor::SVG_COLORTYPE_CURRENTCOLOR)
- color = fgColor;
- else
- color = svgColor->color();
- return color;
-}
+ if (!item->isPrimitiveValue())
+ continue;
-static EPaintOrder paintOrderFlattened(CSSValue* cssPaintOrder)
-{
- if (cssPaintOrder->isValueList()) {
- int paintOrder = 0;
- CSSValueListInspector iter(cssPaintOrder);
- for (size_t i = 0; i < iter.length(); i++) {
- CSSPrimitiveValue* value = toCSSPrimitiveValue(iter.item(i));
+ CSSPrimitiveValue* contentValue = toCSSPrimitiveValue(item);
- EPaintOrderType paintOrderType = PT_NONE;
- switch (value->getValueID()) {
- case CSSValueFill:
- paintOrderType = PT_FILL;
+ if (contentValue->isString()) {
+ state.style()->setContent(contentValue->getStringValue().impl(), didSet);
+ didSet = true;
+ } else if (contentValue->isAttr()) {
+ // FIXME: Can a namespace be specified for an attr(foo)?
+ if (state.style()->styleType() == NOPSEUDO)
+ state.style()->setUnique();
+ else
+ state.parentStyle()->setUnique();
+ QualifiedName attr(nullAtom, AtomicString(contentValue->getStringValue()), nullAtom);
+ const AtomicString& value = state.element()->getAttribute(attr);
+ state.style()->setContent(value.isNull() ? emptyString() : value.string(), didSet);
+ didSet = true;
+ // register the fact that the attribute value affects the style
+ state.contentAttrValues().append(attr.localName());
+ } else if (contentValue->isCounter()) {
+ Counter* counterValue = contentValue->getCounterValue();
+ EListStyleType listStyleType = NoneListStyle;
+ CSSValueID listStyleIdent = counterValue->listStyleIdent();
+ if (listStyleIdent != CSSValueNone)
+ listStyleType = static_cast<EListStyleType>(listStyleIdent - CSSValueDisc);
+ OwnPtr<CounterContent> counter = adoptPtr(new CounterContent(AtomicString(counterValue->identifier()), listStyleType, AtomicString(counterValue->separator())));
+ state.style()->setContent(counter.release(), didSet);
+ didSet = true;
+ } else {
+ switch (contentValue->getValueID()) {
+ case CSSValueOpenQuote:
+ state.style()->setContent(OPEN_QUOTE, didSet);
+ didSet = true;
break;
- case CSSValueStroke:
- paintOrderType = PT_STROKE;
+ case CSSValueCloseQuote:
+ state.style()->setContent(CLOSE_QUOTE, didSet);
+ didSet = true;
break;
- case CSSValueMarkers:
- paintOrderType = PT_MARKERS;
+ case CSSValueNoOpenQuote:
+ state.style()->setContent(NO_OPEN_QUOTE, didSet);
+ didSet = true;
break;
- default:
- ASSERT_NOT_REACHED();
+ case CSSValueNoCloseQuote:
+ state.style()->setContent(NO_CLOSE_QUOTE, didSet);
+ didSet = true;
break;
+ default:
+ // normal and none do not have any effect.
+ { }
}
-
- paintOrder |= (paintOrderType << kPaintOrderBitwidth*i);
}
- return (EPaintOrder)paintOrder;
}
-
- return PO_NORMAL;
+ if (!didSet)
+ state.style()->clearContent();
}
-static inline bool isValidVisitedLinkProperty(CSSPropertyID id)
+void StyleBuilderFunctions::applyInitialCSSPropertyFont(StyleResolverState&)
{
- switch (id) {
- case CSSPropertyBackgroundColor:
- case CSSPropertyBorderLeftColor:
- case CSSPropertyBorderRightColor:
- case CSSPropertyBorderTopColor:
- case CSSPropertyBorderBottomColor:
- case CSSPropertyColor:
- case CSSPropertyFill:
- case CSSPropertyOutlineColor:
- case CSSPropertyStroke:
- case CSSPropertyTextDecorationColor:
- case CSSPropertyWebkitColumnRuleColor:
- case CSSPropertyWebkitTextEmphasisColor:
- case CSSPropertyWebkitTextFillColor:
- case CSSPropertyWebkitTextStrokeColor:
- return true;
- default:
- break;
- }
-
- return false;
+ ASSERT_NOT_REACHED();
}
-static bool hasVariableReference(CSSValue* value)
+void StyleBuilderFunctions::applyInheritCSSPropertyFont(StyleResolverState&)
{
- if (value->isPrimitiveValue()) {
- CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
- return primitiveValue->hasVariableReference();
- }
-
- if (value->isCalcValue())
- return toCSSCalcValue(value)->hasVariableReference();
-
- if (value->isReflectValue()) {
- CSSReflectValue* reflectValue = toCSSReflectValue(value);
- CSSPrimitiveValue* direction = reflectValue->direction();
- CSSPrimitiveValue* offset = reflectValue->offset();
- CSSValue* mask = reflectValue->mask();
- return (direction && hasVariableReference(direction)) || (offset && hasVariableReference(offset)) || (mask && hasVariableReference(mask));
- }
-
- for (CSSValueListIterator i = value; i.hasMore(); i.advance()) {
- if (hasVariableReference(i.value()))
- return true;
- }
-
- return false;
+ ASSERT_NOT_REACHED();
}
-// FIXME: Resolving variables should be factored better. Maybe a resover-style class?
-static void resolveVariables(StyleResolverState& state, CSSPropertyID id, CSSValue* value, Vector<std::pair<CSSPropertyID, String> >& knownExpressions)
+void StyleBuilderFunctions::applyValueCSSPropertyFont(StyleResolverState& state, CSSValue* value)
{
- std::pair<CSSPropertyID, String> expression(id, value->serializeResolvingVariables(*state.style()->variables()));
-
- if (knownExpressions.contains(expression))
- return; // cycle detected.
-
- knownExpressions.append(expression);
-
- // FIXME: It would be faster not to re-parse from strings, but for now CSS property validation lives inside the parser so we do it there.
- RefPtr<MutableStylePropertySet> resultSet = MutableStylePropertySet::create();
- if (!CSSParser::parseValue(resultSet.get(), id, expression.second, false, state.document()))
- return; // expression failed to parse.
-
- for (unsigned i = 0; i < resultSet->propertyCount(); i++) {
- StylePropertySet::PropertyReference property = resultSet->propertyAt(i);
- if (property.id() != CSSPropertyVariable && hasVariableReference(property.value())) {
- resolveVariables(state, property.id(), property.value(), knownExpressions);
- } else {
- StyleBuilder::applyProperty(property.id(), state, property.value());
- // All properties become dependent on their parent style when they use variables.
- state.style()->setHasExplicitlyInheritedProperties();
- }
- }
+ // Only System Font identifiers should come through this method
+ // all other values should have been handled when the shorthand
+ // was expanded by the parser.
+ // FIXME: System Font identifiers should not hijack this
+ // short-hand CSSProperty like this (crbug.com/353932)
+ state.style()->setLineHeight(RenderStyle::initialLineHeight());
+ state.setLineHeightValue(0);
+ state.fontBuilder().fromSystemFont(toCSSPrimitiveValue(value)->getValueID(), state.style()->effectiveZoom());
}
-void StyleBuilder::applyProperty(CSSPropertyID id, StyleResolverState& state, CSSValue* value)
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitLocale(StyleResolverState& state, CSSValue* value)
{
- if (RuntimeEnabledFeatures::cssVariablesEnabled() && id != CSSPropertyVariable && hasVariableReference(value)) {
- Vector<std::pair<CSSPropertyID, String> > knownExpressions;
- resolveVariables(state, id, value, knownExpressions);
- return;
- }
-
- // CSS variables don't resolve shorthands at parsing time, so this should be *after* handling variables.
- ASSERT_WITH_MESSAGE(!isExpandedShorthand(id), "Shorthand property id = %d wasn't expanded at parsing time", id);
-
- bool isInherit = state.parentNode() && value->isInheritedValue();
- bool isInitial = value->isInitialValue() || (!state.parentNode() && value->isInheritedValue());
-
- ASSERT(!isInherit || !isInitial); // isInherit -> !isInitial && isInitial -> !isInherit
- ASSERT(!isInherit || (state.parentNode() && state.parentStyle())); // isInherit -> (state.parentNode() && state.parentStyle())
-
- if (!state.applyPropertyToRegularStyle() && (!state.applyPropertyToVisitedLinkStyle() || !isValidVisitedLinkProperty(id))) {
- // Limit the properties that can be applied to only the ones honored by :visited.
- return;
- }
-
- CSSPrimitiveValue* primitiveValue = value->isPrimitiveValue() ? toCSSPrimitiveValue(value) : 0;
- if (primitiveValue && primitiveValue->getValueID() == CSSValueCurrentcolor)
- state.style()->setHasCurrentColor();
-
- if (isInherit && !state.parentStyle()->hasExplicitlyInheritedProperties() && !CSSProperty::isInheritedProperty(id))
- state.parentStyle()->setHasExplicitlyInheritedProperties();
-
- if (id == CSSPropertyVariable) {
- ASSERT_WITH_SECURITY_IMPLICATION(value->isVariableValue());
- CSSVariableValue* variable = toCSSVariableValue(value);
- ASSERT(!variable->name().isEmpty());
- ASSERT(!variable->value().isEmpty());
- state.style()->setVariable(variable->name(), variable->value());
- return;
- }
-
- if (StyleBuilder::applyProperty(id, state, value, isInitial, isInherit))
+ if (!value->isPrimitiveValue())
return;
-
- // Fall back to the old switch statement, which is now in StyleBuilderCustom.cpp
- StyleBuilder::oldApplyProperty(id, state, value, isInitial, isInherit);
+ const CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->getValueID() == CSSValueAuto)
+ state.style()->setLocale(nullAtom);
+ else
+ state.style()->setLocale(AtomicString(primitiveValue->getStringValue()));
+ state.fontBuilder().setScript(state.style()->locale());
}
-
-void StyleBuilder::oldApplyProperty(CSSPropertyID id, StyleResolverState& state, CSSValue* value, bool isInitial, bool isInherit)
+void StyleBuilderFunctions::applyInitialCSSPropertyWebkitAppRegion(StyleResolverState&)
{
- CSSPrimitiveValue* primitiveValue = value->isPrimitiveValue() ? toCSSPrimitiveValue(value) : 0;
-
- // What follows is a list that maps the CSS properties into their corresponding front-end
- // RenderStyle values.
- switch (id) {
- case CSSPropertyContent:
- // list of string, uri, counter, attr, i
- {
- // FIXME: In CSS3, it will be possible to inherit content. In CSS2 it is not. This
- // note is a reminder that eventually "inherit" needs to be supported.
-
- if (isInitial) {
- state.style()->clearContent();
- return;
- }
+}
- if (!value->isValueList())
- return;
+void StyleBuilderFunctions::applyInheritCSSPropertyWebkitAppRegion(StyleResolverState&)
+{
+}
- bool didSet = false;
- for (CSSValueListIterator i = value; i.hasMore(); i.advance()) {
- CSSValue* item = i.value();
- if (item->isImageGeneratorValue()) {
- if (item->isGradientValue())
- state.style()->setContent(StyleGeneratedImage::create(toCSSGradientValue(item)->gradientWithStylesResolved(state.document().textLinkColors(), state.style()->color()).get()), didSet);
- else
- state.style()->setContent(StyleGeneratedImage::create(toCSSImageGeneratorValue(item)), didSet);
- didSet = true;
- } else if (item->isImageSetValue()) {
- state.style()->setContent(state.elementStyleResources().setOrPendingFromValue(CSSPropertyContent, toCSSImageSetValue(item)), didSet);
- didSet = true;
- }
-
- if (item->isImageValue()) {
- state.style()->setContent(state.elementStyleResources().cachedOrPendingFromValue(CSSPropertyContent, toCSSImageValue(item)), didSet);
- didSet = true;
- continue;
- }
-
- if (!item->isPrimitiveValue())
- continue;
-
- CSSPrimitiveValue* contentValue = toCSSPrimitiveValue(item);
-
- if (contentValue->isString()) {
- state.style()->setContent(contentValue->getStringValue().impl(), didSet);
- didSet = true;
- } else if (contentValue->isAttr()) {
- // FIXME: Can a namespace be specified for an attr(foo)?
- if (state.style()->styleType() == NOPSEUDO)
- state.style()->setUnique();
- else
- state.parentStyle()->setUnique();
- QualifiedName attr(nullAtom, AtomicString(contentValue->getStringValue()), nullAtom);
- const AtomicString& value = state.element()->getAttribute(attr);
- state.style()->setContent(value.isNull() ? emptyString() : value.string(), didSet);
- didSet = true;
- // register the fact that the attribute value affects the style
- state.contentAttrValues().append(attr.localName());
- } else if (contentValue->isCounter()) {
- Counter* counterValue = contentValue->getCounterValue();
- EListStyleType listStyleType = NoneListStyle;
- CSSValueID listStyleIdent = counterValue->listStyleIdent();
- if (listStyleIdent != CSSValueNone)
- listStyleType = static_cast<EListStyleType>(listStyleIdent - CSSValueDisc);
- OwnPtr<CounterContent> counter = adoptPtr(new CounterContent(AtomicString(counterValue->identifier()), listStyleType, AtomicString(counterValue->separator())));
- state.style()->setContent(counter.release(), didSet);
- didSet = true;
- } else {
- switch (contentValue->getValueID()) {
- case CSSValueOpenQuote:
- state.style()->setContent(OPEN_QUOTE, didSet);
- didSet = true;
- break;
- case CSSValueCloseQuote:
- state.style()->setContent(CLOSE_QUOTE, didSet);
- didSet = true;
- break;
- case CSSValueNoOpenQuote:
- state.style()->setContent(NO_OPEN_QUOTE, didSet);
- didSet = true;
- break;
- case CSSValueNoCloseQuote:
- state.style()->setContent(NO_CLOSE_QUOTE, didSet);
- didSet = true;
- break;
- default:
- // normal and none do not have any effect.
- { }
- }
- }
- }
- if (!didSet)
- state.style()->clearContent();
- return;
- }
- case CSSPropertyQuotes:
- HANDLE_INHERIT_AND_INITIAL(quotes, Quotes);
- if (value->isValueList()) {
- CSSValueList* list = toCSSValueList(value);
- RefPtr<QuotesData> quotes = QuotesData::create();
- for (size_t i = 0; i < list->length(); i += 2) {
- CSSValue* first = list->itemWithoutBoundsCheck(i);
- // item() returns null if out of bounds so this is safe.
- CSSValue* second = list->item(i + 1);
- if (!second)
- continue;
- String startQuote = toCSSPrimitiveValue(first)->getStringValue();
- String endQuote = toCSSPrimitiveValue(second)->getStringValue();
- quotes->addPair(std::make_pair(startQuote, endQuote));
- }
- state.style()->setQuotes(quotes);
- return;
- }
- if (primitiveValue) {
- if (primitiveValue->getValueID() == CSSValueNone)
- state.style()->setQuotes(QuotesData::create());
- }
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitAppRegion(StyleResolverState& state, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
return;
- // Shorthand properties.
- case CSSPropertyFont:
- // Only System Font identifiers should come through this method
- // all other values should have been handled when the shorthand
- // was expanded by the parser.
- // FIXME: System Font identifiers should not hijack this
- // short-hand CSSProperty like this.
- ASSERT(!isInitial);
- ASSERT(!isInherit);
- ASSERT(primitiveValue);
- state.style()->setLineHeight(RenderStyle::initialLineHeight());
- state.setLineHeightValue(0);
- state.fontBuilder().fromSystemFont(primitiveValue->getValueID(), state.style()->effectiveZoom());
+ const CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (!primitiveValue->getValueID())
return;
- case CSSPropertyAnimation:
- case CSSPropertyBackground:
- case CSSPropertyBackgroundPosition:
- case CSSPropertyBackgroundRepeat:
- case CSSPropertyBorder:
- case CSSPropertyBorderBottom:
- case CSSPropertyBorderColor:
- case CSSPropertyBorderImage:
- case CSSPropertyBorderLeft:
- case CSSPropertyBorderRadius:
- case CSSPropertyBorderRight:
- case CSSPropertyBorderSpacing:
- case CSSPropertyBorderStyle:
- case CSSPropertyBorderTop:
- case CSSPropertyBorderWidth:
- case CSSPropertyListStyle:
- case CSSPropertyMargin:
- case CSSPropertyObjectPosition:
- case CSSPropertyOutline:
- case CSSPropertyOverflow:
- case CSSPropertyPadding:
- case CSSPropertyTransition:
- case CSSPropertyWebkitAnimation:
- case CSSPropertyWebkitBorderAfter:
- case CSSPropertyWebkitBorderBefore:
- case CSSPropertyWebkitBorderEnd:
- case CSSPropertyWebkitBorderStart:
- case CSSPropertyWebkitBorderRadius:
- case CSSPropertyWebkitColumns:
- case CSSPropertyWebkitColumnRule:
- case CSSPropertyFlex:
- case CSSPropertyFlexFlow:
- case CSSPropertyGridColumn:
- case CSSPropertyGridRow:
- case CSSPropertyGridArea:
- case CSSPropertyWebkitMarginCollapse:
- case CSSPropertyWebkitMask:
- case CSSPropertyWebkitMaskPosition:
- case CSSPropertyWebkitMaskRepeat:
- case CSSPropertyWebkitTextEmphasis:
- case CSSPropertyWebkitTextStroke:
- case CSSPropertyWebkitTransition:
- case CSSPropertyWebkitTransformOrigin:
- ASSERT(isExpandedShorthand(id));
- ASSERT_NOT_REACHED();
- break;
+ state.style()->setDraggableRegionMode(primitiveValue->getValueID() == CSSValueDrag ? DraggableRegionDrag : DraggableRegionNoDrag);
+ state.document().setHasAnnotatedRegions(true);
+}
- // CSS3 Properties
- case CSSPropertyWebkitBoxReflect: {
- HANDLE_INHERIT_AND_INITIAL(boxReflect, BoxReflect)
- if (primitiveValue) {
- state.style()->setBoxReflect(RenderStyle::initialBoxReflect());
- return;
- }
+void StyleBuilderFunctions::applyInitialCSSPropertyWebkitPerspective(StyleResolverState& state)
+{
+ applyInitialCSSPropertyPerspective(state);
+}
- if (!value->isReflectValue())
- return;
+void StyleBuilderFunctions::applyInheritCSSPropertyWebkitPerspective(StyleResolverState& state)
+{
+ applyInheritCSSPropertyPerspective(state);
+}
- CSSReflectValue* reflectValue = toCSSReflectValue(value);
- RefPtr<StyleReflection> reflection = StyleReflection::create();
- reflection->setDirection(*reflectValue->direction());
- if (reflectValue->offset())
- reflection->setOffset(reflectValue->offset()->convertToLength<FixedConversion | PercentConversion>(state.cssToLengthConversionData()));
- NinePieceImage mask;
- mask.setMaskDefaults();
- state.styleMap().mapNinePieceImage(state.style(), id, reflectValue->mask(), mask);
- reflection->setMask(mask);
-
- state.style()->setBoxReflect(reflection.release());
- return;
- }
- case CSSPropertySrc: // Only used in @font-face rules.
- return;
- case CSSPropertyUnicodeRange: // Only used in @font-face rules.
- return;
- case CSSPropertyWebkitLocale: {
- HANDLE_INHERIT_AND_INITIAL(locale, Locale);
- if (!primitiveValue)
- return;
- if (primitiveValue->getValueID() == CSSValueAuto)
- state.style()->setLocale(nullAtom);
- else
- state.style()->setLocale(AtomicString(primitiveValue->getStringValue()));
- state.fontBuilder().setScript(state.style()->locale());
- return;
- }
- case CSSPropertyWebkitAppRegion: {
- if (!primitiveValue || !primitiveValue->getValueID())
- return;
- state.style()->setDraggableRegionMode(primitiveValue->getValueID() == CSSValueDrag ? DraggableRegionDrag : DraggableRegionNoDrag);
- state.document().setHasAnnotatedRegions(true);
- return;
- }
- case CSSPropertyWebkitTextStrokeWidth: {
- HANDLE_INHERIT_AND_INITIAL(textStrokeWidth, TextStrokeWidth)
- float width = 0;
- switch (primitiveValue->getValueID()) {
- case CSSValueThin:
- case CSSValueMedium:
- case CSSValueThick: {
- double result = 1.0 / 48;
- if (primitiveValue->getValueID() == CSSValueMedium)
- result *= 3;
- else if (primitiveValue->getValueID() == CSSValueThick)
- result *= 5;
- width = CSSPrimitiveValue::create(result, CSSPrimitiveValue::CSS_EMS)->computeLength<float>(state.cssToLengthConversionData());
- break;
- }
- default:
- width = primitiveValue->computeLength<float>(state.cssToLengthConversionData());
- break;
- }
- state.style()->setTextStrokeWidth(width);
- return;
- }
- case CSSPropertyWebkitTransform: {
- HANDLE_INHERIT_AND_INITIAL(transform, Transform);
- TransformOperations operations;
- TransformBuilder::createTransformOperations(value, state.cssToLengthConversionData(), operations);
- state.style()->setTransform(operations);
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitPerspective(StyleResolverState& state, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
return;
- }
- case CSSPropertyWebkitPerspective: {
- HANDLE_INHERIT_AND_INITIAL(perspective, Perspective)
-
- if (!primitiveValue)
- return;
-
- if (primitiveValue->getValueID() == CSSValueNone) {
- state.style()->setPerspective(0);
- return;
- }
-
- float perspectiveValue;
- if (primitiveValue->isLength()) {
- perspectiveValue = primitiveValue->computeLength<float>(state.cssToLengthConversionData());
- } else if (primitiveValue->isNumber()) {
- // For backward compatibility, treat valueless numbers as px.
- perspectiveValue = CSSPrimitiveValue::create(primitiveValue->getDoubleValue(), CSSPrimitiveValue::CSS_PX)->computeLength<float>(state.cssToLengthConversionData());
- } else {
- return;
- }
-
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->isNumber()) {
+ float perspectiveValue = CSSPrimitiveValue::create(primitiveValue->getDoubleValue(), CSSPrimitiveValue::CSS_PX)->computeLength<float>(state.cssToLengthConversionData());
if (perspectiveValue >= 0.0f)
state.style()->setPerspective(perspectiveValue);
- return;
+ } else {
+ applyValueCSSPropertyPerspective(state, value);
}
- case CSSPropertyWebkitTapHighlightColor: {
- HANDLE_INHERIT_AND_INITIAL(tapHighlightColor, TapHighlightColor);
- if (!primitiveValue)
- break;
+}
- Color col = state.document().textLinkColors().colorFromPrimitiveValue(primitiveValue, state.style()->color());
- state.style()->setTapHighlightColor(col);
- return;
- }
- case CSSPropertyInternalCallback: {
- if (isInherit || isInitial)
- return;
- if (primitiveValue && primitiveValue->getValueID() == CSSValueInternalPresence) {
- state.style()->addCallbackSelector(state.currentRule()->selectorList().selectorsText());
- return;
- }
- break;
- }
- case CSSPropertyInvalid:
- return;
- // Directional properties are resolved by resolveDirectionAwareProperty() before the switch.
- case CSSPropertyWebkitBorderEndColor:
- case CSSPropertyWebkitBorderEndStyle:
- case CSSPropertyWebkitBorderEndWidth:
- case CSSPropertyWebkitBorderStartColor:
- case CSSPropertyWebkitBorderStartStyle:
- case CSSPropertyWebkitBorderStartWidth:
- case CSSPropertyWebkitBorderBeforeColor:
- case CSSPropertyWebkitBorderBeforeStyle:
- case CSSPropertyWebkitBorderBeforeWidth:
- case CSSPropertyWebkitBorderAfterColor:
- case CSSPropertyWebkitBorderAfterStyle:
- case CSSPropertyWebkitBorderAfterWidth:
- case CSSPropertyWebkitMarginEnd:
- case CSSPropertyWebkitMarginStart:
- case CSSPropertyWebkitMarginBefore:
- case CSSPropertyWebkitMarginAfter:
- case CSSPropertyWebkitMarginBeforeCollapse:
- case CSSPropertyWebkitMarginTopCollapse:
- case CSSPropertyWebkitMarginAfterCollapse:
- case CSSPropertyWebkitMarginBottomCollapse:
- case CSSPropertyWebkitPaddingEnd:
- case CSSPropertyWebkitPaddingStart:
- case CSSPropertyWebkitPaddingBefore:
- case CSSPropertyWebkitPaddingAfter:
- case CSSPropertyWebkitLogicalWidth:
- case CSSPropertyWebkitLogicalHeight:
- case CSSPropertyWebkitMinLogicalWidth:
- case CSSPropertyWebkitMinLogicalHeight:
- case CSSPropertyWebkitMaxLogicalWidth:
- case CSSPropertyWebkitMaxLogicalHeight:
- {
- CSSPropertyID newId = CSSProperty::resolveDirectionAwareProperty(id, state.style()->direction(), state.style()->writingMode());
- ASSERT(newId != id);
- return applyProperty(newId, state, value);
- }
- case CSSPropertyFontStretch:
- case CSSPropertyPage:
- case CSSPropertyTextLineThroughColor:
- case CSSPropertyTextLineThroughMode:
- case CSSPropertyTextLineThroughStyle:
- case CSSPropertyTextLineThroughWidth:
- case CSSPropertyTextOverlineColor:
- case CSSPropertyTextOverlineMode:
- case CSSPropertyTextOverlineStyle:
- case CSSPropertyTextOverlineWidth:
- case CSSPropertyTextUnderlineColor:
- case CSSPropertyTextUnderlineMode:
- case CSSPropertyTextUnderlineStyle:
- case CSSPropertyTextUnderlineWidth:
- case CSSPropertyWebkitFontSizeDelta:
- case CSSPropertyWebkitTextDecorationsInEffect:
+void StyleBuilderFunctions::applyValueCSSPropertyPerspective(StyleResolverState& state, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
return;
-
- // CSS Text Layout Module Level 3: Vertical writing support
- case CSSPropertyWebkitWritingMode: {
- HANDLE_INHERIT_AND_INITIAL(writingMode, WritingMode);
-
- if (primitiveValue)
- state.setWritingMode(*primitiveValue);
-
- // FIXME: It is not ok to modify document state while applying style.
- if (state.element() && state.element() == state.document().documentElement())
- state.document().setWritingModeSetOnDocumentElement(true);
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->getValueID() == CSSValueNone) {
+ state.style()->setPerspective(0);
return;
}
- case CSSPropertyWebkitTextOrientation: {
- HANDLE_INHERIT_AND_INITIAL(textOrientation, TextOrientation);
-
- if (primitiveValue)
- state.setTextOrientation(*primitiveValue);
-
+ if (!primitiveValue->isLength())
return;
- }
-
- case CSSPropertyWebkitLineBoxContain: {
- HANDLE_INHERIT_AND_INITIAL(lineBoxContain, LineBoxContain)
- if (primitiveValue && primitiveValue->getValueID() == CSSValueNone) {
- state.style()->setLineBoxContain(LineBoxContainNone);
- return;
- }
-
- if (!value->isLineBoxContainValue())
- return;
+ float perspectiveValue = primitiveValue->computeLength<float>(state.cssToLengthConversionData());
+ if (perspectiveValue >= 0.0f)
+ state.style()->setPerspective(perspectiveValue);
+}
- state.style()->setLineBoxContain(toCSSLineBoxContainValue(value)->value());
- return;
- }
+void StyleBuilderFunctions::applyInitialCSSPropertyInternalCallback(StyleResolverState& state)
+{
+}
- // CSS Fonts Module Level 3
- case CSSPropertyWebkitFontFeatureSettings: {
- if (primitiveValue && primitiveValue->getValueID() == CSSValueNormal) {
- state.fontBuilder().setFeatureSettingsNormal();
- return;
- }
+void StyleBuilderFunctions::applyInheritCSSPropertyInternalCallback(StyleResolverState& state)
+{
+}
- if (!value->isValueList())
- return;
+void StyleBuilderFunctions::applyValueCSSPropertyInternalCallback(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue() && toCSSPrimitiveValue(value)->getValueID() == CSSValueInternalPresence)
+ state.style()->addCallbackSelector(state.currentRule()->selectorList().selectorsText());
+}
- state.fontBuilder().setFeatureSettingsValue(value);
- return;
- }
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitWritingMode(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue())
+ state.setWritingMode(*toCSSPrimitiveValue(value));
- case CSSPropertyWebkitFilter: {
- HANDLE_INHERIT_AND_INITIAL(filter, Filter);
- FilterOperations operations;
- if (FilterOperationResolver::createFilterOperations(value, state.cssToLengthConversionData(), operations, state))
- state.style()->setFilter(operations);
- return;
- }
- case CSSPropertyGridAutoColumns: {
- HANDLE_INHERIT_AND_INITIAL(gridAutoColumns, GridAutoColumns);
- GridTrackSize trackSize;
- if (!createGridTrackSize(value, trackSize, state))
- return;
- state.style()->setGridAutoColumns(trackSize);
- return;
- }
- case CSSPropertyGridAutoRows: {
- HANDLE_INHERIT_AND_INITIAL(gridAutoRows, GridAutoRows);
- GridTrackSize trackSize;
- if (!createGridTrackSize(value, trackSize, state))
- return;
- state.style()->setGridAutoRows(trackSize);
- return;
- }
- case CSSPropertyGridDefinitionColumns: {
- if (isInherit) {
- state.style()->setGridDefinitionColumns(state.parentStyle()->gridDefinitionColumns());
- state.style()->setNamedGridColumnLines(state.parentStyle()->namedGridColumnLines());
- state.style()->setOrderedNamedGridColumnLines(state.parentStyle()->orderedNamedGridColumnLines());
- return;
- }
- if (isInitial) {
- state.style()->setGridDefinitionColumns(RenderStyle::initialGridDefinitionColumns());
- state.style()->setNamedGridColumnLines(RenderStyle::initialNamedGridColumnLines());
- state.style()->setOrderedNamedGridColumnLines(RenderStyle::initialOrderedNamedGridColumnLines());
- return;
- }
+ // FIXME: It is not ok to modify document state while applying style.
+ if (state.element() && state.element() == state.document().documentElement())
+ state.document().setWritingModeSetOnDocumentElement(true);
+}
- Vector<GridTrackSize> trackSizes;
- NamedGridLinesMap namedGridLines;
- OrderedNamedGridLines orderedNamedGridLines;
- if (!createGridTrackList(value, trackSizes, namedGridLines, orderedNamedGridLines, state))
- return;
- state.style()->setGridDefinitionColumns(trackSizes);
- state.style()->setNamedGridColumnLines(namedGridLines);
- state.style()->setOrderedNamedGridColumnLines(orderedNamedGridLines);
- return;
- }
- case CSSPropertyGridDefinitionRows: {
- if (isInherit) {
- state.style()->setGridDefinitionRows(state.parentStyle()->gridDefinitionRows());
- state.style()->setNamedGridRowLines(state.parentStyle()->namedGridRowLines());
- state.style()->setOrderedNamedGridRowLines(state.parentStyle()->orderedNamedGridRowLines());
- return;
- }
- if (isInitial) {
- state.style()->setGridDefinitionRows(RenderStyle::initialGridDefinitionRows());
- state.style()->setNamedGridRowLines(RenderStyle::initialNamedGridRowLines());
- state.style()->setOrderedNamedGridRowLines(RenderStyle::initialOrderedNamedGridRowLines());
- return;
- }
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitTextOrientation(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue())
+ state.setTextOrientation(*toCSSPrimitiveValue(value));
+}
- Vector<GridTrackSize> trackSizes;
- NamedGridLinesMap namedGridLines;
- OrderedNamedGridLines orderedNamedGridLines;
- if (!createGridTrackList(value, trackSizes, namedGridLines, orderedNamedGridLines, state))
- return;
- state.style()->setGridDefinitionRows(trackSizes);
- state.style()->setNamedGridRowLines(namedGridLines);
- state.style()->setOrderedNamedGridRowLines(orderedNamedGridLines);
- return;
- }
+// FIXME: We should handle initial and inherit for font-feature-settings
+void StyleBuilderFunctions::applyInitialCSSPropertyWebkitFontFeatureSettings(StyleResolverState& state)
+{
+}
- case CSSPropertyGridColumnStart: {
- HANDLE_INHERIT_AND_INITIAL(gridColumnStart, GridColumnStart);
- GridPosition startPosition;
- if (!createGridPosition(value, startPosition))
- return;
- state.style()->setGridColumnStart(startPosition);
- return;
- }
- case CSSPropertyGridColumnEnd: {
- HANDLE_INHERIT_AND_INITIAL(gridColumnEnd, GridColumnEnd);
- GridPosition endPosition;
- if (!createGridPosition(value, endPosition))
- return;
- state.style()->setGridColumnEnd(endPosition);
- return;
- }
+void StyleBuilderFunctions::applyInheritCSSPropertyWebkitFontFeatureSettings(StyleResolverState& state)
+{
+}
- case CSSPropertyGridRowStart: {
- HANDLE_INHERIT_AND_INITIAL(gridRowStart, GridRowStart);
- GridPosition beforePosition;
- if (!createGridPosition(value, beforePosition))
- return;
- state.style()->setGridRowStart(beforePosition);
- return;
- }
- case CSSPropertyGridRowEnd: {
- HANDLE_INHERIT_AND_INITIAL(gridRowEnd, GridRowEnd);
- GridPosition afterPosition;
- if (!createGridPosition(value, afterPosition))
- return;
- state.style()->setGridRowEnd(afterPosition);
+void StyleBuilderFunctions::applyValueCSSPropertyWebkitFontFeatureSettings(StyleResolverState& state, CSSValue* value)
+{
+ if (value->isPrimitiveValue() && toCSSPrimitiveValue(value)->getValueID() == CSSValueNormal) {
+ state.fontBuilder().setFeatureSettingsNormal();
return;
}
- case CSSPropertyGridTemplate: {
- if (isInherit) {
- state.style()->setNamedGridArea(state.parentStyle()->namedGridArea());
- state.style()->setNamedGridAreaRowCount(state.parentStyle()->namedGridAreaRowCount());
- state.style()->setNamedGridAreaColumnCount(state.parentStyle()->namedGridAreaColumnCount());
- return;
- }
- if (isInitial) {
- state.style()->setNamedGridArea(RenderStyle::initialNamedGridArea());
- state.style()->setNamedGridAreaRowCount(RenderStyle::initialNamedGridAreaCount());
- state.style()->setNamedGridAreaColumnCount(RenderStyle::initialNamedGridAreaCount());
- return;
- }
-
- if (value->isPrimitiveValue()) {
- ASSERT(toCSSPrimitiveValue(value)->getValueID() == CSSValueNone);
- return;
- }
+ if (value->isValueList())
+ state.fontBuilder().setFeatureSettingsValue(value);
+}
- CSSGridTemplateValue* gridTemplateValue = toCSSGridTemplateValue(value);
- state.style()->setNamedGridArea(gridTemplateValue->gridAreaMap());
- state.style()->setNamedGridAreaRowCount(gridTemplateValue->rowCount());
- state.style()->setNamedGridAreaColumnCount(gridTemplateValue->columnCount());
- return;
- }
- // These properties are aliased and we already applied the property on the prefixed version.
- case CSSPropertyAnimationDelay:
- case CSSPropertyAnimationDirection:
- case CSSPropertyAnimationDuration:
- case CSSPropertyAnimationFillMode:
- case CSSPropertyAnimationIterationCount:
- case CSSPropertyAnimationName:
- case CSSPropertyAnimationPlayState:
- case CSSPropertyAnimationTimingFunction:
- case CSSPropertyTransitionDelay:
- case CSSPropertyTransitionDuration:
- case CSSPropertyTransitionProperty:
- case CSSPropertyTransitionTimingFunction:
- return;
- // These properties are implemented in StyleBuilder::applyProperty.
- case CSSPropertyBackgroundAttachment:
- case CSSPropertyBackgroundBlendMode:
- case CSSPropertyBackgroundClip:
- case CSSPropertyBackgroundColor:
- case CSSPropertyBackgroundImage:
- case CSSPropertyBackgroundOrigin:
- case CSSPropertyBackgroundPositionX:
- case CSSPropertyBackgroundPositionY:
- case CSSPropertyBackgroundRepeatX:
- case CSSPropertyBackgroundRepeatY:
- case CSSPropertyBackgroundSize:
- case CSSPropertyBorderBottomColor:
- case CSSPropertyBorderBottomLeftRadius:
- case CSSPropertyBorderBottomRightRadius:
- case CSSPropertyBorderBottomStyle:
- case CSSPropertyBorderBottomWidth:
- case CSSPropertyBorderCollapse:
- case CSSPropertyBorderImageOutset:
- case CSSPropertyBorderImageRepeat:
- case CSSPropertyBorderImageSlice:
- case CSSPropertyBorderImageSource:
- case CSSPropertyBorderImageWidth:
- case CSSPropertyBorderLeftColor:
- case CSSPropertyBorderLeftStyle:
- case CSSPropertyBorderLeftWidth:
- case CSSPropertyBorderRightColor:
- case CSSPropertyBorderRightStyle:
- case CSSPropertyBorderRightWidth:
- case CSSPropertyBorderTopColor:
- case CSSPropertyBorderTopLeftRadius:
- case CSSPropertyBorderTopRightRadius:
- case CSSPropertyBorderTopStyle:
- case CSSPropertyBorderTopWidth:
- case CSSPropertyBottom:
- case CSSPropertyBoxShadow:
- case CSSPropertyBoxSizing:
- case CSSPropertyCaptionSide:
- case CSSPropertyClear:
- case CSSPropertyClip:
- case CSSPropertyColor:
- case CSSPropertyCounterIncrement:
- case CSSPropertyCounterReset:
- case CSSPropertyCursor:
- case CSSPropertyDirection:
- case CSSPropertyDisplay:
- case CSSPropertyEmptyCells:
- case CSSPropertyFloat:
- case CSSPropertyFontKerning:
- case CSSPropertyFontSize:
- case CSSPropertyFontStyle:
- case CSSPropertyFontVariant:
- case CSSPropertyFontWeight:
- case CSSPropertyHeight:
- case CSSPropertyImageRendering:
- case CSSPropertyIsolation:
- case CSSPropertyLeft:
- case CSSPropertyLetterSpacing:
- case CSSPropertyLineHeight:
- case CSSPropertyListStyleImage:
- case CSSPropertyListStylePosition:
- case CSSPropertyListStyleType:
- case CSSPropertyMarginBottom:
- case CSSPropertyMarginLeft:
- case CSSPropertyMarginRight:
- case CSSPropertyMarginTop:
- case CSSPropertyMaxHeight:
- case CSSPropertyMaxWidth:
- case CSSPropertyMinHeight:
- case CSSPropertyMixBlendMode:
- case CSSPropertyMinWidth:
- case CSSPropertyObjectFit:
- case CSSPropertyOpacity:
- case CSSPropertyOrphans:
- case CSSPropertyOutlineColor:
- case CSSPropertyOutlineOffset:
- case CSSPropertyOutlineStyle:
- case CSSPropertyOutlineWidth:
- case CSSPropertyOverflowWrap:
- case CSSPropertyOverflowX:
- case CSSPropertyOverflowY:
- case CSSPropertyPaddingBottom:
- case CSSPropertyPaddingLeft:
- case CSSPropertyPaddingRight:
- case CSSPropertyPaddingTop:
- case CSSPropertyPageBreakAfter:
- case CSSPropertyPageBreakBefore:
- case CSSPropertyPageBreakInside:
- case CSSPropertyPointerEvents:
- case CSSPropertyPosition:
- case CSSPropertyResize:
- case CSSPropertyRight:
- case CSSPropertySize:
- case CSSPropertySpeak:
- case CSSPropertyTabSize:
- case CSSPropertyTableLayout:
- case CSSPropertyTextAlign:
- case CSSPropertyTextAlignLast:
- case CSSPropertyTextDecoration:
- case CSSPropertyTextDecorationLine:
- case CSSPropertyTextDecorationStyle:
- case CSSPropertyTextDecorationColor:
- case CSSPropertyTextIndent:
- case CSSPropertyTextJustify:
- case CSSPropertyTextOverflow:
- case CSSPropertyTextRendering:
- case CSSPropertyTextShadow:
- case CSSPropertyTextTransform:
- case CSSPropertyTop:
- case CSSPropertyTouchAction:
- case CSSPropertyTouchActionDelay:
- case CSSPropertyUnicodeBidi:
- case CSSPropertyVariable:
- case CSSPropertyVerticalAlign:
- case CSSPropertyVisibility:
- case CSSPropertyWebkitAnimationDelay:
- case CSSPropertyWebkitAnimationDirection:
- case CSSPropertyWebkitAnimationDuration:
- case CSSPropertyWebkitAnimationFillMode:
- case CSSPropertyWebkitAnimationIterationCount:
- case CSSPropertyWebkitAnimationName:
- case CSSPropertyWebkitAnimationPlayState:
- case CSSPropertyWebkitAnimationTimingFunction:
- case CSSPropertyWebkitAppearance:
- case CSSPropertyWebkitAspectRatio:
- case CSSPropertyWebkitBackfaceVisibility:
- case CSSPropertyWebkitBackgroundClip:
- case CSSPropertyWebkitBackgroundComposite:
- case CSSPropertyWebkitBackgroundOrigin:
- case CSSPropertyWebkitBackgroundSize:
- case CSSPropertyWebkitBorderFit:
- case CSSPropertyWebkitBorderHorizontalSpacing:
- case CSSPropertyWebkitBorderImage:
- case CSSPropertyWebkitBorderVerticalSpacing:
- case CSSPropertyWebkitBoxAlign:
- case CSSPropertyWebkitBoxDecorationBreak:
- case CSSPropertyWebkitBoxDirection:
- case CSSPropertyWebkitBoxFlex:
- case CSSPropertyWebkitBoxFlexGroup:
- case CSSPropertyWebkitBoxLines:
- case CSSPropertyWebkitBoxOrdinalGroup:
- case CSSPropertyWebkitBoxOrient:
- case CSSPropertyWebkitBoxPack:
- case CSSPropertyWebkitBoxShadow:
- case CSSPropertyWebkitColumnAxis:
- case CSSPropertyWebkitColumnBreakAfter:
- case CSSPropertyWebkitColumnBreakBefore:
- case CSSPropertyWebkitColumnBreakInside:
- case CSSPropertyWebkitColumnCount:
- case CSSPropertyColumnFill:
- case CSSPropertyWebkitColumnGap:
- case CSSPropertyWebkitColumnProgression:
- case CSSPropertyWebkitColumnRuleColor:
- case CSSPropertyWebkitColumnRuleStyle:
- case CSSPropertyWebkitColumnRuleWidth:
- case CSSPropertyWebkitColumnSpan:
- case CSSPropertyWebkitColumnWidth:
- case CSSPropertyAlignContent:
- case CSSPropertyAlignItems:
- case CSSPropertyAlignSelf:
- case CSSPropertyFlexBasis:
- case CSSPropertyFlexDirection:
- case CSSPropertyFlexGrow:
- case CSSPropertyFlexShrink:
- case CSSPropertyFlexWrap:
- case CSSPropertyJustifyContent:
- case CSSPropertyOrder:
- case CSSPropertyWebkitFlowFrom:
- case CSSPropertyWebkitFlowInto:
- case CSSPropertyWebkitFontSmoothing:
- case CSSPropertyWebkitFontVariantLigatures:
- case CSSPropertyWebkitHighlight:
- case CSSPropertyWebkitHyphenateCharacter:
- case CSSPropertyWebkitLineAlign:
- case CSSPropertyWebkitLineBreak:
- case CSSPropertyWebkitLineClamp:
- case CSSPropertyWebkitLineGrid:
- case CSSPropertyWebkitLineSnap:
- case CSSPropertyInternalMarqueeDirection:
- case CSSPropertyInternalMarqueeIncrement:
- case CSSPropertyInternalMarqueeRepetition:
- case CSSPropertyInternalMarqueeSpeed:
- case CSSPropertyInternalMarqueeStyle:
- case CSSPropertyWebkitMaskBoxImage:
- case CSSPropertyWebkitMaskBoxImageOutset:
- case CSSPropertyWebkitMaskBoxImageRepeat:
- case CSSPropertyWebkitMaskBoxImageSlice:
- case CSSPropertyWebkitMaskBoxImageSource:
- case CSSPropertyWebkitMaskBoxImageWidth:
- case CSSPropertyWebkitMaskClip:
- case CSSPropertyWebkitMaskComposite:
- case CSSPropertyWebkitMaskImage:
- case CSSPropertyWebkitMaskOrigin:
- case CSSPropertyWebkitMaskPositionX:
- case CSSPropertyWebkitMaskPositionY:
- case CSSPropertyWebkitMaskRepeatX:
- case CSSPropertyWebkitMaskRepeatY:
- case CSSPropertyWebkitMaskSize:
- case CSSPropertyWebkitPerspectiveOrigin:
- case CSSPropertyWebkitPerspectiveOriginX:
- case CSSPropertyWebkitPerspectiveOriginY:
- case CSSPropertyWebkitPrintColorAdjust:
- case CSSPropertyWebkitRegionBreakAfter:
- case CSSPropertyWebkitRegionBreakBefore:
- case CSSPropertyWebkitRegionBreakInside:
- case CSSPropertyWebkitRegionFragment:
- case CSSPropertyWebkitRtlOrdering:
- case CSSPropertyWebkitRubyPosition:
- case CSSPropertyWebkitTextCombine:
- case CSSPropertyTextUnderlinePosition:
- case CSSPropertyWebkitTextEmphasisColor:
- case CSSPropertyWebkitTextEmphasisPosition:
- case CSSPropertyWebkitTextEmphasisStyle:
- case CSSPropertyWebkitTextFillColor:
- case CSSPropertyWebkitTextSecurity:
- case CSSPropertyWebkitTextStrokeColor:
- case CSSPropertyWebkitTransformOriginX:
- case CSSPropertyWebkitTransformOriginY:
- case CSSPropertyWebkitTransformOriginZ:
- case CSSPropertyWebkitTransformStyle:
- case CSSPropertyWebkitTransitionDelay:
- case CSSPropertyWebkitTransitionDuration:
- case CSSPropertyWebkitTransitionProperty:
- case CSSPropertyWebkitTransitionTimingFunction:
- case CSSPropertyWebkitUserDrag:
- case CSSPropertyWebkitUserModify:
- case CSSPropertyWebkitUserSelect:
- case CSSPropertyWebkitClipPath:
- case CSSPropertyWebkitWrapFlow:
- case CSSPropertyShapeMargin:
- case CSSPropertyShapePadding:
- case CSSPropertyShapeImageThreshold:
- case CSSPropertyWebkitWrapThrough:
- case CSSPropertyShapeInside:
- case CSSPropertyShapeOutside:
- case CSSPropertyWhiteSpace:
- case CSSPropertyWidows:
- case CSSPropertyWidth:
- case CSSPropertyWordBreak:
- case CSSPropertyWordSpacing:
- case CSSPropertyWordWrap:
- case CSSPropertyZIndex:
- case CSSPropertyZoom:
- case CSSPropertyFontFamily:
- case CSSPropertyGridAutoFlow:
- case CSSPropertyMarker:
- case CSSPropertyAlignmentBaseline:
- case CSSPropertyBufferedRendering:
- case CSSPropertyClipRule:
- case CSSPropertyColorInterpolation:
- case CSSPropertyColorInterpolationFilters:
- case CSSPropertyColorRendering:
- case CSSPropertyDominantBaseline:
- case CSSPropertyFillRule:
- case CSSPropertyMaskSourceType:
- case CSSPropertyMaskType:
- case CSSPropertyShapeRendering:
- case CSSPropertyStrokeLinecap:
- case CSSPropertyStrokeLinejoin:
- case CSSPropertyTextAnchor:
- case CSSPropertyVectorEffect:
- case CSSPropertyWritingMode:
- case CSSPropertyClipPath:
- case CSSPropertyFillOpacity:
- case CSSPropertyFilter:
- case CSSPropertyFloodOpacity:
- case CSSPropertyKerning:
- case CSSPropertyMarkerEnd:
- case CSSPropertyMarkerMid:
- case CSSPropertyMarkerStart:
- case CSSPropertyMask:
- case CSSPropertyStopOpacity:
- case CSSPropertyStrokeDashoffset:
- case CSSPropertyStrokeMiterlimit:
- case CSSPropertyStrokeOpacity:
- case CSSPropertyStrokeWidth:
- ASSERT_NOT_REACHED();
- return;
- // Only used in @viewport rules
- case CSSPropertyMaxZoom:
- case CSSPropertyMinZoom:
- case CSSPropertyOrientation:
- case CSSPropertyUserZoom:
+void StyleBuilderFunctions::applyValueCSSPropertyBaselineShift(StyleResolverState& state, CSSValue* value)
+{
+ if (!value->isPrimitiveValue())
return;
- case CSSPropertyBaselineShift:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(baselineShift, BaselineShift);
- if (!primitiveValue)
+ SVGRenderStyle* svgStyle = state.style()->accessSVGStyle();
+ CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value);
+ if (primitiveValue->getValueID()) {
+ switch (primitiveValue->getValueID()) {
+ case CSSValueBaseline:
+ svgStyle->setBaselineShift(BS_BASELINE);
break;
-
- SVGRenderStyle* svgStyle = state.style()->accessSVGStyle();
- if (primitiveValue->getValueID()) {
- switch (primitiveValue->getValueID()) {
- case CSSValueBaseline:
- svgStyle->setBaselineShift(BS_BASELINE);
- break;
- case CSSValueSub:
- svgStyle->setBaselineShift(BS_SUB);
- break;
- case CSSValueSuper:
- svgStyle->setBaselineShift(BS_SUPER);
- break;
- default:
- break;
- }
- } else {
- svgStyle->setBaselineShift(BS_LENGTH);
- svgStyle->setBaselineShiftValue(SVGLength::fromCSSPrimitiveValue(primitiveValue));
- }
-
- break;
- }
- case CSSPropertyColorProfile:
- {
- // Not implemented.
- break;
- }
- // end of ident only properties
- case CSSPropertyFill:
- {
- SVGRenderStyle* svgStyle = state.style()->accessSVGStyle();
- if (isInherit) {
- const SVGRenderStyle* svgParentStyle = state.parentStyle()->svgStyle();
- svgStyle->setFillPaint(svgParentStyle->fillPaintType(), svgParentStyle->fillPaintColor(), svgParentStyle->fillPaintUri(), state.applyPropertyToRegularStyle(), state.applyPropertyToVisitedLinkStyle());
- return;
- }
- if (isInitial) {
- svgStyle->setFillPaint(SVGRenderStyle::initialFillPaintType(), SVGRenderStyle::initialFillPaintColor(), SVGRenderStyle::initialFillPaintUri(), state.applyPropertyToRegularStyle(), state.applyPropertyToVisitedLinkStyle());
- return;
- }
- if (value->isSVGPaint()) {
- SVGPaint* svgPaint = toSVGPaint(value);
- svgStyle->setFillPaint(svgPaint->paintType(), colorFromSVGColorCSSValue(svgPaint, state.style()->color()), svgPaint->uri(), state.applyPropertyToRegularStyle(), state.applyPropertyToVisitedLinkStyle());
- }
- break;
- }
- case CSSPropertyStroke:
- {
- SVGRenderStyle* svgStyle = state.style()->accessSVGStyle();
- if (isInherit) {
- const SVGRenderStyle* svgParentStyle = state.parentStyle()->svgStyle();
- svgStyle->setStrokePaint(svgParentStyle->strokePaintType(), svgParentStyle->strokePaintColor(), svgParentStyle->strokePaintUri(), state.applyPropertyToRegularStyle(), state.applyPropertyToVisitedLinkStyle());
- return;
- }
- if (isInitial) {
- svgStyle->setStrokePaint(SVGRenderStyle::initialStrokePaintType(), SVGRenderStyle::initialStrokePaintColor(), SVGRenderStyle::initialStrokePaintUri(), state.applyPropertyToRegularStyle(), state.applyPropertyToVisitedLinkStyle());
- return;
- }
- if (value->isSVGPaint()) {
- SVGPaint* svgPaint = toSVGPaint(value);
- svgStyle->setStrokePaint(svgPaint->paintType(), colorFromSVGColorCSSValue(svgPaint, state.style()->color()), svgPaint->uri(), state.applyPropertyToRegularStyle(), state.applyPropertyToVisitedLinkStyle());
- }
- break;
- }
- case CSSPropertyStrokeDasharray:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(strokeDashArray, StrokeDashArray)
- if (!value->isValueList()) {
- state.style()->accessSVGStyle()->setStrokeDashArray(SVGRenderStyle::initialStrokeDashArray());
+ case CSSValueSub:
+ svgStyle->setBaselineShift(BS_SUB);
break;
- }
-
- CSSValueList* dashes = toCSSValueList(value);
-
- Vector<SVGLength> array;
- size_t length = dashes->length();
- for (size_t i = 0; i < length; ++i) {
- CSSValue* currValue = dashes->itemWithoutBoundsCheck(i);
- if (!currValue->isPrimitiveValue())
- continue;
-
- CSSPrimitiveValue* dash = toCSSPrimitiveValue(dashes->itemWithoutBoundsCheck(i));
- array.append(SVGLength::fromCSSPrimitiveValue(dash));
- }
-
- state.style()->accessSVGStyle()->setStrokeDashArray(array);
- break;
- }
- case CSSPropertyStopColor:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(stopColor, StopColor);
- if (value->isSVGColor())
- state.style()->accessSVGStyle()->setStopColor(colorFromSVGColorCSSValue(toSVGColor(value), state.style()->color()));
- break;
- }
- case CSSPropertyLightingColor:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(lightingColor, LightingColor);
- if (value->isSVGColor())
- state.style()->accessSVGStyle()->setLightingColor(colorFromSVGColorCSSValue(toSVGColor(value), state.style()->color()));
- break;
- }
- case CSSPropertyFloodColor:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(floodColor, FloodColor);
- if (value->isSVGColor())
- state.style()->accessSVGStyle()->setFloodColor(colorFromSVGColorCSSValue(toSVGColor(value), state.style()->color()));
- break;
- }
- case CSSPropertyGlyphOrientationHorizontal:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(glyphOrientationHorizontal, GlyphOrientationHorizontal)
- EGlyphOrientation orientation;
- if (degreeToGlyphOrientation(primitiveValue, orientation))
- state.style()->accessSVGStyle()->setGlyphOrientationHorizontal(orientation);
- break;
- }
- case CSSPropertyPaintOrder: {
- HANDLE_SVG_INHERIT_AND_INITIAL(paintOrder, PaintOrder)
- if (value->isValueList())
- state.style()->accessSVGStyle()->setPaintOrder(paintOrderFlattened(value));
- break;
- }
- case CSSPropertyGlyphOrientationVertical:
- {
- HANDLE_SVG_INHERIT_AND_INITIAL(glyphOrientationVertical, GlyphOrientationVertical)
- if (primitiveValue->getValueID() == CSSValueAuto) {
- state.style()->accessSVGStyle()->setGlyphOrientationVertical(GO_AUTO);
+ case CSSValueSuper:
+ svgStyle->setBaselineShift(BS_SUPER);
+ break;
+ default:
break;
}
- EGlyphOrientation orientation;
- if (degreeToGlyphOrientation(primitiveValue, orientation))
- state.style()->accessSVGStyle()->setGlyphOrientationVertical(orientation);
- break;
- }
- case CSSPropertyEnableBackground:
- // Silently ignoring this property for now
- // http://bugs.webkit.org/show_bug.cgi?id=6022
- break;
+ } else {
+ svgStyle->setBaselineShift(BS_LENGTH);
+ svgStyle->setBaselineShiftValue(SVGLength::fromCSSPrimitiveValue(primitiveValue));
}
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.cpp
index bc5cbdab5db..28b0cc9254b 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.cpp
@@ -29,41 +29,42 @@
#include "config.h"
#include "core/css/resolver/StyleResolver.h"
-#include "CSSPropertyNames.h"
-#include "HTMLNames.h"
-#include "RuntimeEnabledFeatures.h"
-#include "StylePropertyShorthand.h"
+#include "core/CSSPropertyNames.h"
+#include "core/HTMLNames.h"
+#include "core/StylePropertyShorthand.h"
#include "core/animation/ActiveAnimations.h"
-#include "core/animation/AnimatableLength.h"
#include "core/animation/AnimatableValue.h"
#include "core/animation/Animation.h"
-#include "core/animation/DocumentTimeline.h"
+#include "core/animation/AnimationTimeline.h"
#include "core/animation/css/CSSAnimatableValueFactory.h"
#include "core/animation/css/CSSAnimations.h"
+#include "core/animation/interpolation/StyleInterpolation.h"
#include "core/css/CSSCalculationValue.h"
#include "core/css/CSSDefaultStyleSheets.h"
-#include "core/css/CSSFontFace.h"
#include "core/css/CSSFontSelector.h"
#include "core/css/CSSKeyframeRule.h"
#include "core/css/CSSKeyframesRule.h"
-#include "core/css/CSSParser.h"
#include "core/css/CSSReflectValue.h"
#include "core/css/CSSRuleList.h"
#include "core/css/CSSSelector.h"
#include "core/css/CSSStyleRule.h"
#include "core/css/CSSValueList.h"
-#include "core/css/CSSVariableValue.h"
+#include "core/css/CSSValuePool.h"
#include "core/css/ElementRuleCollector.h"
+#include "core/css/FontFace.h"
#include "core/css/MediaQueryEvaluator.h"
#include "core/css/PageRuleCollector.h"
#include "core/css/StylePropertySet.h"
#include "core/css/StyleRuleImport.h"
#include "core/css/StyleSheetContents.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/resolver/AnimatedStyleBuilder.h"
#include "core/css/resolver/MatchResult.h"
#include "core/css/resolver/MediaQueryResult.h"
#include "core/css/resolver/SharedStyleFinder.h"
#include "core/css/resolver/StyleAdjuster.h"
+#include "core/css/resolver/StyleResolverParentScope.h"
+#include "core/css/resolver/StyleResolverState.h"
#include "core/css/resolver/StyleResolverStats.h"
#include "core/css/resolver/ViewportStyleResolver.h"
#include "core/dom/CSSSelectorWatch.h"
@@ -72,20 +73,18 @@
#include "core/dom/Text.h"
#include "core/dom/shadow/ElementShadow.h"
#include "core/dom/shadow/ShadowRoot.h"
+#include "core/frame/FrameView.h"
+#include "core/frame/LocalFrame.h"
#include "core/html/HTMLIFrameElement.h"
#include "core/inspector/InspectorInstrumentation.h"
-#include "core/frame/Frame.h"
-#include "core/frame/FrameView.h"
#include "core/rendering/RenderView.h"
#include "core/rendering/style/KeyframeList.h"
-#include "core/rendering/style/StyleCustomFilterProgramCache.h"
#include "core/svg/SVGDocumentExtensions.h"
#include "core/svg/SVGElement.h"
#include "core/svg/SVGFontFaceElement.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "wtf/StdLibExtras.h"
-using namespace std;
-
namespace {
using namespace WebCore;
@@ -94,8 +93,8 @@ void setAnimationUpdateIfNeeded(StyleResolverState& state, Element& element)
{
// If any changes to CSS Animations were detected, stash the update away for application after the
// render object is updated if we're in the appropriate scope.
- if (RuntimeEnabledFeatures::webAnimationsCSSEnabled() && state.animationUpdate())
- element.ensureActiveAnimations()->cssAnimations().setPendingUpdate(state.takeAnimationUpdate());
+ if (state.animationUpdate())
+ element.ensureActiveAnimations().cssAnimations().setPendingUpdate(state.takeAnimationUpdate());
}
} // namespace
@@ -124,9 +123,9 @@ static StylePropertySet* rightToLeftDeclaration()
static void addFontFaceRule(Document* document, CSSFontSelector* cssFontSelector, const StyleRuleFontFace* fontFaceRule)
{
- RefPtr<CSSFontFace> cssFontFace = CSSFontFace::createFromStyleRule(document, fontFaceRule);
- if (cssFontFace)
- cssFontSelector->addFontFaceRule(fontFaceRule, cssFontFace);
+ RefPtrWillBeRawPtr<FontFace> fontFace = FontFace::create(document, fontFaceRule);
+ if (fontFace)
+ cssFontSelector->fontFaceCache()->add(cssFontSelector, fontFaceRule, fontFace);
}
StyleResolver::StyleResolver(Document& document)
@@ -134,46 +133,31 @@ StyleResolver::StyleResolver(Document& document)
, m_viewportStyleResolver(ViewportStyleResolver::create(&document))
, m_needCollectFeatures(false)
, m_styleResourceLoader(document.fetcher())
+ , m_styleSharingDepth(0)
, m_styleResolverStatsSequence(0)
, m_accessCount(0)
{
- // FIXME: Why do this here instead of as part of resolving style on the root?
- CSSDefaultStyleSheets::loadDefaultStylesheetIfNecessary();
-
- // Construct document root element default style. This is needed
- // to evaluate media queries that contain relative constraints, like "screen and (max-width: 10em)"
- // This is here instead of constructor because when constructor is run,
- // Document doesn't have documentElement.
- // NOTE: This assumes that element that gets passed to the styleForElement call
- // is always from the document that owns the StyleResolver.
FrameView* view = document.view();
if (view)
- m_medium = adoptPtr(new MediaQueryEvaluator(view->mediaType()));
+ m_medium = adoptPtr(new MediaQueryEvaluator(view->mediaType(), &view->frame()));
else
m_medium = adoptPtr(new MediaQueryEvaluator("all"));
- Element* root = document.documentElement();
- if (root)
- m_rootDefaultStyle = styleForElement(root, 0, DisallowStyleSharing, MatchOnlyUserAgentRules);
-
- if (m_rootDefaultStyle && view)
- m_medium = adoptPtr(new MediaQueryEvaluator(view->mediaType(), &view->frame(), m_rootDefaultStyle.get()));
-
m_styleTree.clear();
initWatchedSelectorRules(CSSSelectorWatch::from(document).watchedCallbackSelectors());
#if ENABLE(SVG_FONTS)
if (document.svgExtensions()) {
- const HashSet<SVGFontFaceElement*>& svgFontFaceElements = document.svgExtensions()->svgFontFaceElements();
- HashSet<SVGFontFaceElement*>::const_iterator end = svgFontFaceElements.end();
- for (HashSet<SVGFontFaceElement*>::const_iterator it = svgFontFaceElements.begin(); it != end; ++it)
+ const WillBeHeapHashSet<RawPtrWillBeMember<SVGFontFaceElement> >& svgFontFaceElements = document.svgExtensions()->svgFontFaceElements();
+ WillBeHeapHashSet<RawPtrWillBeMember<SVGFontFaceElement> >::const_iterator end = svgFontFaceElements.end();
+ for (WillBeHeapHashSet<RawPtrWillBeMember<SVGFontFaceElement> >::const_iterator it = svgFontFaceElements.begin(); it != end; ++it)
addFontFaceRule(&document, document.styleEngine()->fontSelector(), (*it)->fontFaceRule());
}
#endif
}
-void StyleResolver::initWatchedSelectorRules(const Vector<RefPtr<StyleRule> >& watchedSelectors)
+void StyleResolver::initWatchedSelectorRules(const WillBeHeapVector<RefPtrWillBeMember<StyleRule> >& watchedSelectors)
{
if (!watchedSelectors.size())
return;
@@ -182,14 +166,14 @@ void StyleResolver::initWatchedSelectorRules(const Vector<RefPtr<StyleRule> >& w
m_watchedSelectorsRules->addStyleRule(watchedSelectors[i].get(), RuleHasNoSpecialState);
}
-void StyleResolver::lazyAppendAuthorStyleSheets(unsigned firstNew, const Vector<RefPtr<CSSStyleSheet> >& styleSheets)
+void StyleResolver::lazyAppendAuthorStyleSheets(unsigned firstNew, const WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> >& styleSheets)
{
unsigned size = styleSheets.size();
for (unsigned i = firstNew; i < size; ++i)
m_pendingStyleSheets.add(styleSheets[i].get());
}
-void StyleResolver::removePendingAuthorStyleSheets(const Vector<RefPtr<CSSStyleSheet> >& styleSheets)
+void StyleResolver::removePendingAuthorStyleSheets(const WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> >& styleSheets)
{
for (unsigned i = 0; i < styleSheets.size(); ++i)
m_pendingStyleSheets.remove(styleSheets[i].get());
@@ -202,33 +186,31 @@ void StyleResolver::appendCSSStyleSheet(CSSStyleSheet* cssSheet)
if (cssSheet->mediaQueries() && !m_medium->eval(cssSheet->mediaQueries(), &m_viewportDependentMediaQueryResults))
return;
- StyleSheetContents* sheet = cssSheet->contents();
ContainerNode* scopingNode = ScopedStyleResolver::scopingNodeFor(document(), cssSheet);
if (!scopingNode)
return;
ScopedStyleResolver* resolver = ensureScopedStyleResolver(scopingNode);
ASSERT(resolver);
- resolver->addRulesFromSheet(sheet, *m_medium, this);
- m_inspectorCSSOMWrappers.collectFromStyleSheetIfNeeded(cssSheet);
+ resolver->addRulesFromSheet(cssSheet, *m_medium, this);
}
void StyleResolver::appendPendingAuthorStyleSheets()
{
setBuildScopedStyleTreeInDocumentOrder(false);
- for (ListHashSet<CSSStyleSheet*, 16>::iterator it = m_pendingStyleSheets.begin(); it != m_pendingStyleSheets.end(); ++it)
+ for (WillBeHeapListHashSet<RawPtrWillBeMember<CSSStyleSheet>, 16>::iterator it = m_pendingStyleSheets.begin(); it != m_pendingStyleSheets.end(); ++it)
appendCSSStyleSheet(*it);
m_pendingStyleSheets.clear();
finishAppendAuthorStyleSheets();
}
-void StyleResolver::appendAuthorStyleSheets(unsigned firstNew, const Vector<RefPtr<CSSStyleSheet> >& styleSheets)
+void StyleResolver::appendAuthorStyleSheets(const WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> >& styleSheets)
{
// This handles sheets added to the end of the stylesheet list only. In other cases the style resolver
// needs to be reconstructed. To handle insertions too the rule order numbers would need to be updated.
unsigned size = styleSheets.size();
- for (unsigned i = firstNew; i < size; ++i)
+ for (unsigned i = 0; i < size; ++i)
appendCSSStyleSheet(styleSheets[i].get());
}
@@ -236,8 +218,8 @@ void StyleResolver::finishAppendAuthorStyleSheets()
{
collectFeatures();
- if (document().renderer() && document().renderer()->style())
- document().renderer()->style()->font().update(document().styleEngine()->fontSelector());
+ if (document().renderView() && document().renderView()->style())
+ document().renderView()->style()->font().update(document().styleEngine()->fontSelector());
collectViewportRules();
@@ -253,43 +235,31 @@ void StyleResolver::resetRuleFeatures()
m_needCollectFeatures = true;
}
-void StyleResolver::addTreeBoundaryCrossingRules(const Vector<MinimalRuleData>& rules, ContainerNode* scope)
+void StyleResolver::processScopedRules(const RuleSet& authorRules, CSSStyleSheet* parentStyleSheet, ContainerNode& scope)
{
- for (unsigned i = 0; i < rules.size(); ++i) {
- const MinimalRuleData& info = rules[i];
- m_treeBoundaryCrossingRules.addRule(info.m_rule, info.m_selectorIndex, scope, info.m_flags);
- }
-}
-
-void StyleResolver::processScopedRules(const RuleSet& authorRules, const KURL& sheetBaseURL, ContainerNode* scope)
-{
- const Vector<StyleRuleKeyframes*> keyframesRules = authorRules.keyframesRules();
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRuleKeyframes> > keyframesRules = authorRules.keyframesRules();
for (unsigned i = 0; i < keyframesRules.size(); ++i)
- ensureScopedStyleResolver(scope)->addKeyframeStyle(keyframesRules[i]);
+ ensureScopedStyleResolver(&scope)->addKeyframeStyle(keyframesRules[i]);
- addTreeBoundaryCrossingRules(authorRules.treeBoundaryCrossingRules(), scope);
+ m_treeBoundaryCrossingRules.addTreeBoundaryCrossingRules(authorRules, scope, parentStyleSheet);
// FIXME(BUG 72461): We don't add @font-face rules of scoped style sheets for the moment.
- if (!scope || scope->isDocumentNode()) {
- const Vector<StyleRuleFontFace*> fontFaceRules = authorRules.fontFaceRules();
+ if (scope.isDocumentNode()) {
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRuleFontFace> > fontFaceRules = authorRules.fontFaceRules();
for (unsigned i = 0; i < fontFaceRules.size(); ++i)
addFontFaceRule(&m_document, document().styleEngine()->fontSelector(), fontFaceRules[i]);
if (fontFaceRules.size())
invalidateMatchedPropertiesCache();
- } else {
- addTreeBoundaryCrossingRules(authorRules.shadowDistributedRules(), scope);
}
}
void StyleResolver::resetAuthorStyle(const ContainerNode* scopingNode)
{
- // FIXME: When chanking scoped attribute, scopingNode's hasScopedHTMLStyleChild has been already modified.
- // So we cannot use hasScopedHTMLStyleChild flag here.
ScopedStyleResolver* resolver = scopingNode ? m_styleTree.lookupScopedStyleResolverFor(scopingNode) : m_styleTree.scopedStyleResolverForDocument();
if (!resolver)
return;
- treeBoundaryCrossingRules().reset(scopingNode);
+ m_treeBoundaryCrossingRules.reset(scopingNode);
resolver->resetAuthorStyle();
resetRuleFeatures();
@@ -299,12 +269,12 @@ void StyleResolver::resetAuthorStyle(const ContainerNode* scopingNode)
m_styleTree.remove(scopingNode);
}
-static PassOwnPtr<RuleSet> makeRuleSet(const Vector<RuleFeature>& rules)
+static PassOwnPtrWillBeRawPtr<RuleSet> makeRuleSet(const WillBeHeapVector<RuleFeature>& rules)
{
size_t size = rules.size();
if (!size)
return nullptr;
- OwnPtr<RuleSet> ruleSet = RuleSet::create();
+ OwnPtrWillBeRawPtr<RuleSet> ruleSet = RuleSet::create();
for (size_t i = 0; i < size; ++i)
ruleSet->addRule(rules[i].rule, rules[i].selectorIndex, rules[i].hasDocumentSecurityOrigin ? RuleHasDocumentSecurityOrigin : RuleHasNoSpecialState);
return ruleSet.release();
@@ -316,11 +286,15 @@ void StyleResolver::collectFeatures()
// Collect all ids and rules using sibling selectors (:first-child and similar)
// in the current set of stylesheets. Style sharing code uses this information to reject
// sharing candidates.
- if (CSSDefaultStyleSheets::defaultStyle)
- m_features.add(CSSDefaultStyleSheets::defaultStyle->features());
+ CSSDefaultStyleSheets& defaultStyleSheets = CSSDefaultStyleSheets::instance();
+ if (defaultStyleSheets.defaultStyle())
+ m_features.add(defaultStyleSheets.defaultStyle()->features());
if (document().isViewSource())
- m_features.add(CSSDefaultStyleSheets::viewSourceStyle()->features());
+ m_features.add(defaultStyleSheets.defaultViewSourceStyle()->features());
+
+ if (document().isTransitionDocument())
+ m_features.add(defaultStyleSheets.defaultTransitionStyle()->features());
if (m_watchedSelectorsRules)
m_features.add(m_watchedSelectorsRules->features());
@@ -336,7 +310,7 @@ void StyleResolver::collectFeatures()
bool StyleResolver::hasRulesForId(const AtomicString& id) const
{
- return m_features.idsInRules.contains(id);
+ return m_features.hasSelectorForId(id);
}
void StyleResolver::addToStyleSharingList(Element& element)
@@ -346,20 +320,29 @@ void StyleResolver::addToStyleSharingList(Element& element)
if (!document().inStyleRecalc())
return;
INCREMENT_STYLE_STATS_COUNTER(*this, sharedStyleCandidates);
- if (m_styleSharingList.size() >= styleSharingListSize)
- m_styleSharingList.remove(--m_styleSharingList.end());
- m_styleSharingList.prepend(&element);
+ StyleSharingList& list = styleSharingList();
+ if (list.size() >= styleSharingListSize)
+ list.remove(--list.end());
+ list.prepend(&element);
}
-void StyleResolver::clearStyleSharingList()
+StyleSharingList& StyleResolver::styleSharingList()
{
- m_styleSharingList.clear();
+ m_styleSharingLists.resize(styleSharingMaxDepth);
+
+ // We never put things at depth 0 into the list since that's only the <html> element
+ // and it has no siblings or cousins to share with.
+ unsigned depth = std::max(std::min(m_styleSharingDepth, styleSharingMaxDepth), 1u) - 1u;
+ ASSERT(depth >= 0);
+
+ if (!m_styleSharingLists[depth])
+ m_styleSharingLists[depth] = adoptPtr(new StyleSharingList);
+ return *m_styleSharingLists[depth];
}
-void StyleResolver::fontsNeedUpdate(FontSelector* fontSelector)
+void StyleResolver::clearStyleSharingList()
{
- invalidateMatchedPropertiesCache();
- m_document.setNeedsStyleRecalc();
+ m_styleSharingLists.resize(0);
}
void StyleResolver::pushParentElement(Element& parent)
@@ -403,39 +386,11 @@ void StyleResolver::popParentShadowRoot(const ShadowRoot& shadowRoot)
StyleResolver::~StyleResolver()
{
- m_viewportStyleResolver->clearDocument();
-}
-
-inline void StyleResolver::collectTreeBoundaryCrossingRules(Element* element, ElementRuleCollector& collector, bool includeEmptyRules)
-{
- if (m_treeBoundaryCrossingRules.isEmpty())
- return;
-
- RuleRange ruleRange = collector.matchedResult().ranges.authorRuleRange();
-
- CascadeOrder cascadeOrder = 0;
-
- DocumentOrderedList::iterator it = m_treeBoundaryCrossingRules.end();
- while (it != m_treeBoundaryCrossingRules.begin()) {
- --it;
- const ContainerNode* scopingNode = toContainerNode(*it);
- RuleSet* ruleSet = m_treeBoundaryCrossingRules.ruleSetScopedBy(scopingNode);
- unsigned boundaryBehavior = SelectorChecker::CrossesBoundary | SelectorChecker::ScopeContainsLastMatchedElement;
-
- // If a given scoping node is a shadow root and a given element is in a descendant tree of tree hosted by
- // the scoping node's shadow host, we should use ScopeIsShadowHost.
- if (scopingNode && scopingNode->isShadowRoot()) {
- if (element->isInDescendantTreeOf(toShadowRoot(scopingNode)->host()))
- boundaryBehavior |= SelectorChecker::ScopeIsShadowHost;
- scopingNode = toShadowRoot(scopingNode)->host();
- }
- collector.collectMatchingRules(MatchRequest(ruleSet, includeEmptyRules, scopingNode), ruleRange, static_cast<SelectorChecker::BehaviorAtBoundary>(boundaryBehavior), ignoreCascadeScope, cascadeOrder++);
- }
}
static inline bool applyAuthorStylesOf(const Element* element)
{
- return element->treeScope().applyAuthorStyles() || (element->shadow() && element->shadow()->applyAuthorStyles());
+ return element->treeScope().applyAuthorStyles();
}
void StyleResolver::matchAuthorRulesForShadowHost(Element* element, ElementRuleCollector& collector, bool includeEmptyRules, Vector<ScopedStyleResolver*, 8>& resolvers, Vector<ScopedStyleResolver*, 8>& resolversInShadowTree)
@@ -456,7 +411,7 @@ void StyleResolver::matchAuthorRulesForShadowHost(Element* element, ElementRuleC
for (unsigned i = 0; i < resolvers.size(); ++i)
resolvers.at(i)->collectMatchingAuthorRules(collector, includeEmptyRules, applyAuthorStyles, cascadeScope++, --cascadeOrder);
- collectTreeBoundaryCrossingRules(element, collector, includeEmptyRules);
+ m_treeBoundaryCrossingRules.collectTreeBoundaryCrossingRules(element, collector, includeEmptyRules);
collector.sortAndTransferMatchedRules();
}
@@ -468,7 +423,7 @@ void StyleResolver::matchAuthorRules(Element* element, ElementRuleCollector& col
bool applyAuthorStyles = applyAuthorStylesOf(element);
if (m_styleTree.hasOnlyScopedResolverForDocument()) {
m_styleTree.scopedStyleResolverForDocument()->collectMatchingAuthorRules(collector, includeEmptyRules, applyAuthorStyles, ignoreCascadeScope);
- collectTreeBoundaryCrossingRules(element, collector, includeEmptyRules);
+ m_treeBoundaryCrossingRules.collectTreeBoundaryCrossingRules(element, collector, includeEmptyRules);
collector.sortAndTransferMatchedRules();
return;
}
@@ -494,7 +449,7 @@ void StyleResolver::matchAuthorRules(Element* element, ElementRuleCollector& col
resolver->collectMatchingAuthorRules(collector, includeEmptyRules, applyAuthorStyles, cascadeScope++, resolver->treeScope() == element->treeScope() && resolver->scopingNode().isShadowRoot() ? 0 : cascadeOrder);
}
- collectTreeBoundaryCrossingRules(element, collector, includeEmptyRules);
+ m_treeBoundaryCrossingRules.collectTreeBoundaryCrossingRules(element, collector, includeEmptyRules);
collector.sortAndTransferMatchedRules();
}
@@ -509,7 +464,6 @@ void StyleResolver::matchWatchSelectorRules(ElementRuleCollector& collector)
MatchRequest matchRequest(m_watchedSelectorsRules.get());
RuleRange ruleRange = collector.matchedResult().ranges.userRuleRange();
collector.collectMatchingRules(matchRequest, ruleRange);
- collector.collectMatchingRulesForRegion(matchRequest, ruleRange);
collector.sortAndTransferMatchedRules();
}
@@ -518,17 +472,21 @@ void StyleResolver::matchUARules(ElementRuleCollector& collector)
{
collector.setMatchingUARules(true);
+ CSSDefaultStyleSheets& defaultStyleSheets = CSSDefaultStyleSheets::instance();
RuleSet* userAgentStyleSheet = m_medium->mediaTypeMatchSpecific("print")
- ? CSSDefaultStyleSheets::defaultPrintStyle : CSSDefaultStyleSheets::defaultStyle;
+ ? defaultStyleSheets.defaultPrintStyle() : defaultStyleSheets.defaultStyle();
matchUARules(collector, userAgentStyleSheet);
// In quirks mode, we match rules from the quirks user agent sheet.
if (document().inQuirksMode())
- matchUARules(collector, CSSDefaultStyleSheets::defaultQuirksStyle);
+ matchUARules(collector, defaultStyleSheets.defaultQuirksStyle());
// If document uses view source styles (in view source mode or in xml viewer mode), then we match rules from the view source style sheet.
if (document().isViewSource())
- matchUARules(collector, CSSDefaultStyleSheets::viewSourceStyle());
+ matchUARules(collector, defaultStyleSheets.defaultViewSourceStyle());
+
+ if (document().isTransitionDocument())
+ matchUARules(collector, defaultStyleSheets.defaultTransitionStyle());
collector.setMatchingUARules(false);
@@ -582,33 +540,20 @@ void StyleResolver::matchAllRules(StyleResolverState& state, ElementRuleCollecto
}
}
-PassRefPtr<RenderStyle> StyleResolver::styleForDocument(Document& document, CSSFontSelector* fontSelector)
+PassRefPtr<RenderStyle> StyleResolver::styleForDocument(Document& document)
{
- const Frame* frame = document.frame();
+ const LocalFrame* frame = document.frame();
- // HTML5 states that seamless iframes should replace default CSS values
- // with values inherited from the containing iframe element. However,
- // some values (such as the case of designMode = "on") still need to
- // be set by this "document style".
RefPtr<RenderStyle> documentStyle = RenderStyle::create();
- bool seamlessWithParent = document.shouldDisplaySeamlesslyWithParent();
- if (seamlessWithParent) {
- RenderStyle* iframeStyle = document.seamlessParentIFrame()->renderStyle();
- if (iframeStyle)
- documentStyle->inheritFrom(iframeStyle);
- }
-
- // FIXME: It's not clear which values below we want to override in the seamless case!
documentStyle->setDisplay(BLOCK);
- if (!seamlessWithParent) {
- documentStyle->setRTLOrdering(document.visuallyOrdered() ? VisualOrder : LogicalOrder);
- documentStyle->setZoom(frame && !document.printing() ? frame->pageZoomFactor() : 1);
- documentStyle->setLocale(document.contentLanguage());
- }
- // This overrides any -webkit-user-modify inherited from the parent iframe.
+ documentStyle->setRTLOrdering(document.visuallyOrdered() ? VisualOrder : LogicalOrder);
+ documentStyle->setZoom(frame && !document.printing() ? frame->pageZoomFactor() : 1);
+ documentStyle->setLocale(document.contentLanguage());
+ documentStyle->setZIndex(0);
documentStyle->setUserModify(document.inDesignMode() ? READ_WRITE : READ_ONLY);
- document.setStyleDependentState(documentStyle.get());
+ document.setupFontBuilder(documentStyle.get());
+
return documentStyle.release();
}
@@ -631,11 +576,24 @@ static inline void resetDirectionAndWritingModeOnDocument(Document& document)
static void addContentAttrValuesToFeatures(const Vector<AtomicString>& contentAttrValues, RuleFeatureSet& features)
{
for (size_t i = 0; i < contentAttrValues.size(); ++i)
- features.attrsInRules.add(contentAttrValues[i]);
+ features.addContentAttr(contentAttrValues[i]);
+}
+
+void StyleResolver::adjustRenderStyle(StyleResolverState& state, Element* element)
+{
+ StyleAdjuster adjuster(m_document.inQuirksMode());
+ adjuster.adjustRenderStyle(state.style(), state.parentStyle(), element, state.cachedUAStyle());
+}
+
+// Start loading resources referenced by this style.
+void StyleResolver::loadPendingResources(StyleResolverState& state)
+{
+ m_styleResourceLoader.loadPendingResources(state.style(), state.elementStyleResources());
+ document().styleEngine()->fontSelector()->fontLoader()->loadPendingFonts();
}
PassRefPtr<RenderStyle> StyleResolver::styleForElement(Element* element, RenderStyle* defaultParent, StyleSharingBehavior sharingBehavior,
- RuleMatchingBehavior matchingBehavior, RenderRegion* regionForStyling)
+ RuleMatchingBehavior matchingBehavior)
{
ASSERT(document().frame());
ASSERT(documentSettings());
@@ -644,23 +602,26 @@ PassRefPtr<RenderStyle> StyleResolver::styleForElement(Element* element, RenderS
// Once an element has a renderer, we don't try to destroy it, since otherwise the renderer
// will vanish if a style recalc happens during loading.
- if (sharingBehavior == AllowStyleSharing && !element->document().haveStylesheetsLoaded() && !element->renderer()) {
+ if (sharingBehavior == AllowStyleSharing && !document().isRenderingReady() && !element->renderer()) {
if (!s_styleNotYetAvailable) {
s_styleNotYetAvailable = RenderStyle::create().leakRef();
s_styleNotYetAvailable->setDisplay(NONE);
s_styleNotYetAvailable->font().update(document().styleEngine()->fontSelector());
}
- element->document().setHasNodesWithPlaceholderStyle();
+
+ document().setHasNodesWithPlaceholderStyle();
return s_styleNotYetAvailable;
}
didAccess();
+ StyleResolverParentScope::ensureParentStackIsPushed();
+
if (element == document().documentElement())
resetDirectionAndWritingModeOnDocument(document());
- StyleResolverState state(document(), element, defaultParent, regionForStyling);
+ StyleResolverState state(document(), element, defaultParent);
- if (sharingBehavior == AllowStyleSharing && !state.distributedToInsertionPoint() && state.parentStyle()) {
+ if (sharingBehavior == AllowStyleSharing && state.parentStyle()) {
SharedStyleFinder styleFinder(state.elementContext(), m_features, m_siblingRuleSet.get(), m_uncommonAttributeRuleSet.get(), *this);
if (RefPtr<RenderStyle> sharedStyle = styleFinder.findSharedStyle())
return sharedStyle.release();
@@ -682,7 +643,7 @@ PassRefPtr<RenderStyle> StyleResolver::styleForElement(Element* element, RenderS
}
}
- state.fontBuilder().initForStyleResolve(state.document(), state.style(), state.useSVGZoomRules());
+ state.fontBuilder().initForStyleResolve(state.document(), state.style());
if (element->isLink()) {
state.style()->setIsLink(true);
@@ -696,41 +657,40 @@ PassRefPtr<RenderStyle> StyleResolver::styleForElement(Element* element, RenderS
}
bool needsCollection = false;
- CSSDefaultStyleSheets::ensureDefaultStyleSheetsForElement(element, needsCollection);
- if (needsCollection) {
+ CSSDefaultStyleSheets::instance().ensureDefaultStyleSheetsForElement(element, needsCollection);
+ if (needsCollection)
collectFeatures();
- m_inspectorCSSOMWrappers.reset();
- }
{
ElementRuleCollector collector(state.elementContext(), m_selectorFilter, state.style());
- collector.setRegionForStyling(regionForStyling);
- if (matchingBehavior == MatchOnlyUserAgentRules)
- matchUARules(collector);
- else
- matchAllRules(state, collector, matchingBehavior != MatchAllRulesExcludingSMIL);
+ matchAllRules(state, collector, matchingBehavior != MatchAllRulesExcludingSMIL);
applyMatchedProperties(state, collector.matchedResult());
addContentAttrValuesToFeatures(state.contentAttrValues(), m_features);
}
- {
- StyleAdjuster adjuster(state.cachedUAStyle(), m_document.inQuirksMode());
- adjuster.adjustRenderStyle(state.style(), state.parentStyle(), element);
- }
+
+ // Cache our original display.
+ state.style()->setOriginalDisplay(state.style()->display());
+
+ adjustRenderStyle(state, element);
// FIXME: The CSSWG wants to specify that the effects of animations are applied before
// important rules, but this currently happens here as we require adjustment to have happened
// before deciding which properties to transition.
- applyAnimatedProperties(state, element);
+ if (applyAnimatedProperties(state, element))
+ adjustRenderStyle(state, element);
// FIXME: Shouldn't this be on RenderBody::styleDidChange?
- if (element->hasTagName(bodyTag))
+ if (isHTMLBodyElement(*element))
document().textLinkColors().setTextColor(state.style()->color());
setAnimationUpdateIfNeeded(state, *element);
+ if (state.style()->hasViewportUnits())
+ document().setHasViewportUnits();
+
// Now return the style.
return state.takeStyle();
}
@@ -746,8 +706,7 @@ PassRefPtr<RenderStyle> StyleResolver::styleForKeyframe(Element* element, const
StyleResolverState state(document(), element, parentStyle);
MatchResult result;
- if (keyframe->properties())
- result.addMatchedProperties(keyframe->properties());
+ result.addMatchedProperties(&keyframe->properties());
ASSERT(!state.style());
@@ -755,28 +714,15 @@ PassRefPtr<RenderStyle> StyleResolver::styleForKeyframe(Element* element, const
state.setStyle(RenderStyle::clone(&elementStyle));
state.setLineHeightValue(0);
- // Make sure that the CSSAnimationData for the animation to which this
- // keyframe belongs is first in the list. This makes sure that if the
- // animation-timing-function property is set for this keyframe, it will be
- // applied to the correct CSSAnimationData object. Note that objects other
- // than the first in the list are ignored when reading the timing function
- // value. See KeyframeValue::timingFunction().
- CSSAnimationDataList* animations = state.style()->accessAnimations();
- ASSERT(animations && !animations->isEmpty());
- while (animations->animation(0)->name() != animationName)
- animations->remove(0);
- ASSERT(!animations->isEmpty() && animations->animation(0)->name() == animationName);
-
- state.fontBuilder().initForStyleResolve(state.document(), state.style(), state.useSVGZoomRules());
+ state.fontBuilder().initForStyleResolve(state.document(), state.style());
// We don't need to bother with !important. Since there is only ever one
// decl, there's nothing to override. So just add the first properties.
+ // We also don't need to bother with animation properties since the only
+ // relevant one is animation-timing-function and we special-case that in
+ // CSSAnimations.cpp
bool inheritedOnly = false;
- if (keyframe->properties()) {
- // FIXME: Can't keyframes contain variables?
- applyMatchedProperties<AnimationProperties>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
- applyMatchedProperties<HighPriorityProperties>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
- }
+ applyMatchedProperties<HighPriorityProperties>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
// If our font got dirtied, go ahead and update it now.
updateFont(state);
@@ -786,124 +732,73 @@ PassRefPtr<RenderStyle> StyleResolver::styleForKeyframe(Element* element, const
StyleBuilder::applyProperty(CSSPropertyLineHeight, state, state.lineHeightValue());
// Now do rest of the properties.
- if (keyframe->properties())
- applyMatchedProperties<LowPriorityProperties>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
+ applyMatchedProperties<LowPriorityProperties>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
// If our font got dirtied by one of the non-essential font props,
// go ahead and update it a second time.
updateFont(state);
- // Start loading resources referenced by this style.
- m_styleResourceLoader.loadPendingResources(state.style(), state.elementStyleResources());
- document().styleEngine()->fontSelector()->loadPendingFonts();
+ loadPendingResources(state);
didAccess();
return state.takeStyle();
}
-void StyleResolver::keyframeStylesForAnimation(Element* e, const RenderStyle& elementStyle, KeyframeList& list)
-{
- ASSERT(!RuntimeEnabledFeatures::webAnimationsCSSEnabled());
- list.clear();
-
- // Get the keyframesRule for this name
- if (!e || list.animationName().isEmpty())
- return;
-
- ASSERT(!hasPendingAuthorStyleSheets());
- const StyleRuleKeyframes* keyframesRule = CSSAnimations::matchScopedKeyframesRule(this, e, list.animationName().impl());
- if (!keyframesRule)
- return;
-
- // Construct and populate the style for each keyframe
- const AtomicString& name = list.animationName();
- const Vector<RefPtr<StyleKeyframe> >& keyframes = keyframesRule->keyframes();
- for (unsigned i = 0; i < keyframes.size(); ++i) {
- // Apply the declaration to the style. This is a simplified version of the logic in styleForElement
- const StyleKeyframe* keyframe = keyframes[i].get();
-
- KeyframeValue keyframeValue(0, 0);
- keyframeValue.setStyle(styleForKeyframe(e, elementStyle, 0, keyframe, name));
- keyframeValue.addProperties(keyframe->properties());
-
- // Add this keyframe style to all the indicated key times
- const Vector<double>& keys = keyframe->keys();
- for (size_t keyIndex = 0; keyIndex < keys.size(); ++keyIndex) {
- keyframeValue.setKey(keys[keyIndex]);
- list.insert(keyframeValue);
- }
- }
-
- // If the 0% keyframe is missing, create it (but only if there is at least one other keyframe)
- int initialListSize = list.size();
- if (initialListSize > 0 && list[0].key()) {
- static StyleKeyframe* zeroPercentKeyframe;
- if (!zeroPercentKeyframe) {
- zeroPercentKeyframe = StyleKeyframe::create().leakRef();
- zeroPercentKeyframe->setKeyText("0%");
- }
- KeyframeValue keyframeValue(0, 0);
- keyframeValue.setStyle(styleForKeyframe(e, elementStyle, 0, zeroPercentKeyframe, name));
- keyframeValue.addProperties(zeroPercentKeyframe->properties());
- list.insert(keyframeValue);
- }
-
- // If the 100% keyframe is missing, create it (but only if there is at least one other keyframe)
- if (initialListSize > 0 && (list[list.size() - 1].key() != 1)) {
- static StyleKeyframe* hundredPercentKeyframe;
- if (!hundredPercentKeyframe) {
- hundredPercentKeyframe = StyleKeyframe::create().leakRef();
- hundredPercentKeyframe->setKeyText("100%");
- }
- KeyframeValue keyframeValue(1, 0);
- keyframeValue.setStyle(styleForKeyframe(e, elementStyle, 0, hundredPercentKeyframe, name));
- keyframeValue.addProperties(hundredPercentKeyframe->properties());
- list.insert(keyframeValue);
- }
-}
-
// This function is used by the WebAnimations JavaScript API method animate().
// FIXME: Remove this when animate() switches away from resolution-dependent parsing.
-PassRefPtr<KeyframeAnimationEffect> StyleResolver::createKeyframeAnimationEffect(Element& element, const Vector<RefPtr<MutableStylePropertySet> >& propertySetVector, KeyframeAnimationEffect::KeyframeVector& keyframes)
+PassRefPtrWillBeRawPtr<AnimatableValue> StyleResolver::createAnimatableValueSnapshot(Element& element, CSSPropertyID property, CSSValue& value)
{
- ASSERT(RuntimeEnabledFeatures::webAnimationsAPIEnabled());
- ASSERT(propertySetVector.size() == keyframes.size());
-
+ RefPtr<RenderStyle> style;
+ if (element.renderStyle())
+ style = RenderStyle::clone(element.renderStyle());
+ else
+ style = RenderStyle::create();
StyleResolverState state(element.document(), &element);
- state.setStyle(RenderStyle::create());
+ state.setStyle(style);
+ state.fontBuilder().initForStyleResolve(state.document(), state.style());
+ return createAnimatableValueSnapshot(state, property, value);
+}
- for (unsigned i = 0; i < propertySetVector.size(); ++i) {
- for (unsigned j = 0; j < propertySetVector[i]->propertyCount(); ++j) {
- CSSPropertyID id = propertySetVector[i]->propertyAt(j).id();
- StyleBuilder::applyProperty(id, state, propertySetVector[i]->getPropertyCSSValue(id).get());
- keyframes[i]->setPropertyValue(id, CSSAnimatableValueFactory::create(id, *state.style()).get());
- }
- }
- return KeyframeAnimationEffect::create(keyframes);
+PassRefPtrWillBeRawPtr<AnimatableValue> StyleResolver::createAnimatableValueSnapshot(StyleResolverState& state, CSSPropertyID property, CSSValue& value)
+{
+ StyleBuilder::applyProperty(property, state, &value);
+ return CSSAnimatableValueFactory::create(property, *state.style());
}
-PassRefPtr<PseudoElement> StyleResolver::createPseudoElementIfNeeded(Element& element, PseudoId pseudoId)
+PassRefPtrWillBeRawPtr<PseudoElement> StyleResolver::createPseudoElementIfNeeded(Element& parent, PseudoId pseudoId)
{
- RenderObject* renderer = element.renderer();
- if (!renderer)
- return 0;
+ RenderObject* parentRenderer = parent.renderer();
+ if (!parentRenderer)
+ return nullptr;
+
+ if (pseudoId < FIRST_INTERNAL_PSEUDOID && !parentRenderer->style()->hasPseudoStyle(pseudoId))
+ return nullptr;
- if (pseudoId < FIRST_INTERNAL_PSEUDOID && !renderer->style()->hasPseudoStyle(pseudoId))
- return 0;
+ if (pseudoId == BACKDROP && !parent.isInTopLayer())
+ return nullptr;
+
+ if (!parentRenderer->canHaveGeneratedChildren())
+ return nullptr;
- RenderStyle* parentStyle = renderer->style();
- StyleResolverState state(document(), &element, parentStyle);
- if (!pseudoStyleForElementInternal(element, pseudoId, parentStyle, state))
- return 0;
+ RenderStyle* parentStyle = parentRenderer->style();
+ if (RenderStyle* cachedStyle = parentStyle->getCachedPseudoStyle(pseudoId)) {
+ if (!pseudoElementRendererIsNeeded(cachedStyle))
+ return nullptr;
+ return PseudoElement::create(&parent, pseudoId);
+ }
+
+ StyleResolverState state(document(), &parent, parentStyle);
+ if (!pseudoStyleForElementInternal(parent, pseudoId, parentStyle, state))
+ return nullptr;
RefPtr<RenderStyle> style = state.takeStyle();
ASSERT(style);
+ parentStyle->addCachedPseudoStyle(style);
- if (!element.needsPseudoElement(pseudoId, *style))
- return 0;
+ if (!pseudoElementRendererIsNeeded(style.get()))
+ return nullptr;
- renderer->style()->addCachedPseudoStyle(style.release());
- RefPtr<PseudoElement> pseudo = PseudoElement::create(&element, pseudoId);
+ RefPtrWillBeRawPtr<PseudoElement> pseudo = PseudoElement::create(&parent, pseudoId);
setAnimationUpdateIfNeeded(state, *pseudo);
if (ActiveAnimations* activeAnimations = pseudo->activeAnimations())
@@ -917,6 +812,8 @@ bool StyleResolver::pseudoStyleForElementInternal(Element& element, const Pseudo
ASSERT(documentSettings());
ASSERT(pseudoStyleRequest.pseudoId != FIRST_LINE_INHERITED);
+ StyleResolverParentScope::ensureParentStackIsPushed();
+
if (pseudoStyleRequest.allowsInheritance(state.parentStyle())) {
state.setStyle(RenderStyle::create());
state.style()->inheritFrom(state.parentStyle());
@@ -925,7 +822,7 @@ bool StyleResolver::pseudoStyleForElementInternal(Element& element, const Pseudo
state.setParentStyle(RenderStyle::clone(state.style()));
}
- state.fontBuilder().initForStyleResolve(state.document(), state.style(), state.useSVGZoomRules());
+ state.fontBuilder().initForStyleResolve(state.document(), state.style());
// Since we don't use pseudo-elements in any of our quirk/print
// user agent rules, don't waste time walking those rules.
@@ -947,20 +844,25 @@ bool StyleResolver::pseudoStyleForElementInternal(Element& element, const Pseudo
addContentAttrValuesToFeatures(state.contentAttrValues(), m_features);
}
- {
- StyleAdjuster adjuster(state.cachedUAStyle(), m_document.inQuirksMode());
- // FIXME: Passing 0 as the Element* introduces a lot of complexity
- // in the adjustRenderStyle code.
- adjuster.adjustRenderStyle(state.style(), state.parentStyle(), 0);
- }
+
+ // Cache our original display.
+ state.style()->setOriginalDisplay(state.style()->display());
+
+ // FIXME: Passing 0 as the Element* introduces a lot of complexity
+ // in the adjustRenderStyle code.
+ adjustRenderStyle(state, 0);
// FIXME: The CSSWG wants to specify that the effects of animations are applied before
// important rules, but this currently happens here as we require adjustment to have happened
// before deciding which properties to transition.
- applyAnimatedProperties(state, element.pseudoElement(pseudoStyleRequest.pseudoId));
+ if (applyAnimatedProperties(state, element.pseudoElement(pseudoStyleRequest.pseudoId)))
+ adjustRenderStyle(state, 0);
didAccess();
+ if (state.style()->hasViewportUnits())
+ document().setHasViewportUnits();
+
return true;
}
@@ -968,11 +870,11 @@ PassRefPtr<RenderStyle> StyleResolver::pseudoStyleForElement(Element* element, c
{
ASSERT(parentStyle);
if (!element)
- return 0;
+ return nullptr;
StyleResolverState state(document(), element, parentStyle);
if (!pseudoStyleForElementInternal(*element, pseudoStyleRequest, parentStyle, state))
- return 0;
+ return nullptr;
if (PseudoElement* pseudoElement = element->pseudoElement(pseudoStyleRequest.pseudoId))
setAnimationUpdateIfNeeded(state, *pseudoElement);
@@ -992,11 +894,11 @@ PassRefPtr<RenderStyle> StyleResolver::styleForPage(int pageIndex)
ASSERT(rootElementStyle);
state.style()->inheritFrom(rootElementStyle);
- state.fontBuilder().initForStyleResolve(state.document(), state.style(), state.useSVGZoomRules());
+ state.fontBuilder().initForStyleResolve(state.document(), state.style());
PageRuleCollector collector(rootElementStyle, pageIndex);
- collector.matchPageRules(CSSDefaultStyleSheets::defaultPrintStyle);
+ collector.matchPageRules(CSSDefaultStyleSheets::instance().defaultPrintStyle());
if (ScopedStyleResolver* scopedResolver = m_styleTree.scopedStyleResolverForDocument())
scopedResolver->matchPageRules(collector);
@@ -1005,7 +907,6 @@ PassRefPtr<RenderStyle> StyleResolver::styleForPage(int pageIndex)
bool inheritedOnly = false;
MatchResult& result = collector.matchedResult();
- applyMatchedProperties<VariableDefinitions>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
applyMatchedProperties<HighPriorityProperties>(state, result, false, 0, result.matchedProperties.size() - 1, inheritedOnly);
// If our font got dirtied, go ahead and update it now.
@@ -1019,9 +920,7 @@ PassRefPtr<RenderStyle> StyleResolver::styleForPage(int pageIndex)
addContentAttrValuesToFeatures(state.contentAttrValues(), m_features);
- // Start loading resources referenced by this style.
- m_styleResourceLoader.loadPendingResources(state.style(), state.elementStyleResources());
- document().styleEngine()->fontSelector()->loadPendingFonts();
+ loadPendingResources(state);
didAccess();
@@ -1031,13 +930,14 @@ PassRefPtr<RenderStyle> StyleResolver::styleForPage(int pageIndex)
void StyleResolver::collectViewportRules()
{
- viewportStyleResolver()->collectViewportRules(CSSDefaultStyleSheets::defaultStyle, ViewportStyleResolver::UserAgentOrigin);
+ CSSDefaultStyleSheets& defaultStyleSheets = CSSDefaultStyleSheets::instance();
+ viewportStyleResolver()->collectViewportRules(defaultStyleSheets.defaultStyle(), ViewportStyleResolver::UserAgentOrigin);
if (!InspectorInstrumentation::applyViewportStyleOverride(&document(), this))
- viewportStyleResolver()->collectViewportRules(CSSDefaultStyleSheets::defaultViewportStyle, ViewportStyleResolver::UserAgentOrigin);
+ viewportStyleResolver()->collectViewportRules(defaultStyleSheets.defaultViewportStyle(), ViewportStyleResolver::UserAgentOrigin);
if (document().isMobileDocument())
- viewportStyleResolver()->collectViewportRules(CSSDefaultStyleSheets::xhtmlMobileProfileStyle(), ViewportStyleResolver::UserAgentOrigin);
+ viewportStyleResolver()->collectViewportRules(defaultStyleSheets.defaultXHTMLMobileProfileStyle(), ViewportStyleResolver::UserAgentOrigin);
if (ScopedStyleResolver* scopedResolver = m_styleTree.scopedStyleResolverForDocument())
scopedResolver->collectViewportRulesTo(this);
@@ -1049,7 +949,7 @@ PassRefPtr<RenderStyle> StyleResolver::defaultStyleForElement()
{
StyleResolverState state(document(), 0);
state.setStyle(RenderStyle::create());
- state.fontBuilder().initForStyleResolve(document(), state.style(), state.useSVGZoomRules());
+ state.fontBuilder().initForStyleResolve(document(), state.style());
state.style()->setLineHeight(RenderStyle::initialLineHeight());
state.setLineHeightValue(0);
state.fontBuilder().setInitial(state.style()->effectiveZoom());
@@ -1063,28 +963,19 @@ PassRefPtr<RenderStyle> StyleResolver::styleForText(Text* textNode)
NodeRenderingTraversal::ParentDetails parentDetails;
Node* parentNode = NodeRenderingTraversal::parent(textNode, &parentDetails);
- if (!parentNode || !parentNode->renderStyle() || parentDetails.resetStyleInheritance())
+ if (!parentNode || !parentNode->renderStyle())
return defaultStyleForElement();
return parentNode->renderStyle();
}
-bool StyleResolver::checkRegionStyle(Element* regionElement)
-{
- // FIXME (BUG 72472): We don't add @-webkit-region rules of scoped style sheets for the moment,
- // so all region rules are global by default. Verify whether that can stand or needs changing.
- if (ScopedStyleResolver* scopedResolver = m_styleTree.scopedStyleResolverForDocument()) {
- if (scopedResolver->checkRegionStyle(regionElement))
- return true;
- }
- return false;
-}
-
void StyleResolver::updateFont(StyleResolverState& state)
{
state.fontBuilder().createFont(document().styleEngine()->fontSelector(), state.parentStyle(), state.style());
+ if (state.fontBuilder().fontSizeHasViewportUnits())
+ state.style()->setHasViewportUnits();
}
-PassRefPtr<StyleRuleList> StyleResolver::styleRulesForElement(Element* element, unsigned rulesToInclude)
+PassRefPtrWillBeRawPtr<StyleRuleList> StyleResolver::styleRulesForElement(Element* element, unsigned rulesToInclude)
{
ASSERT(element);
StyleResolverState state(document(), element);
@@ -1094,19 +985,19 @@ PassRefPtr<StyleRuleList> StyleResolver::styleRulesForElement(Element* element,
return collector.matchedStyleRuleList();
}
-PassRefPtr<CSSRuleList> StyleResolver::pseudoCSSRulesForElement(Element* element, PseudoId pseudoId, unsigned rulesToInclude, ShouldIncludeStyleSheetInCSSOMWrapper includeDocument)
+PassRefPtrWillBeRawPtr<CSSRuleList> StyleResolver::pseudoCSSRulesForElement(Element* element, PseudoId pseudoId, unsigned rulesToInclude)
{
ASSERT(element);
StyleResolverState state(document(), element);
- ElementRuleCollector collector(state.elementContext(), m_selectorFilter, state.style(), includeDocument);
+ ElementRuleCollector collector(state.elementContext(), m_selectorFilter, state.style());
collector.setMode(SelectorChecker::CollectingCSSRules);
collectPseudoRulesForElement(element, collector, pseudoId, rulesToInclude);
return collector.matchedCSSRuleList();
}
-PassRefPtr<CSSRuleList> StyleResolver::cssRulesForElement(Element* element, unsigned rulesToInclude, ShouldIncludeStyleSheetInCSSOMWrapper includeDocument)
+PassRefPtrWillBeRawPtr<CSSRuleList> StyleResolver::cssRulesForElement(Element* element, unsigned rulesToInclude)
{
- return pseudoCSSRulesForElement(element, NOPSEUDO, rulesToInclude, includeDocument);
+ return pseudoCSSRulesForElement(element, NOPSEUDO, rulesToInclude);
}
void StyleResolver::collectPseudoRulesForElement(Element* element, ElementRuleCollector& collector, PseudoId pseudoId, unsigned rulesToInclude)
@@ -1125,11 +1016,8 @@ void StyleResolver::collectPseudoRulesForElement(Element* element, ElementRuleCo
// -------------------------------------------------------------------------------------
// this is mostly boring stuff on how to apply a certain rule to the renderstyle...
-void StyleResolver::applyAnimatedProperties(StyleResolverState& state, Element* animatingElement)
+bool StyleResolver::applyAnimatedProperties(StyleResolverState& state, Element* animatingElement)
{
- if (!RuntimeEnabledFeatures::webAnimationsCSSEnabled())
- return;
-
const Element* element = state.element();
ASSERT(element);
@@ -1139,61 +1027,45 @@ void StyleResolver::applyAnimatedProperties(StyleResolverState& state, Element*
ASSERT(animatingElement == element || !animatingElement || animatingElement->parentOrShadowHostElement() == element);
if (!(animatingElement && animatingElement->hasActiveAnimations())
- && !(state.style()->transitions() && !state.style()->transitions()->isEmpty())
- && !(state.style()->animations() && !state.style()->animations()->isEmpty()))
- return;
+ && !state.style()->transitions() && !state.style()->animations())
+ return false;
state.setAnimationUpdate(CSSAnimations::calculateUpdate(animatingElement, *element, *state.style(), state.parentStyle(), this));
if (!state.animationUpdate())
- return;
+ return false;
+
+ const WillBeHeapHashMap<CSSPropertyID, RefPtrWillBeMember<Interpolation> >& activeInterpolationsForAnimations = state.animationUpdate()->activeInterpolationsForAnimations();
+ const WillBeHeapHashMap<CSSPropertyID, RefPtrWillBeMember<Interpolation> >& activeInterpolationsForTransitions = state.animationUpdate()->activeInterpolationsForTransitions();
+ applyAnimatedProperties<HighPriorityProperties>(state, activeInterpolationsForAnimations);
+ applyAnimatedProperties<HighPriorityProperties>(state, activeInterpolationsForTransitions);
+
+ updateFont(state);
+
+ applyAnimatedProperties<LowPriorityProperties>(state, activeInterpolationsForAnimations);
+ applyAnimatedProperties<LowPriorityProperties>(state, activeInterpolationsForTransitions);
+
+ // Start loading resources used by animations.
+ loadPendingResources(state);
- const AnimationEffect::CompositableValueMap& compositableValuesForAnimations = state.animationUpdate()->compositableValuesForAnimations();
- const AnimationEffect::CompositableValueMap& compositableValuesForTransitions = state.animationUpdate()->compositableValuesForTransitions();
- applyAnimatedProperties<HighPriorityProperties>(state, compositableValuesForAnimations);
- applyAnimatedProperties<HighPriorityProperties>(state, compositableValuesForTransitions);
- applyAnimatedProperties<LowPriorityProperties>(state, compositableValuesForAnimations);
- applyAnimatedProperties<LowPriorityProperties>(state, compositableValuesForTransitions);
+ ASSERT(!state.fontBuilder().fontDirty());
- // If the animations/transitions change opacity or transform, we need to update
- // the style to impose the stacking rules. Note that this is also
- // done in StyleResolver::adjustRenderStyle().
- RenderStyle* style = state.style();
- if (style->hasAutoZIndex() && (style->opacity() < 1.0f || style->hasTransform()))
- style->setZIndex(0);
+ return true;
}
template <StyleResolver::StyleApplicationPass pass>
-void StyleResolver::applyAnimatedProperties(StyleResolverState& state, const AnimationEffect::CompositableValueMap& compositableValues)
+void StyleResolver::applyAnimatedProperties(StyleResolverState& state, const WillBeHeapHashMap<CSSPropertyID, RefPtrWillBeMember<Interpolation> >& activeInterpolations)
{
- ASSERT(RuntimeEnabledFeatures::webAnimationsCSSEnabled());
- ASSERT(pass != VariableDefinitions);
ASSERT(pass != AnimationProperties);
- for (AnimationEffect::CompositableValueMap::const_iterator iter = compositableValues.begin(); iter != compositableValues.end(); ++iter) {
+ for (WillBeHeapHashMap<CSSPropertyID, RefPtrWillBeMember<Interpolation> >::const_iterator iter = activeInterpolations.begin(); iter != activeInterpolations.end(); ++iter) {
CSSPropertyID property = iter->key;
if (!isPropertyForPass<pass>(property))
continue;
- ASSERT_WITH_MESSAGE(!iter->value->dependsOnUnderlyingValue(), "Web Animations not yet implemented: An interface for compositing onto the underlying value.");
- RefPtr<AnimatableValue> animatableValue = iter->value->compositeOnto(0);
- AnimatedStyleBuilder::applyProperty(property, state, animatableValue.get());
+ const StyleInterpolation* interpolation = toStyleInterpolation(iter->value.get());
+ interpolation->apply(state);
}
}
-// http://dev.w3.org/csswg/css3-regions/#the-at-region-style-rule
-// FIXME: add incremental support for other region styling properties.
-static inline bool isValidRegionStyleProperty(CSSPropertyID id)
-{
- switch (id) {
- case CSSPropertyBackgroundColor:
- case CSSPropertyColor:
- return true;
- default:
- break;
- }
-
- return false;
-}
-
static inline bool isValidCueStyleProperty(CSSPropertyID id)
{
switch (id) {
@@ -1242,36 +1114,237 @@ static inline bool isValidCueStyleProperty(CSSPropertyID id)
return false;
}
+static inline bool isValidFirstLetterStyleProperty(CSSPropertyID id)
+{
+ switch (id) {
+ // Valid ::first-letter properties listed in spec:
+ // http://www.w3.org/TR/css3-selectors/#application-in-css
+ case CSSPropertyBackgroundAttachment:
+ case CSSPropertyBackgroundBlendMode:
+ case CSSPropertyBackgroundClip:
+ case CSSPropertyBackgroundColor:
+ case CSSPropertyBackgroundImage:
+ case CSSPropertyBackgroundOrigin:
+ case CSSPropertyBackgroundPosition:
+ case CSSPropertyBackgroundPositionX:
+ case CSSPropertyBackgroundPositionY:
+ case CSSPropertyBackgroundRepeat:
+ case CSSPropertyBackgroundRepeatX:
+ case CSSPropertyBackgroundRepeatY:
+ case CSSPropertyBackgroundSize:
+ case CSSPropertyBorderBottomColor:
+ case CSSPropertyBorderBottomLeftRadius:
+ case CSSPropertyBorderBottomRightRadius:
+ case CSSPropertyBorderBottomStyle:
+ case CSSPropertyBorderBottomWidth:
+ case CSSPropertyBorderImageOutset:
+ case CSSPropertyBorderImageRepeat:
+ case CSSPropertyBorderImageSlice:
+ case CSSPropertyBorderImageSource:
+ case CSSPropertyBorderImageWidth:
+ case CSSPropertyBorderLeftColor:
+ case CSSPropertyBorderLeftStyle:
+ case CSSPropertyBorderLeftWidth:
+ case CSSPropertyBorderRightColor:
+ case CSSPropertyBorderRightStyle:
+ case CSSPropertyBorderRightWidth:
+ case CSSPropertyBorderTopColor:
+ case CSSPropertyBorderTopLeftRadius:
+ case CSSPropertyBorderTopRightRadius:
+ case CSSPropertyBorderTopStyle:
+ case CSSPropertyBorderTopWidth:
+ case CSSPropertyColor:
+ case CSSPropertyFloat:
+ case CSSPropertyFont:
+ case CSSPropertyFontFamily:
+ case CSSPropertyFontKerning:
+ case CSSPropertyFontSize:
+ case CSSPropertyFontStretch:
+ case CSSPropertyFontStyle:
+ case CSSPropertyFontVariant:
+ case CSSPropertyFontVariantLigatures:
+ case CSSPropertyFontWeight:
+ case CSSPropertyLetterSpacing:
+ case CSSPropertyLineHeight:
+ case CSSPropertyMarginBottom:
+ case CSSPropertyMarginLeft:
+ case CSSPropertyMarginRight:
+ case CSSPropertyMarginTop:
+ case CSSPropertyPaddingBottom:
+ case CSSPropertyPaddingLeft:
+ case CSSPropertyPaddingRight:
+ case CSSPropertyPaddingTop:
+ case CSSPropertyTextTransform:
+ case CSSPropertyVerticalAlign:
+ case CSSPropertyWebkitBackgroundClip:
+ case CSSPropertyWebkitBackgroundComposite:
+ case CSSPropertyWebkitBackgroundOrigin:
+ case CSSPropertyWebkitBackgroundSize:
+ case CSSPropertyWebkitBorderAfter:
+ case CSSPropertyWebkitBorderAfterColor:
+ case CSSPropertyWebkitBorderAfterStyle:
+ case CSSPropertyWebkitBorderAfterWidth:
+ case CSSPropertyWebkitBorderBefore:
+ case CSSPropertyWebkitBorderBeforeColor:
+ case CSSPropertyWebkitBorderBeforeStyle:
+ case CSSPropertyWebkitBorderBeforeWidth:
+ case CSSPropertyWebkitBorderEnd:
+ case CSSPropertyWebkitBorderEndColor:
+ case CSSPropertyWebkitBorderEndStyle:
+ case CSSPropertyWebkitBorderEndWidth:
+ case CSSPropertyWebkitBorderFit:
+ case CSSPropertyWebkitBorderHorizontalSpacing:
+ case CSSPropertyWebkitBorderImage:
+ case CSSPropertyWebkitBorderRadius:
+ case CSSPropertyWebkitBorderStart:
+ case CSSPropertyWebkitBorderStartColor:
+ case CSSPropertyWebkitBorderStartStyle:
+ case CSSPropertyWebkitBorderStartWidth:
+ case CSSPropertyWebkitBorderVerticalSpacing:
+ case CSSPropertyWebkitFontSmoothing:
+ case CSSPropertyWebkitMarginAfter:
+ case CSSPropertyWebkitMarginAfterCollapse:
+ case CSSPropertyWebkitMarginBefore:
+ case CSSPropertyWebkitMarginBeforeCollapse:
+ case CSSPropertyWebkitMarginBottomCollapse:
+ case CSSPropertyWebkitMarginCollapse:
+ case CSSPropertyWebkitMarginEnd:
+ case CSSPropertyWebkitMarginStart:
+ case CSSPropertyWebkitMarginTopCollapse:
+ case CSSPropertyWordSpacing:
+ return true;
+ case CSSPropertyTextDecorationColor:
+ case CSSPropertyTextDecorationLine:
+ case CSSPropertyTextDecorationStyle:
+ return RuntimeEnabledFeatures::css3TextDecorationsEnabled();
+
+ // text-shadow added in text decoration spec:
+ // http://www.w3.org/TR/css-text-decor-3/#text-shadow-property
+ case CSSPropertyTextShadow:
+ // box-shadox added in CSS3 backgrounds spec:
+ // http://www.w3.org/TR/css3-background/#placement
+ case CSSPropertyBoxShadow:
+ case CSSPropertyWebkitBoxShadow:
+ // Properties that we currently support outside of spec.
+ case CSSPropertyWebkitLineBoxContain:
+ case CSSPropertyVisibility:
+ return true;
+
+ default:
+ return false;
+ }
+}
+
+// FIXME: Consider refactoring to create a new class which owns the following
+// first/last/range properties.
+// This method returns the first CSSPropertyId of properties which generate
+// animations. All animation properties are obtained by using
+// firstCSSPropertyId<AnimationProperties> and
+// lastCSSPropertyId<AnimationProperties>.
+// c.f. //src/third_party/WebKit/Source/core/css/CSSPropertyNames.in.
+template<> CSSPropertyID StyleResolver::firstCSSPropertyId<StyleResolver::AnimationProperties>()
+{
+ COMPILE_ASSERT(firstCSSProperty == CSSPropertyDisplay, CSS_first_animation_property_should_be_first_property);
+ return CSSPropertyDisplay;
+}
+
+// This method returns the first CSSPropertyId of properties which generate
+// animations.
+template<> CSSPropertyID StyleResolver::lastCSSPropertyId<StyleResolver::AnimationProperties>()
+{
+ COMPILE_ASSERT(CSSPropertyTransitionTimingFunction == CSSPropertyColor - 1, CSS_transition_timing_is_last_animation_property);
+ return CSSPropertyTransitionTimingFunction;
+}
+
+// This method returns the first CSSPropertyId of high priority properties.
+// Other properties can depend on high priority properties. For example,
+// border-color property with currentColor value depends on color property.
+// All high priority properties are obtained by using
+// firstCSSPropertyId<HighPriorityProperties> and
+// lastCSSPropertyId<HighPriorityProperties>.
+template<> CSSPropertyID StyleResolver::firstCSSPropertyId<StyleResolver::HighPriorityProperties>()
+{
+ COMPILE_ASSERT(CSSPropertyTransitionTimingFunction + 1 == CSSPropertyColor, CSS_color_is_first_high_priority_property);
+ return CSSPropertyColor;
+}
+
+// This method returns the last CSSPropertyId of high priority properties.
+template<> CSSPropertyID StyleResolver::lastCSSPropertyId<StyleResolver::HighPriorityProperties>()
+{
+ COMPILE_ASSERT(CSSPropertyLineHeight == CSSPropertyColor + 17, CSS_line_height_is_end_of_high_prioity_property_range);
+ COMPILE_ASSERT(CSSPropertyZoom == CSSPropertyLineHeight - 1, CSS_zoom_is_before_line_height);
+ return CSSPropertyLineHeight;
+}
+
+// This method returns the first CSSPropertyId of remaining properties,
+// i.e. low priority properties. No properties depend on low priority
+// properties. So we don't need to resolve such properties quickly.
+// All low priority properties are obtained by using
+// firstCSSPropertyId<LowPriorityProperties> and
+// lastCSSPropertyId<LowPriorityProperties>.
+template<> CSSPropertyID StyleResolver::firstCSSPropertyId<StyleResolver::LowPriorityProperties>()
+{
+ COMPILE_ASSERT(CSSPropertyBackground == CSSPropertyLineHeight + 1, CSS_background_is_first_low_priority_property);
+ return CSSPropertyBackground;
+}
+
+// This method returns the last CSSPropertyId of low priority properties.
+template<> CSSPropertyID StyleResolver::lastCSSPropertyId<StyleResolver::LowPriorityProperties>()
+{
+ return static_cast<CSSPropertyID>(lastCSSProperty);
+}
+
template <StyleResolver::StyleApplicationPass pass>
bool StyleResolver::isPropertyForPass(CSSPropertyID property)
{
- COMPILE_ASSERT(CSSPropertyVariable < firstCSSProperty, CSS_variable_is_before_first_property);
- const CSSPropertyID firstAnimationProperty = CSSPropertyDisplay;
- const CSSPropertyID lastAnimationProperty = CSSPropertyTransitionTimingFunction;
- COMPILE_ASSERT(firstCSSProperty == firstAnimationProperty, CSS_first_animation_property_should_be_first_property);
- const CSSPropertyID firstHighPriorityProperty = CSSPropertyColor;
- const CSSPropertyID lastHighPriorityProperty = CSSPropertyLineHeight;
- COMPILE_ASSERT(lastAnimationProperty + 1 == firstHighPriorityProperty, CSS_color_is_first_high_priority_property);
- COMPILE_ASSERT(CSSPropertyLineHeight == firstHighPriorityProperty + 17, CSS_line_height_is_end_of_high_prioity_property_range);
- COMPILE_ASSERT(CSSPropertyZoom == lastHighPriorityProperty - 1, CSS_zoom_is_before_line_height);
- switch (pass) {
- case VariableDefinitions:
- return property == CSSPropertyVariable;
- case AnimationProperties:
- return property >= firstAnimationProperty && property <= lastAnimationProperty;
- case HighPriorityProperties:
- return property >= firstHighPriorityProperty && property <= lastHighPriorityProperty;
- case LowPriorityProperties:
- return property > lastHighPriorityProperty;
+ return firstCSSPropertyId<pass>() <= property && property <= lastCSSPropertyId<pass>();
+}
+
+// This method expands all shorthand property to longhand properties
+// considering StyleApplicationPass, and apply each expanded longhand property.
+// For example, if StyleApplicationPass is AnimationProperties, all shorthand
+// is expaneded to display, -webkit-animation, -webkit-animation-delay, ...,
+// transition-timing-function. So each property's value will be applied
+// according to all's value (initial, inherit or unset).
+template <StyleResolver::StyleApplicationPass pass>
+void StyleResolver::applyAllProperty(StyleResolverState& state, CSSValue* allValue)
+{
+ bool isUnsetValue = !allValue->isInitialValue() && !allValue->isInheritedValue();
+ unsigned startCSSProperty = firstCSSPropertyId<pass>();
+ unsigned endCSSProperty = lastCSSPropertyId<pass>();
+
+ for (unsigned i = startCSSProperty; i <= endCSSProperty; ++i) {
+ CSSPropertyID propertyId = static_cast<CSSPropertyID>(i);
+
+ // StyleBuilder does not allow any expanded shorthands.
+ if (isExpandedShorthandForAll(propertyId))
+ continue;
+
+ // all shorthand spec says:
+ // The all property is a shorthand that resets all CSS properties
+ // except direction and unicode-bidi.
+ // c.f. http://dev.w3.org/csswg/css-cascade/#all-shorthand
+ // We skip applyProperty when a given property is unicode-bidi or
+ // direction.
+ if (!CSSProperty::isAffectedByAllProperty(propertyId))
+ continue;
+
+ CSSValue* value;
+ if (!isUnsetValue) {
+ value = allValue;
+ } else {
+ if (CSSProperty::isInheritedProperty(propertyId))
+ value = cssValuePool().createInheritedValue().get();
+ else
+ value = cssValuePool().createExplicitInitialValue().get();
+ }
+ StyleBuilder::applyProperty(propertyId, state, value);
}
- ASSERT_NOT_REACHED();
- return false;
}
template <StyleResolver::StyleApplicationPass pass>
void StyleResolver::applyProperties(StyleResolverState& state, const StylePropertySet* properties, StyleRule* rule, bool isImportant, bool inheritedOnly, PropertyWhitelistType propertyWhitelistType)
{
- ASSERT((propertyWhitelistType != PropertyWhitelistRegion) || state.regionForStyling());
state.setCurrentRule(rule);
unsigned propertyCount = properties->propertyCount();
@@ -1279,6 +1352,13 @@ void StyleResolver::applyProperties(StyleResolverState& state, const StyleProper
StylePropertySet::PropertyReference current = properties->propertyAt(i);
if (isImportant != current.isImportant())
continue;
+
+ CSSPropertyID property = current.id();
+ if (property == CSSPropertyAll) {
+ applyAllProperty<pass>(state, current.value());
+ continue;
+ }
+
if (inheritedOnly && !current.isInherited()) {
// If the property value is explicitly inherited, we need to apply further non-inherited properties
// as they might override the value inherited here. For this reason we don't allow declarations with
@@ -1286,12 +1366,11 @@ void StyleResolver::applyProperties(StyleResolverState& state, const StyleProper
ASSERT(!current.value()->isInheritedValue());
continue;
}
- CSSPropertyID property = current.id();
- if (propertyWhitelistType == PropertyWhitelistRegion && !isValidRegionStyleProperty(property))
- continue;
if (propertyWhitelistType == PropertyWhitelistCue && !isValidCueStyleProperty(property))
continue;
+ if (propertyWhitelistType == PropertyWhitelistFirstLetter && !isValidFirstLetterStyleProperty(property))
+ continue;
if (!isPropertyForPass<pass>(property))
continue;
if (pass == HighPriorityProperties && property == CSSPropertyLineHeight)
@@ -1337,6 +1416,12 @@ void StyleResolver::invalidateMatchedPropertiesCache()
m_matchedPropertiesCache.clear();
}
+void StyleResolver::notifyResizeForViewportUnits()
+{
+ collectViewportRules();
+ m_matchedPropertiesCache.clearViewportDependent();
+}
+
void StyleResolver::applyMatchedProperties(StyleResolverState& state, const MatchResult& matchResult)
{
const Element* element = state.element();
@@ -1355,7 +1440,8 @@ void StyleResolver::applyMatchedProperties(StyleResolverState& state, const Matc
// style declarations. We then only need to apply the inherited properties, if any, as their values can depend on the
// element context. This is fast and saves memory by reusing the style data structures.
state.style()->copyNonInheritedFrom(cachedMatchedProperties->renderStyle.get());
- if (state.parentStyle()->inheritedDataShared(cachedMatchedProperties->parentRenderStyle.get()) && !isAtShadowBoundary(element)) {
+ if (state.parentStyle()->inheritedDataShared(cachedMatchedProperties->parentRenderStyle.get()) && !isAtShadowBoundary(element)
+ && (!state.distributedToInsertionPoint() || state.style()->userModify() == READ_ONLY)) {
INCREMENT_STYLE_STATS_COUNTER(*this, matchedPropertyCacheInheritedHit);
EInsideLink linkStatus = state.style()->insideLink();
@@ -1370,24 +1456,12 @@ void StyleResolver::applyMatchedProperties(StyleResolverState& state, const Matc
applyInheritedOnly = true;
}
- // First apply all variable definitions, as they may be used during application of later properties.
- applyMatchedProperties<VariableDefinitions>(state, matchResult, false, 0, matchResult.matchedProperties.size() - 1, applyInheritedOnly);
- applyMatchedProperties<VariableDefinitions>(state, matchResult, true, matchResult.ranges.firstAuthorRule, matchResult.ranges.lastAuthorRule, applyInheritedOnly);
- applyMatchedProperties<VariableDefinitions>(state, matchResult, true, matchResult.ranges.firstUserRule, matchResult.ranges.lastUserRule, applyInheritedOnly);
- applyMatchedProperties<VariableDefinitions>(state, matchResult, true, matchResult.ranges.firstUARule, matchResult.ranges.lastUARule, applyInheritedOnly);
-
// Apply animation properties in order to apply animation results and trigger transitions below.
applyMatchedProperties<AnimationProperties>(state, matchResult, false, 0, matchResult.matchedProperties.size() - 1, applyInheritedOnly);
applyMatchedProperties<AnimationProperties>(state, matchResult, true, matchResult.ranges.firstAuthorRule, matchResult.ranges.lastAuthorRule, applyInheritedOnly);
applyMatchedProperties<AnimationProperties>(state, matchResult, true, matchResult.ranges.firstUserRule, matchResult.ranges.lastUserRule, applyInheritedOnly);
applyMatchedProperties<AnimationProperties>(state, matchResult, true, matchResult.ranges.firstUARule, matchResult.ranges.lastUARule, applyInheritedOnly);
- // Match transition-property / animation-name length by trimming and
- // lengthening other transition / animation property lists
- // FIXME: This is wrong because we shouldn't affect the computed values
- state.style()->adjustAnimations();
- state.style()->adjustTransitions();
-
// Now we have all of the matched rules in the appropriate order. Walk the rules and apply
// high-priority properties first, i.e., those properties that other properties depend on.
// The order is (1) high-priority not important, (2) high-priority important, (3) normal not important
@@ -1398,6 +1472,17 @@ void StyleResolver::applyMatchedProperties(StyleResolverState& state, const Matc
applyMatchedProperties<HighPriorityProperties>(state, matchResult, true, matchResult.ranges.firstUserRule, matchResult.ranges.lastUserRule, applyInheritedOnly);
applyMatchedProperties<HighPriorityProperties>(state, matchResult, true, matchResult.ranges.firstUARule, matchResult.ranges.lastUARule, applyInheritedOnly);
+ if (UNLIKELY(isSVGForeignObjectElement(element))) {
+ // RenderSVGRoot handles zooming for the whole SVG subtree, so foreignObject content should not be scaled again.
+ //
+ // FIXME: The following hijacks the zoom property for foreignObject so that children of foreignObject get the
+ // correct font-size in case of zooming. 'zoom' is part of HighPriorityProperties, along with other font-related
+ // properties used as input to the FontBuilder, so resetting it here may cause the FontBuilder to recompute the
+ // font used as inheritable font for foreignObject content. If we want to support zoom on foreignObject we'll
+ // need to find another way of handling the SVG zoom model.
+ state.setEffectiveZoom(RenderStyle::initialZoom());
+ }
+
if (cachedMatchedProperties && cachedMatchedProperties->renderStyle->effectiveZoom() != state.style()->effectiveZoom()) {
state.fontBuilder().setFontDirty(true);
applyInheritedOnly = false;
@@ -1426,9 +1511,7 @@ void StyleResolver::applyMatchedProperties(StyleResolverState& state, const Matc
applyMatchedProperties<LowPriorityProperties>(state, matchResult, true, matchResult.ranges.firstUserRule, matchResult.ranges.lastUserRule, applyInheritedOnly);
applyMatchedProperties<LowPriorityProperties>(state, matchResult, true, matchResult.ranges.firstUARule, matchResult.ranges.lastUARule, applyInheritedOnly);
- // Start loading resources referenced by this style.
- m_styleResourceLoader.loadPendingResources(state.style(), state.elementStyleResources());
- document().styleEngine()->fontSelector()->loadPendingFonts();
+ loadPendingResources(state);
if (!cachedMatchedProperties && cacheHash && MatchedPropertiesCache::isCacheable(element, state.style(), state.parentStyle())) {
INCREMENT_STYLE_STATS_COUNTER(*this, matchedPropertyCacheAdded);
@@ -1476,7 +1559,7 @@ void StyleResolver::applyPropertiesToStyle(const CSSPropertyValue* properties, s
StyleResolverState state(document(), document().documentElement(), style);
state.setStyle(style);
- state.fontBuilder().initForStyleResolve(document(), style, state.useSVGZoomRules());
+ state.fontBuilder().initForStyleResolve(document(), style);
for (size_t i = 0; i < count; ++i) {
if (properties[i].value) {
@@ -1502,13 +1585,26 @@ void StyleResolver::addMediaQueryResults(const MediaQueryResultList& list)
m_viewportDependentMediaQueryResults.append(list[i]);
}
-bool StyleResolver::affectedByViewportChange() const
+bool StyleResolver::mediaQueryAffectedByViewportChange() const
{
for (unsigned i = 0; i < m_viewportDependentMediaQueryResults.size(); ++i) {
- if (m_medium->eval(&m_viewportDependentMediaQueryResults[i]->m_expression) != m_viewportDependentMediaQueryResults[i]->m_result)
+ if (m_medium->eval(m_viewportDependentMediaQueryResults[i]->expression()) != m_viewportDependentMediaQueryResults[i]->result())
return true;
}
return false;
}
+void StyleResolver::trace(Visitor* visitor)
+{
+ visitor->trace(m_keyframesRuleMap);
+ visitor->trace(m_viewportDependentMediaQueryResults);
+ visitor->trace(m_viewportStyleResolver);
+ visitor->trace(m_features);
+ visitor->trace(m_siblingRuleSet);
+ visitor->trace(m_uncommonAttributeRuleSet);
+ visitor->trace(m_watchedSelectorsRules);
+ visitor->trace(m_treeBoundaryCrossingRules);
+ visitor->trace(m_pendingStyleSheets);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.h
index f1dae0b2381..1ab53b349d0 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolver.h
@@ -22,8 +22,6 @@
#ifndef StyleResolver_h
#define StyleResolver_h
-#include "core/animation/KeyframeAnimationEffect.h"
-#include "core/css/InspectorCSSOMWrappers.h"
#include "core/css/PseudoStyleRequest.h"
#include "core/css/RuleFeature.h"
#include "core/css/RuleSet.h"
@@ -35,9 +33,8 @@
#include "core/css/resolver/ScopedStyleResolver.h"
#include "core/css/resolver/ScopedStyleTree.h"
#include "core/css/resolver/StyleBuilder.h"
-#include "core/css/resolver/StyleResolverIncludes.h"
-#include "core/css/resolver/StyleResolverState.h"
#include "core/css/resolver/StyleResourceLoader.h"
+#include "platform/heap/Handle.h"
#include "wtf/Deque.h"
#include "wtf/HashMap.h"
#include "wtf/HashSet.h"
@@ -47,6 +44,8 @@
namespace WebCore {
+class AnimatableValue;
+class AnimationTimeline;
class CSSAnimationUpdate;
class CSSFontSelector;
class CSSRuleList;
@@ -55,14 +54,13 @@ class CSSStyleSheet;
class CSSValue;
class ContainerNode;
class Document;
-class DocumentTimeline;
class Element;
class ElementRuleCollector;
+class Interpolation;
class KeyframeList;
class KeyframeValue;
class MediaQueryEvaluator;
class MediaQueryResult;
-class RenderRegion;
class RuleData;
class Settings;
class StyleKeyframe;
@@ -73,40 +71,39 @@ class StyleRuleKeyframes;
class StyleRulePage;
class ViewportStyleResolver;
-struct MatchResult;
+class MatchResult;
enum StyleSharingBehavior {
AllowStyleSharing,
DisallowStyleSharing,
};
-// MatchOnlyUserAgentRules is used in media queries, where relative units
-// are interpreted according to the document root element style, and styled only
-// from the User Agent Stylesheet rules.
enum RuleMatchingBehavior {
MatchAllRules,
- MatchAllRulesExcludingSMIL,
- MatchOnlyUserAgentRules,
+ MatchAllRulesExcludingSMIL
};
-const unsigned styleSharingListSize = 40;
+const unsigned styleSharingListSize = 15;
+const unsigned styleSharingMaxDepth = 32;
typedef WTF::Deque<Element*, styleSharingListSize> StyleSharingList;
struct CSSPropertyValue {
+ STACK_ALLOCATED();
+public:
CSSPropertyValue(CSSPropertyID property, CSSValue* value)
: property(property), value(value) { }
// Stores value=propertySet.getPropertyCSSValue(id).get().
CSSPropertyValue(CSSPropertyID, const StylePropertySet&);
CSSPropertyID property;
- CSSValue* value;
+ RawPtrWillBeMember<CSSValue> value;
};
// This class selects a RenderStyle for a given element based on a collection of stylesheets.
-class StyleResolver : public FontSelectorClient {
- WTF_MAKE_NONCOPYABLE(StyleResolver); WTF_MAKE_FAST_ALLOCATED;
+class StyleResolver FINAL : public NoBaseWillBeGarbageCollectedFinalized<StyleResolver> {
+ WTF_MAKE_NONCOPYABLE(StyleResolver); WTF_MAKE_FAST_ALLOCATED_WILL_BE_REMOVED;
public:
explicit StyleResolver(Document&);
- ~StyleResolver();
+ virtual ~StyleResolver();
// FIXME: StyleResolver should not be keeping tree-walk state.
// These should move to some global tree-walk state, or should be contained in a
@@ -118,13 +115,11 @@ public:
void popParentShadowRoot(const ShadowRoot&);
PassRefPtr<RenderStyle> styleForElement(Element*, RenderStyle* parentStyle = 0, StyleSharingBehavior = AllowStyleSharing,
- RuleMatchingBehavior = MatchAllRules, RenderRegion* regionForStyling = 0);
+ RuleMatchingBehavior = MatchAllRules);
- // FIXME: keyframeStylesForAnimation is only used in the legacy animations implementation
- // and should be removed when that is replaced by Web Animations.
- void keyframeStylesForAnimation(Element*, const RenderStyle&, KeyframeList&);
PassRefPtr<RenderStyle> styleForKeyframe(Element*, const RenderStyle&, RenderStyle* parentStyle, const StyleKeyframe*, const AtomicString& animationName);
- static PassRefPtr<KeyframeAnimationEffect> createKeyframeAnimationEffect(Element&, const Vector<RefPtr<MutableStylePropertySet> >&, KeyframeAnimationEffect::KeyframeVector&);
+ static PassRefPtrWillBeRawPtr<AnimatableValue> createAnimatableValueSnapshot(Element&, CSSPropertyID, CSSValue&);
+ static PassRefPtrWillBeRawPtr<AnimatableValue> createAnimatableValueSnapshot(StyleResolverState&, CSSPropertyID, CSSValue&);
PassRefPtr<RenderStyle> pseudoStyleForElement(Element*, const PseudoStyleRequest&, RenderStyle* parentStyle);
@@ -132,7 +127,7 @@ public:
PassRefPtr<RenderStyle> defaultStyleForElement();
PassRefPtr<RenderStyle> styleForText(Text*);
- static PassRefPtr<RenderStyle> styleForDocument(Document&, CSSFontSelector* = 0);
+ static PassRefPtr<RenderStyle> styleForDocument(Document&);
// FIXME: This only has 5 callers and should be removed. Callers should be explicit about
// their dependency on Document* instead of grabbing one through StyleResolver.
@@ -140,15 +135,14 @@ public:
// FIXME: It could be better to call appendAuthorStyleSheets() directly after we factor StyleResolver further.
// https://bugs.webkit.org/show_bug.cgi?id=108890
- void appendAuthorStyleSheets(unsigned firstNew, const Vector<RefPtr<CSSStyleSheet> >&);
+ void appendAuthorStyleSheets(const WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> >&);
void resetAuthorStyle(const ContainerNode*);
void finishAppendAuthorStyleSheets();
- TreeBoundaryCrossingRules& treeBoundaryCrossingRules() { return m_treeBoundaryCrossingRules; }
- void processScopedRules(const RuleSet& authorRules, const KURL&, ContainerNode* scope = 0);
+ void processScopedRules(const RuleSet& authorRules, CSSStyleSheet*, ContainerNode& scope);
- void lazyAppendAuthorStyleSheets(unsigned firstNew, const Vector<RefPtr<CSSStyleSheet> >&);
- void removePendingAuthorStyleSheets(const Vector<RefPtr<CSSStyleSheet> >&);
+ void lazyAppendAuthorStyleSheets(unsigned firstNew, const WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> >&);
+ void removePendingAuthorStyleSheets(const WillBeHeapVector<RefPtrWillBeMember<CSSStyleSheet> >&);
void appendPendingAuthorStyleSheets();
bool hasPendingAuthorStyleSheets() const { return m_pendingStyleSheets.size() > 0 || m_needCollectFeatures; }
@@ -179,9 +173,9 @@ public:
AllButEmptyCSSRules = UAAndUserCSSRules | AuthorCSSRules | CrossOriginCSSRules,
AllCSSRules = AllButEmptyCSSRules | EmptyCSSRules,
};
- PassRefPtr<CSSRuleList> cssRulesForElement(Element*, unsigned rulesToInclude = AllButEmptyCSSRules, ShouldIncludeStyleSheetInCSSOMWrapper = IncludeStyleSheetInCSSOMWrapper);
- PassRefPtr<CSSRuleList> pseudoCSSRulesForElement(Element*, PseudoId, unsigned rulesToInclude = AllButEmptyCSSRules, ShouldIncludeStyleSheetInCSSOMWrapper = IncludeStyleSheetInCSSOMWrapper);
- PassRefPtr<StyleRuleList> styleRulesForElement(Element*, unsigned rulesToInclude);
+ PassRefPtrWillBeRawPtr<CSSRuleList> cssRulesForElement(Element*, unsigned rulesToInclude = AllButEmptyCSSRules);
+ PassRefPtrWillBeRawPtr<CSSRuleList> pseudoCSSRulesForElement(Element*, PseudoId, unsigned rulesToInclude = AllButEmptyCSSRules);
+ PassRefPtrWillBeRawPtr<StyleRuleList> styleRulesForElement(Element*, unsigned rulesToInclude);
// |properties| is an array with |count| elements.
void applyPropertiesToStyle(const CSSPropertyValue* properties, size_t count, RenderStyle*);
@@ -191,28 +185,29 @@ public:
void addMediaQueryResults(const MediaQueryResultList&);
MediaQueryResultList* viewportDependentMediaQueryResults() { return &m_viewportDependentMediaQueryResults; }
bool hasViewportDependentMediaQueries() const { return !m_viewportDependentMediaQueryResults.isEmpty(); }
- bool affectedByViewportChange() const;
-
- // FIXME: Regions should not require special logic in StyleResolver.
- bool checkRegionStyle(Element* regionElement);
+ bool mediaQueryAffectedByViewportChange() const;
// FIXME: Rename to reflect the purpose, like didChangeFontSize or something.
void invalidateMatchedPropertiesCache();
+ void notifyResizeForViewportUnits();
+
// Exposed for RenderStyle::isStyleAvilable().
static RenderStyle* styleNotYetAvailable() { return s_styleNotYetAvailable; }
- // FIXME: StyleResolver should not have this member or method.
- InspectorCSSOMWrappers& inspectorCSSOMWrappers() { return m_inspectorCSSOMWrappers; }
-
- const RuleFeatureSet& ensureRuleFeatureSet()
+ RuleFeatureSet& ensureUpdatedRuleFeatureSet()
{
if (hasPendingAuthorStyleSheets())
appendPendingAuthorStyleSheets();
return m_features;
}
- StyleSharingList& styleSharingList() { return m_styleSharingList; }
+ RuleFeatureSet& ruleFeatureSet()
+ {
+ return m_features;
+ }
+
+ StyleSharingList& styleSharingList();
bool hasRulesForId(const AtomicString&) const;
@@ -229,20 +224,22 @@ public:
unsigned accessCount() const { return m_accessCount; }
void didAccess() { ++m_accessCount; }
- PassRefPtr<PseudoElement> createPseudoElementIfNeeded(Element&, PseudoId);
+ void increaseStyleSharingDepth() { ++m_styleSharingDepth; }
+ void decreaseStyleSharingDepth() { --m_styleSharingDepth; }
-private:
- // FontSelectorClient implementation.
- virtual void fontsNeedUpdate(FontSelector*);
+ PassRefPtrWillBeRawPtr<PseudoElement> createPseudoElementIfNeeded(Element& parent, PseudoId);
-private:
- void initWatchedSelectorRules(const Vector<RefPtr<StyleRule> >& watchedSelectors);
+ void trace(Visitor*);
- void addTreeBoundaryCrossingRules(const Vector<MinimalRuleData>&, ContainerNode* scope);
+private:
+ void initWatchedSelectorRules(const WillBeHeapVector<RefPtrWillBeMember<StyleRule> >& watchedSelectors);
// FIXME: This should probably go away, folded into FontBuilder.
void updateFont(StyleResolverState&);
+ void loadPendingResources(StyleResolverState&);
+ void adjustRenderStyle(StyleResolverState&, Element*);
+
void appendCSSStyleSheet(CSSStyleSheet*);
void collectPseudoRulesForElement(Element*, ElementRuleCollector&, PseudoId, unsigned rulesToInclude);
@@ -254,30 +251,35 @@ private:
// FIXME: watched selectors should be implemented using injected author stylesheets: http://crbug.com/316960
void matchWatchSelectorRules(ElementRuleCollector&);
void collectFeatures();
- void collectTreeBoundaryCrossingRules(Element*, ElementRuleCollector&, bool includeEmptyRules);
void resetRuleFeatures();
bool fastRejectSelector(const RuleData&) const;
void applyMatchedProperties(StyleResolverState&, const MatchResult&);
- void applyAnimatedProperties(StyleResolverState&, Element* animatingElement);
+ bool applyAnimatedProperties(StyleResolverState&, Element* animatingElement);
enum StyleApplicationPass {
- VariableDefinitions,
AnimationProperties,
HighPriorityProperties,
LowPriorityProperties
};
template <StyleResolver::StyleApplicationPass pass>
+ static inline CSSPropertyID firstCSSPropertyId();
+ template <StyleResolver::StyleApplicationPass pass>
+ static inline CSSPropertyID lastCSSPropertyId();
+ template <StyleResolver::StyleApplicationPass pass>
static inline bool isPropertyForPass(CSSPropertyID);
template <StyleApplicationPass pass>
void applyMatchedProperties(StyleResolverState&, const MatchResult&, bool important, int startIndex, int endIndex, bool inheritedOnly);
template <StyleApplicationPass pass>
void applyProperties(StyleResolverState&, const StylePropertySet* properties, StyleRule*, bool isImportant, bool inheritedOnly, PropertyWhitelistType = PropertyWhitelistNone);
template <StyleApplicationPass pass>
- void applyAnimatedProperties(StyleResolverState&, const AnimationEffect::CompositableValueMap&);
+ void applyAnimatedProperties(StyleResolverState&, const WillBeHeapHashMap<CSSPropertyID, RefPtrWillBeMember<Interpolation> >&);
+ template <StyleResolver::StyleApplicationPass pass>
+ void applyAllProperty(StyleResolverState&, CSSValue*);
+
void matchPageRules(MatchResult&, RuleSet*, bool isLeftPage, bool isFirstPage, const String& pageName);
- void matchPageRulesForList(Vector<StyleRulePage*>& matchedRules, const Vector<StyleRulePage*>&, bool isLeftPage, bool isFirstPage, const String& pageName);
+ void matchPageRulesForList(WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >& matchedRules, const WillBeHeapVector<RawPtrWillBeMember<StyleRulePage> >&, bool isLeftPage, bool isFirstPage, const String& pageName);
void collectViewportRules();
Settings* documentSettings() { return m_document.settings(); }
@@ -289,7 +291,7 @@ private:
bool pseudoStyleForElementInternal(Element&, const PseudoStyleRequest&, RenderStyle* parentStyle, StyleResolverState&);
// FIXME: This likely belongs on RuleSet.
- typedef HashMap<StringImpl*, RefPtr<StyleRuleKeyframes> > KeyframesRuleMap;
+ typedef WillBeHeapHashMap<StringImpl*, RefPtrWillBeMember<StyleRuleKeyframes> > KeyframesRuleMap;
KeyframesRuleMap m_keyframesRuleMap;
static RenderStyle* s_styleNotYetAvailable;
@@ -301,56 +303,40 @@ private:
OwnPtr<MediaQueryEvaluator> m_medium;
MediaQueryResultList m_viewportDependentMediaQueryResults;
- RefPtr<RenderStyle> m_rootDefaultStyle;
-
Document& m_document;
SelectorFilter m_selectorFilter;
- RefPtr<ViewportStyleResolver> m_viewportStyleResolver;
+ OwnPtrWillBeMember<ViewportStyleResolver> m_viewportStyleResolver;
- ListHashSet<CSSStyleSheet*, 16> m_pendingStyleSheets;
+ WillBeHeapListHashSet<RawPtrWillBeMember<CSSStyleSheet>, 16> m_pendingStyleSheets;
ScopedStyleTree m_styleTree;
- // FIXME: The entire logic of collecting features on StyleResolver, as well astransferring them
+ // FIXME: The entire logic of collecting features on StyleResolver, as well as transferring them
// between various parts of machinery smells wrong. This needs to be better somehow.
RuleFeatureSet m_features;
- OwnPtr<RuleSet> m_siblingRuleSet;
- OwnPtr<RuleSet> m_uncommonAttributeRuleSet;
+ OwnPtrWillBeMember<RuleSet> m_siblingRuleSet;
+ OwnPtrWillBeMember<RuleSet> m_uncommonAttributeRuleSet;
// FIXME: watched selectors should be implemented using injected author stylesheets: http://crbug.com/316960
- OwnPtr<RuleSet> m_watchedSelectorsRules;
+ OwnPtrWillBeMember<RuleSet> m_watchedSelectorsRules;
TreeBoundaryCrossingRules m_treeBoundaryCrossingRules;
bool m_needCollectFeatures;
- InspectorCSSOMWrappers m_inspectorCSSOMWrappers;
-
StyleResourceLoader m_styleResourceLoader;
- StyleSharingList m_styleSharingList;
+ unsigned m_styleSharingDepth;
+ Vector<OwnPtr<StyleSharingList>, styleSharingMaxDepth> m_styleSharingLists;
OwnPtr<StyleResolverStats> m_styleResolverStats;
OwnPtr<StyleResolverStats> m_styleResolverStatsTotals;
unsigned m_styleResolverStatsSequence;
+ // Use only for Internals::updateStyleAndReturnAffectedElementCount.
unsigned m_accessCount;
};
-inline bool checkRegionSelector(const CSSSelector* regionSelector, Element* regionElement)
-{
- if (!regionSelector || !regionElement)
- return false;
-
- SelectorChecker selectorChecker(regionElement->document(), SelectorChecker::QueryingRules);
- for (const CSSSelector* s = regionSelector; s; s = CSSSelectorList::next(s)) {
- SelectorChecker::SelectorCheckingContext selectorCheckingContext(s, regionElement, SelectorChecker::VisitedMatchDisabled);
- if (selectorChecker.match(selectorCheckingContext, DOMSiblingTraversalStrategy()) == SelectorChecker::SelectorMatches)
- return true;
- }
- return false;
-}
-
} // namespace WebCore
#endif // StyleResolver_h
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverIncludes.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverIncludes.h
deleted file mode 100644
index 380c1eb1d57..00000000000
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverIncludes.h
+++ /dev/null
@@ -1,13 +0,0 @@
-#ifndef StyleResolverIncludes_h
-#define StyleResolverIncludes_h
-
-namespace WebCore {
-
-enum ShouldIncludeStyleSheetInCSSOMWrapper {
- IncludeStyleSheetInCSSOMWrapper,
- DoNotIncludeStyleSheetInCSSOMWrapper,
-};
-
-}
-
-#endif // StyleResolverIncludes_h
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.cpp
new file mode 100644
index 00000000000..bde3a362aed
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.cpp
@@ -0,0 +1,13 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+
+#include "core/css/resolver/StyleResolverParentScope.h"
+
+namespace WebCore {
+
+StyleResolverParentScope* StyleResolverParentScope::s_currentScope = 0;
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.h
new file mode 100644
index 00000000000..87ca21cee91
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverParentScope.h
@@ -0,0 +1,78 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef StyleResolverParentScope_h
+#define StyleResolverParentScope_h
+
+#include "core/css/resolver/StyleResolver.h"
+#include "core/dom/Element.h"
+#include "core/dom/shadow/ShadowRoot.h"
+
+namespace WebCore {
+
+// Maintains the parent element stack (and bloom filter) inside recalcStyle.
+class StyleResolverParentScope FINAL {
+public:
+ explicit StyleResolverParentScope(Node& parent);
+ ~StyleResolverParentScope();
+
+ static void ensureParentStackIsPushed();
+
+private:
+ void pushParentIfNeeded();
+
+ Node& m_parent;
+ bool m_pushed;
+ StyleResolverParentScope* m_previous;
+ StyleResolver& m_resolver;
+
+ static StyleResolverParentScope* s_currentScope;
+};
+
+inline StyleResolverParentScope::StyleResolverParentScope(Node& parent)
+ : m_parent(parent)
+ , m_pushed(false)
+ , m_previous(s_currentScope)
+ , m_resolver(*m_parent.document().styleResolver())
+{
+ ASSERT(m_parent.document().inStyleRecalc());
+ ASSERT(parent.isElementNode() || parent.isShadowRoot());
+ s_currentScope = this;
+ m_resolver.increaseStyleSharingDepth();
+}
+
+inline StyleResolverParentScope::~StyleResolverParentScope()
+{
+ s_currentScope = m_previous;
+ m_resolver.decreaseStyleSharingDepth();
+ if (!m_pushed)
+ return;
+ if (m_parent.isElementNode())
+ m_resolver.popParentElement(toElement(m_parent));
+ else
+ m_resolver.popParentShadowRoot(toShadowRoot(m_parent));
+}
+
+inline void StyleResolverParentScope::ensureParentStackIsPushed()
+{
+ if (s_currentScope)
+ s_currentScope->pushParentIfNeeded();
+}
+
+inline void StyleResolverParentScope::pushParentIfNeeded()
+{
+ if (m_pushed)
+ return;
+ if (m_previous)
+ m_previous->pushParentIfNeeded();
+ if (m_parent.isElementNode())
+ m_resolver.pushParentElement(toElement(m_parent));
+ else
+ m_resolver.pushParentShadowRoot(toShadowRoot(m_parent));
+ m_pushed = true;
+}
+
+} // namespace WebCore
+
+#endif // StyleResolverParentScope_h
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.cpp
index 6df80021ba5..f0efa4a7d8a 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.cpp
@@ -22,33 +22,48 @@
#include "config.h"
#include "core/css/resolver/StyleResolverState.h"
+#include "core/animation/css/CSSAnimations.h"
#include "core/dom/Node.h"
#include "core/dom/NodeRenderStyle.h"
-#include "core/page/Page.h"
+#include "core/frame/FrameHost.h"
namespace WebCore {
-StyleResolverState::StyleResolverState(Document& document, Element* element, RenderStyle* parentStyle, RenderRegion* regionForStyling)
+StyleResolverState::StyleResolverState(Document& document, Element* element, RenderStyle* parentStyle)
: m_elementContext(element ? ElementResolveContext(*element) : ElementResolveContext())
, m_document(document)
- , m_style(0)
- , m_cssToLengthConversionData(0, rootElementStyle())
+ , m_style(nullptr)
+ , m_cssToLengthConversionData(0, rootElementStyle(), document.renderView())
, m_parentStyle(parentStyle)
- , m_regionForStyling(regionForStyling)
, m_applyPropertyToRegularStyle(true)
, m_applyPropertyToVisitedLinkStyle(false)
- , m_lineHeightValue(0)
+ , m_lineHeightValue(nullptr)
, m_styleMap(*this, m_elementStyleResources)
- , m_currentRule(0)
+ , m_currentRule(nullptr)
{
- if (m_elementContext.resetStyleInheritance())
- m_parentStyle = 0;
- else if (!parentStyle && m_elementContext.parentNode())
+ if (!parentStyle && m_elementContext.parentNode())
m_parentStyle = m_elementContext.parentNode()->renderStyle();
- // FIXME: How can we not have a page here?
- if (Page* page = document.page())
- m_elementStyleResources.setDeviceScaleFactor(page->deviceScaleFactor());
+ // FIXME: Animation unitests will start animations on non-active documents!
+ // http://crbug.com/330095
+ // ASSERT(document.isActive());
+ if (!document.isActive())
+ return;
+ m_elementStyleResources.setDeviceScaleFactor(document.frameHost()->deviceScaleFactor());
+}
+
+StyleResolverState::~StyleResolverState()
+{
+}
+
+void StyleResolverState::setAnimationUpdate(PassOwnPtrWillBeRawPtr<CSSAnimationUpdate> update)
+{
+ m_animationUpdate = update;
+}
+
+PassOwnPtrWillBeRawPtr<CSSAnimationUpdate> StyleResolverState::takeAnimationUpdate()
+{
+ return m_animationUpdate.release();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.h
index 18095bd28dd..2a723ba471b 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResolverState.h
@@ -22,9 +22,8 @@
#ifndef StyleResolverState_h
#define StyleResolverState_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
-#include "core/animation/css/CSSAnimations.h"
#include "core/css/CSSSVGDocumentValue.h"
#include "core/css/CSSToLengthConversionData.h"
#include "core/css/resolver/CSSToStyleMap.h"
@@ -38,14 +37,16 @@
namespace WebCore {
+class CSSAnimationUpdate;
class FontDescription;
-class RenderRegion;
class StyleRule;
class StyleResolverState {
-WTF_MAKE_NONCOPYABLE(StyleResolverState);
+ STACK_ALLOCATED();
+ WTF_MAKE_NONCOPYABLE(StyleResolverState);
public:
- StyleResolverState(Document&, Element*, RenderStyle* parentStyle = 0, RenderRegion* regionForStyling = 0);
+ StyleResolverState(Document&, Element*, RenderStyle* parentStyle = 0);
+ ~StyleResolverState();
// In FontFaceSet and CanvasRenderingContext2D, we don't have an element to grab the document from.
// This is why we have to store the document separately.
@@ -66,16 +67,14 @@ public:
const CSSToLengthConversionData& cssToLengthConversionData() const { return m_cssToLengthConversionData; }
- void setAnimationUpdate(PassOwnPtr<CSSAnimationUpdate> update) { m_animationUpdate = update; }
+ void setAnimationUpdate(PassOwnPtrWillBeRawPtr<CSSAnimationUpdate>);
const CSSAnimationUpdate* animationUpdate() { return m_animationUpdate.get(); }
- PassOwnPtr<CSSAnimationUpdate> takeAnimationUpdate() { return m_animationUpdate.release(); }
+ PassOwnPtrWillBeRawPtr<CSSAnimationUpdate> takeAnimationUpdate();
void setParentStyle(PassRefPtr<RenderStyle> parentStyle) { m_parentStyle = parentStyle; }
const RenderStyle* parentStyle() const { return m_parentStyle.get(); }
RenderStyle* parentStyle() { return m_parentStyle.get(); }
- const RenderRegion* regionForStyling() const { return m_regionForStyling; }
-
void setCurrentRule(StyleRule* currentRule) { m_currentRule = currentRule; }
const StyleRule* currentRule() const { return m_currentRule; }
@@ -95,8 +94,20 @@ public:
void setLineHeightValue(CSSValue* value) { m_lineHeightValue = value; }
CSSValue* lineHeightValue() { return m_lineHeightValue; }
- void cacheUserAgentBorderAndBackground() { m_cachedUAStyle = CachedUAStyle(style()); }
- const CachedUAStyle& cachedUAStyle() const { return m_cachedUAStyle; }
+ void cacheUserAgentBorderAndBackground()
+ {
+ // RenderTheme only needs the cached style if it has an appearance,
+ // and constructing it is expensive so we avoid it if possible.
+ if (!style()->hasAppearance())
+ return;
+
+ m_cachedUAStyle = CachedUAStyle::create(style());
+ }
+
+ const CachedUAStyle* cachedUAStyle() const
+ {
+ return m_cachedUAStyle.get();
+ }
ElementStyleResources& elementStyleResources() { return m_elementStyleResources; }
const CSSToStyleMap& styleMap() const { return m_styleMap; }
@@ -107,7 +118,7 @@ public:
// sites are extremely verbose.
PassRefPtr<StyleImage> styleImage(CSSPropertyID propertyId, CSSValue* value)
{
- return m_elementStyleResources.styleImage(document().textLinkColors(), style()->color(), propertyId, value);
+ return m_elementStyleResources.styleImage(document(), document().textLinkColors(), style()->color(), propertyId, value);
}
FontBuilder& fontBuilder() { return m_fontBuilder; }
@@ -122,19 +133,7 @@ public:
void setWritingMode(WritingMode writingMode) { m_fontBuilder.didChangeFontParameters(m_style->setWritingMode(writingMode)); }
void setTextOrientation(TextOrientation textOrientation) { m_fontBuilder.didChangeFontParameters(m_style->setTextOrientation(textOrientation)); }
- // SVG handles zooming in a different way compared to CSS. The whole document is scaled instead
- // of each individual length value in the render style / tree. CSSPrimitiveValue::computeLength*()
- // multiplies each resolved length with the zoom multiplier - so for SVG we need to disable that.
- // Though all CSS values that can be applied to outermost <svg> elements (width/height/border/padding...)
- // need to respect the scaling. RenderBox (the parent class of RenderSVGRoot) grabs values like
- // width/height/border/padding/... from the RenderStyle -> for SVG these values would never scale,
- // if we'd pass a 1.0 zoom factor everyhwere. So we only pass a zoom factor of 1.0 for specific
- // properties that are NOT allowed to scale within a zoomed SVG document (letter/word-spacing/font-size).
- bool useSVGZoomRules() const { return element() && element()->isSVGElement(); }
-
private:
- friend class StyleResolveScope;
-
ElementResolveContext m_elementContext;
Document& m_document;
@@ -147,21 +146,16 @@ private:
// so we keep it separate from m_elementContext.
RefPtr<RenderStyle> m_parentStyle;
- OwnPtr<CSSAnimationUpdate> m_animationUpdate;
-
- // Required to ASSERT in applyProperties.
- // FIXME: Regions should not need special state on StyleResolverState
- // no other @rule does.
- RenderRegion* m_regionForStyling;
+ OwnPtrWillBeMember<CSSAnimationUpdate> m_animationUpdate;
bool m_applyPropertyToRegularStyle;
bool m_applyPropertyToVisitedLinkStyle;
- CSSValue* m_lineHeightValue;
+ RawPtrWillBeMember<CSSValue> m_lineHeightValue;
FontBuilder m_fontBuilder;
- CachedUAStyle m_cachedUAStyle;
+ OwnPtr<CachedUAStyle> m_cachedUAStyle;
ElementStyleResources m_elementStyleResources;
// CSSToStyleMap is a pure-logic class and only contains
@@ -169,7 +163,7 @@ private:
CSSToStyleMap m_styleMap;
Vector<AtomicString> m_contentAttrValues;
- StyleRule* m_currentRule;
+ RawPtrWillBeMember<StyleRule> m_currentRule;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.cpp
index 04405c340a7..9025bf04f78 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.cpp
@@ -23,37 +23,29 @@
#include "config.h"
#include "core/css/resolver/StyleResourceLoader.h"
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
#include "core/css/CSSCursorImageValue.h"
#include "core/css/CSSImageValue.h"
#include "core/css/CSSSVGDocumentValue.h"
-#include "core/css/CSSShaderValue.h"
#include "core/css/resolver/ElementStyleResources.h"
#include "core/fetch/ResourceFetcher.h"
#include "core/rendering/style/ContentData.h"
-#include "core/rendering/style/CursorList.h"
#include "core/rendering/style/FillLayer.h"
#include "core/rendering/style/RenderStyle.h"
-#include "core/rendering/style/StyleCustomFilterProgram.h"
-#include "core/rendering/style/StyleCustomFilterProgramCache.h"
#include "core/rendering/style/StyleFetchedImage.h"
#include "core/rendering/style/StyleFetchedImageSet.h"
-#include "core/rendering/style/StyleFetchedShader.h"
#include "core/rendering/style/StyleGeneratedImage.h"
#include "core/rendering/style/StylePendingImage.h"
-#include "core/rendering/style/StylePendingShader.h"
#include "core/rendering/svg/ReferenceFilterBuilder.h"
-#include "platform/graphics/filters/custom/CustomFilterOperation.h"
namespace WebCore {
StyleResourceLoader::StyleResourceLoader(ResourceFetcher* fetcher)
- : m_customFilterProgramCache(StyleCustomFilterProgramCache::create())
- , m_fetcher(fetcher)
+ : m_fetcher(fetcher)
{
}
-void StyleResourceLoader::loadPendingSVGDocuments(RenderStyle* renderStyle, const ElementStyleResources& elementStyleResources)
+void StyleResourceLoader::loadPendingSVGDocuments(RenderStyle* renderStyle, ElementStyleResources& elementStyleResources)
{
if (!renderStyle->hasFilter() || elementStyleResources.pendingSVGDocuments().isEmpty())
return;
@@ -75,35 +67,37 @@ void StyleResourceLoader::loadPendingSVGDocuments(RenderStyle* renderStyle, cons
ReferenceFilterBuilder::setDocumentResourceReference(referenceFilter, adoptPtr(new DocumentResourceReference(resource)));
}
}
+
+ elementStyleResources.clearPendingSVGDocuments();
}
-PassRefPtr<StyleImage> StyleResourceLoader::loadPendingImage(StylePendingImage* pendingImage, float deviceScaleFactor)
+static PassRefPtr<StyleImage> doLoadPendingImage(ResourceFetcher* fetcher, StylePendingImage* pendingImage, float deviceScaleFactor, const ResourceLoaderOptions& options)
{
- if (pendingImage->cssImageValue()) {
- CSSImageValue* imageValue = pendingImage->cssImageValue();
- return imageValue->cachedImage(m_fetcher);
- }
+ if (CSSImageValue* imageValue = pendingImage->cssImageValue())
+ return imageValue->cachedImage(fetcher, options);
- if (pendingImage->cssImageGeneratorValue()) {
- CSSImageGeneratorValue* imageGeneratorValue = pendingImage->cssImageGeneratorValue();
- imageGeneratorValue->loadSubimages(m_fetcher);
+ if (CSSImageGeneratorValue* imageGeneratorValue
+ = pendingImage->cssImageGeneratorValue()) {
+ imageGeneratorValue->loadSubimages(fetcher);
return StyleGeneratedImage::create(imageGeneratorValue);
}
- if (pendingImage->cssCursorImageValue()) {
- CSSCursorImageValue* cursorImageValue = pendingImage->cssCursorImageValue();
- return cursorImageValue->cachedImage(m_fetcher, deviceScaleFactor);
- }
+ if (CSSCursorImageValue* cursorImageValue
+ = pendingImage->cssCursorImageValue())
+ return cursorImageValue->cachedImage(fetcher, deviceScaleFactor);
- if (pendingImage->cssImageSetValue()) {
- CSSImageSetValue* imageSetValue = pendingImage->cssImageSetValue();
- return imageSetValue->cachedImageSet(m_fetcher, deviceScaleFactor);
- }
+ if (CSSImageSetValue* imageSetValue = pendingImage->cssImageSetValue())
+ return imageSetValue->cachedImageSet(fetcher, deviceScaleFactor, options);
+
+ return nullptr;
+}
- return 0;
+PassRefPtr<StyleImage> StyleResourceLoader::loadPendingImage(StylePendingImage* pendingImage, float deviceScaleFactor)
+{
+ return doLoadPendingImage(m_fetcher, pendingImage, deviceScaleFactor, ResourceFetcher::defaultResourceOptions());
}
-void StyleResourceLoader::loadPendingShapeImage(RenderStyle* renderStyle, ShapeValue* shapeValue)
+void StyleResourceLoader::loadPendingShapeImage(RenderStyle* renderStyle, ShapeValue* shapeValue, float deviceScaleFactor)
{
if (!shapeValue)
return;
@@ -112,16 +106,15 @@ void StyleResourceLoader::loadPendingShapeImage(RenderStyle* renderStyle, ShapeV
if (!image || !image->isPendingImage())
return;
- StylePendingImage* pendingImage = toStylePendingImage(image);
- CSSImageValue* cssImageValue = pendingImage->cssImageValue();
-
ResourceLoaderOptions options = ResourceFetcher::defaultResourceOptions();
options.allowCredentials = DoNotAllowStoredCredentials;
+ options.credentialsRequested = ClientDidNotRequestCredentials;
+ options.corsEnabled = IsCORSEnabled;
- shapeValue->setImage(cssImageValue->cachedImage(m_fetcher, options, PotentiallyCORSEnabled));
+ shapeValue->setImage(doLoadPendingImage(m_fetcher, toStylePendingImage(image), deviceScaleFactor, options));
}
-void StyleResourceLoader::loadPendingImages(RenderStyle* style, const ElementStyleResources& elementStyleResources)
+void StyleResourceLoader::loadPendingImages(RenderStyle* style, ElementStyleResources& elementStyleResources)
{
if (elementStyleResources.pendingImageProperties().isEmpty())
return;
@@ -195,51 +188,15 @@ void StyleResourceLoader::loadPendingImages(RenderStyle* style, const ElementSty
}
break;
}
- case CSSPropertyShapeInside:
- loadPendingShapeImage(style, style->shapeInside());
- break;
case CSSPropertyShapeOutside:
- loadPendingShapeImage(style, style->shapeOutside());
+ loadPendingShapeImage(style, style->shapeOutside(), elementStyleResources.deviceScaleFactor());
break;
default:
ASSERT_NOT_REACHED();
}
}
-}
-void StyleResourceLoader::loadPendingShaders(RenderStyle* style, const ElementStyleResources& elementStyleResources)
-{
- if (!style->hasFilter() || !elementStyleResources.hasNewCustomFilterProgram())
- return;
-
- Vector<RefPtr<FilterOperation> >& filterOperations = style->mutableFilter().operations();
- for (unsigned i = 0; i < filterOperations.size(); ++i) {
- RefPtr<FilterOperation> filterOperation = filterOperations.at(i);
- if (filterOperation->type() == FilterOperation::CUSTOM) {
- CustomFilterOperation* customFilter = toCustomFilterOperation(filterOperation.get());
- ASSERT(customFilter->program());
- StyleCustomFilterProgram* program = static_cast<StyleCustomFilterProgram*>(customFilter->program());
- // Note that the StylePendingShaders could be already resolved to StyleFetchedShaders. That's because the rule was matched before.
- // However, the StyleCustomFilterProgram that was initially created could have been removed from the cache in the meanwhile,
- // meaning that we get a new StyleCustomFilterProgram here that is not yet in the cache, but already has loaded StyleShaders.
- if (!program->hasPendingShaders() && program->inCache())
- continue;
- RefPtr<StyleCustomFilterProgram> styleProgram = m_customFilterProgramCache->lookup(program);
- if (styleProgram.get()) {
- customFilter->setProgram(styleProgram.release());
- } else {
- if (program->vertexShader() && program->vertexShader()->isPendingShader()) {
- CSSShaderValue* shaderValue = static_cast<StylePendingShader*>(program->vertexShader())->cssShaderValue();
- program->setVertexShader(shaderValue->resource(m_fetcher));
- }
- if (program->fragmentShader() && program->fragmentShader()->isPendingShader()) {
- CSSShaderValue* shaderValue = static_cast<StylePendingShader*>(program->fragmentShader())->cssShaderValue();
- program->setFragmentShader(shaderValue->resource(m_fetcher));
- }
- m_customFilterProgramCache->add(program);
- }
- }
- }
+ elementStyleResources.clearPendingImageProperties();
}
void StyleResourceLoader::loadPendingResources(RenderStyle* renderStyle, ElementStyleResources& elementStyleResources)
@@ -247,9 +204,6 @@ void StyleResourceLoader::loadPendingResources(RenderStyle* renderStyle, Element
// Start loading images referenced by this style.
loadPendingImages(renderStyle, elementStyleResources);
- // Start loading the shaders referenced by this style.
- loadPendingShaders(renderStyle, elementStyleResources);
-
// Start loading the SVG Documents referenced by this style.
loadPendingSVGDocuments(renderStyle, elementStyleResources);
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.h b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.h
index 4b33efeea47..8d3eff19ec0 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/StyleResourceLoader.h
@@ -29,34 +29,29 @@
namespace WebCore {
class ElementStyleResources;
-class ResourceFetcher;
class RenderStyle;
+class ResourceFetcher;
class ShapeValue;
class StyleImage;
class StylePendingImage;
-class StyleCustomFilterProgramCache;
// Manages loading of resources, requested by the stylesheets.
-// Expects the same lifetime as StyleResolver, because:
-// 1) it expects ResourceFetcher to never change, and
-// 2) it also holds the StyleCustomFilterProgramCache.
+// Expects the same lifetime as StyleResolver, because
+// it expects ResourceFetcher to never change.
class StyleResourceLoader {
WTF_MAKE_NONCOPYABLE(StyleResourceLoader);
public:
explicit StyleResourceLoader(ResourceFetcher*);
void loadPendingResources(RenderStyle*, ElementStyleResources&);
- StyleCustomFilterProgramCache* customFilterProgramCache() const { return m_customFilterProgramCache.get(); }
private:
- void loadPendingSVGDocuments(RenderStyle*, const ElementStyleResources&);
- void loadPendingShaders(RenderStyle*, const ElementStyleResources&);
+ void loadPendingSVGDocuments(RenderStyle*, ElementStyleResources&);
PassRefPtr<StyleImage> loadPendingImage(StylePendingImage*, float deviceScaleFactor);
- void loadPendingImages(RenderStyle*, const ElementStyleResources&);
- void loadPendingShapeImage(RenderStyle*, ShapeValue*);
+ void loadPendingImages(RenderStyle*, ElementStyleResources&);
+ void loadPendingShapeImage(RenderStyle*, ShapeValue*, float deviceScaleFactor);
- OwnPtr<StyleCustomFilterProgramCache> m_customFilterProgramCache;
ResourceFetcher* m_fetcher;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.cpp
index 3779a01f6a5..b111c0b7844 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.cpp
@@ -32,6 +32,7 @@
#include "core/css/CSSPrimitiveValueMappings.h"
#include "core/css/CSSTransformValue.h"
#include "core/rendering/style/RenderStyle.h"
+#include "platform/heap/Handle.h"
#include "platform/transforms/Matrix3DTransformOperation.h"
#include "platform/transforms/MatrixTransformOperation.h"
#include "platform/transforms/PerspectiveTransformOperation.h"
@@ -43,17 +44,10 @@
namespace WebCore {
-TransformBuilder::TransformBuilder()
-{
-}
-
-TransformBuilder::~TransformBuilder()
-{
-}
-
static Length convertToFloatLength(CSSPrimitiveValue* primitiveValue, const CSSToLengthConversionData& conversionData)
{
- return primitiveValue ? primitiveValue->convertToLength<FixedConversion | PercentConversion>(conversionData) : Length(Undefined);
+ ASSERT(primitiveValue);
+ return primitiveValue->convertToLength<FixedConversion | PercentConversion>(conversionData);
}
static TransformOperation::OperationType getTransformOperationType(CSSTransformValue::TransformOperationType type)
@@ -180,19 +174,16 @@ bool TransformBuilder::createTransformOperations(CSSValue* inValue, const CSSToL
}
}
- if (tx.isUndefined() || ty.isUndefined())
- return false;
-
- operations.operations().append(TranslateTransformOperation::create(tx, ty, Length(0, Fixed), getTransformOperationType(transformValue->operationType())));
+ operations.operations().append(TranslateTransformOperation::create(tx, ty, 0, getTransformOperationType(transformValue->operationType())));
break;
}
case CSSTransformValue::TranslateZTransformOperation:
case CSSTransformValue::Translate3DTransformOperation: {
Length tx = Length(0, Fixed);
Length ty = Length(0, Fixed);
- Length tz = Length(0, Fixed);
+ double tz = 0;
if (transformValue->operationType() == CSSTransformValue::TranslateZTransformOperation)
- tz = convertToFloatLength(firstValue, conversionData);
+ tz = firstValue->computeLength<double>(conversionData);
else if (transformValue->operationType() == CSSTransformValue::TranslateYTransformOperation)
ty = convertToFloatLength(firstValue, conversionData);
else {
@@ -200,7 +191,7 @@ bool TransformBuilder::createTransformOperations(CSSValue* inValue, const CSSToL
if (transformValue->operationType() != CSSTransformValue::TranslateXTransformOperation) {
if (transformValue->length() > 2) {
CSSPrimitiveValue* thirdValue = toCSSPrimitiveValue(transformValue->itemWithoutBoundsCheck(2));
- tz = convertToFloatLength(thirdValue, conversionData);
+ tz = thirdValue->computeLength<double>(conversionData);
}
if (transformValue->length() > 1) {
CSSPrimitiveValue* secondValue = toCSSPrimitiveValue(transformValue->itemWithoutBoundsCheck(1));
@@ -209,9 +200,6 @@ bool TransformBuilder::createTransformOperations(CSSValue* inValue, const CSSToL
}
}
- if (tx.isUndefined() || ty.isUndefined() || tz.isUndefined())
- return false;
-
operations.operations().append(TranslateTransformOperation::create(tx, ty, tz, getTransformOperationType(transformValue->operationType())));
break;
}
@@ -305,18 +293,17 @@ bool TransformBuilder::createTransformOperations(CSSValue* inValue, const CSSToL
break;
}
case CSSTransformValue::PerspectiveTransformOperation: {
- Length p = Length(0, Fixed);
+ double p;
if (firstValue->isLength())
- p = convertToFloatLength(firstValue, conversionData);
+ p = firstValue->computeLength<double>(conversionData);
else {
// This is a quirk that should go away when 3d transforms are finalized.
double val = firstValue->getDoubleValue();
- p = val >= 0 ? Length(clampToPositiveInteger(val), Fixed) : Length(Undefined);
+ if (val < 0)
+ return false;
+ p = clampToPositiveInteger(val);
}
- if (p.isUndefined())
- return false;
-
operations.operations().append(PerspectiveTransformOperation::create(p));
break;
}
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.h b/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.h
index a3ac2e0b0f5..94fc5a5b946 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/TransformBuilder.h
@@ -31,6 +31,7 @@
#ifndef TransformBuilder_h
#define TransformBuilder_h
+#include "platform/heap/Handle.h"
#include "platform/transforms/TransformOperations.h"
#include "wtf/Noncopyable.h"
@@ -40,11 +41,8 @@ class CSSToLengthConversionData;
class CSSValue;
class TransformBuilder {
- WTF_MAKE_NONCOPYABLE(TransformBuilder); WTF_MAKE_FAST_ALLOCATED;
+ STATIC_ONLY(TransformBuilder);
public:
- TransformBuilder();
- ~TransformBuilder();
-
static bool createTransformOperations(CSSValue* inValue, const CSSToLengthConversionData&, TransformOperations& outOperations);
};
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.cpp b/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.cpp
index 61894a2458a..a8c3be72ed1 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.cpp
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.cpp
@@ -30,41 +30,41 @@
#include "config.h"
#include "core/css/resolver/ViewportStyleResolver.h"
-#include "CSSValueKeywords.h"
+#include "core/CSSValueKeywords.h"
+#include "core/css/CSSPrimitiveValueMappings.h"
#include "core/css/CSSToLengthConversionData.h"
#include "core/css/StylePropertySet.h"
#include "core/css/StyleRule.h"
#include "core/dom/Document.h"
#include "core/dom/NodeRenderStyle.h"
#include "core/dom/ViewportDescription.h"
+#include "core/frame/FrameView.h"
namespace WebCore {
+DEFINE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(ViewportStyleResolver);
+
ViewportStyleResolver::ViewportStyleResolver(Document* document)
- : m_document(document),
- m_hasAuthorStyle(false)
+ : m_document(document)
+ , m_hasAuthorStyle(false)
{
ASSERT(m_document);
}
-ViewportStyleResolver::~ViewportStyleResolver()
-{
-}
-
void ViewportStyleResolver::collectViewportRules(RuleSet* rules, Origin origin)
{
rules->compactRulesIfNeeded();
- const Vector<StyleRuleViewport*>& viewportRules = rules->viewportRules();
+ const WillBeHeapVector<RawPtrWillBeMember<StyleRuleViewport> >& viewportRules = rules->viewportRules();
for (size_t i = 0; i < viewportRules.size(); ++i)
addViewportRule(viewportRules[i], origin);
}
void ViewportStyleResolver::addViewportRule(StyleRuleViewport* viewportRule, Origin origin)
{
- StylePropertySet* propertySet = viewportRule->mutableProperties();
+ StylePropertySet& propertySet = viewportRule->mutableProperties();
- unsigned propertyCount = propertySet->propertyCount();
+ unsigned propertyCount = propertySet.propertyCount();
if (!propertyCount)
return;
@@ -72,19 +72,14 @@ void ViewportStyleResolver::addViewportRule(StyleRuleViewport* viewportRule, Ori
m_hasAuthorStyle = true;
if (!m_propertySet) {
- m_propertySet = propertySet->mutableCopy();
+ m_propertySet = propertySet.mutableCopy();
return;
}
// We cannot use mergeAndOverrideOnConflict() here because it doesn't
// respect the !important declaration (but addParsedProperty() does).
for (unsigned i = 0; i < propertyCount; ++i)
- m_propertySet->addParsedProperty(propertySet->propertyAt(i).toCSSProperty());
-}
-
-void ViewportStyleResolver::clearDocument()
-{
- m_document = 0;
+ m_propertySet->addParsedProperty(propertySet.propertyAt(i).toCSSProperty());
}
void ViewportStyleResolver::resolve()
@@ -92,10 +87,8 @@ void ViewportStyleResolver::resolve()
if (!m_document)
return;
- if (!m_propertySet || (!m_hasAuthorStyle && m_document->hasLegacyViewportTag())) {
- ASSERT(!m_hasAuthorStyle);
- m_propertySet = 0;
- m_document->setViewportDescription(ViewportDescription());
+ if (!m_propertySet) {
+ m_document->setViewportDescription(ViewportDescription(ViewportDescription::UserAgentStyleSheet));
return;
}
@@ -113,7 +106,7 @@ void ViewportStyleResolver::resolve()
m_document->setViewportDescription(description);
- m_propertySet = 0;
+ m_propertySet = nullptr;
m_hasAuthorStyle = false;
}
@@ -127,7 +120,7 @@ float ViewportStyleResolver::viewportArgumentValue(CSSPropertyID id) const
if (id == CSSPropertyUserZoom)
defaultValue = 1;
- RefPtr<CSSValue> value = m_propertySet->getPropertyCSSValue(id);
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet->getPropertyCSSValue(id);
if (!value || !value->isPrimitiveValue())
return defaultValue;
@@ -177,31 +170,36 @@ Length ViewportStyleResolver::viewportLengthValue(CSSPropertyID id) const
|| id == CSSPropertyMaxWidth
|| id == CSSPropertyMinWidth);
- RefPtr<CSSValue> value = m_propertySet->getPropertyCSSValue(id);
+ RefPtrWillBeRawPtr<CSSValue> value = m_propertySet->getPropertyCSSValue(id);
if (!value || !value->isPrimitiveValue())
return Length(); // auto
CSSPrimitiveValue* primitiveValue = toCSSPrimitiveValue(value.get());
- if (primitiveValue->isLength())
- return primitiveValue->computeLength<Length>(CSSToLengthConversionData(m_document->renderStyle(), m_document->renderStyle(), 1.0f));
+ if (primitiveValue->getValueID() == CSSValueInternalExtendToZoom)
+ return Length(ExtendToZoom);
- if (primitiveValue->isViewportPercentageLength())
- return primitiveValue->viewportPercentageLength();
+ RenderStyle* documentStyle = m_document->renderStyle();
- if (primitiveValue->isPercentage())
- return Length(primitiveValue->getFloatValue(), Percent);
+ // If we have viewport units the conversion will mark the document style as having viewport units.
+ bool documentStyleHasViewportUnits = documentStyle->hasViewportUnits();
+ documentStyle->setHasViewportUnits(false);
- switch (primitiveValue->getValueID()) {
- case CSSValueInternalExtendToZoom:
- return Length(ExtendToZoom);
- case CSSValueAuto:
- return Length();
- default:
- // Unrecognized keyword.
- ASSERT_NOT_REACHED();
- return Length(0, Fixed);
- }
+ FrameView* view = m_document->view();
+ float width = view ? view->width() : 0;
+ float height = view ? view->height() : 0;
+
+ Length result = primitiveValue->convertToLength<AnyConversion>(CSSToLengthConversionData(documentStyle, documentStyle, width, height, 1.0f));
+ if (documentStyle->hasViewportUnits())
+ m_document->setHasViewportUnits();
+ documentStyle->setHasViewportUnits(documentStyleHasViewportUnits);
+
+ return result;
+}
+
+void ViewportStyleResolver::trace(Visitor* visitor)
+{
+ visitor->trace(m_propertySet);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.h b/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.h
index 30b663f2b18..604a9890b97 100644
--- a/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.h
+++ b/chromium/third_party/WebKit/Source/core/css/resolver/ViewportStyleResolver.h
@@ -30,7 +30,7 @@
#ifndef ViewportStyleResolver_h
#define ViewportStyleResolver_h
-#include "CSSPropertyNames.h"
+#include "core/CSSPropertyNames.h"
#include "core/css/RuleSet.h"
#include "platform/Length.h"
#include "wtf/RefCounted.h"
@@ -42,22 +42,22 @@ class Document;
class MutableStylePropertySet;
class StyleRuleViewport;
-class ViewportStyleResolver : public RefCounted<ViewportStyleResolver> {
+class ViewportStyleResolver : public NoBaseWillBeGarbageCollected<ViewportStyleResolver> {
+ DECLARE_EMPTY_DESTRUCTOR_WILL_BE_REMOVED(ViewportStyleResolver);
public:
- static PassRefPtr<ViewportStyleResolver> create(Document* document)
+ static PassOwnPtrWillBeRawPtr<ViewportStyleResolver> create(Document* document)
{
- return adoptRef(new ViewportStyleResolver(document));
+ return adoptPtrWillBeNoop(new ViewportStyleResolver(document));
}
- ~ViewportStyleResolver();
-
enum Origin { UserAgentOrigin, AuthorOrigin };
void collectViewportRules(RuleSet*, Origin);
- void clearDocument();
void resolve();
+ void trace(Visitor*);
+
private:
explicit ViewportStyleResolver(Document*);
@@ -67,7 +67,7 @@ private:
Length viewportLengthValue(CSSPropertyID) const;
Document* m_document;
- RefPtr<MutableStylePropertySet> m_propertySet;
+ RefPtrWillBeMember<MutableStylePropertySet> m_propertySet;
bool m_hasAuthorStyle;
};
diff --git a/chromium/third_party/WebKit/Source/core/css/svg.css b/chromium/third_party/WebKit/Source/core/css/svg.css
index 3975ab42872..6151d17c5d2 100644
--- a/chromium/third_party/WebKit/Source/core/css/svg.css
+++ b/chromium/third_party/WebKit/Source/core/css/svg.css
@@ -47,14 +47,23 @@ svg:not(:root), symbol, image, marker, pattern, foreignObject {
overflow: hidden
}
+svg:root {
+ width: 100%;
+ height: 100%
+}
+
text, foreignObject {
display: block
}
-text, tspan, textPath {
+text {
white-space: nowrap
}
+tspan, textPath {
+ white-space: inherit
+}
+
/* states */
:focus {
diff --git a/chromium/third_party/WebKit/Source/core/css/themeChromium.css b/chromium/third_party/WebKit/Source/core/css/themeChromium.css
index 0a413e1efde..6094c1dd04e 100644
--- a/chromium/third_party/WebKit/Source/core/css/themeChromium.css
+++ b/chromium/third_party/WebKit/Source/core/css/themeChromium.css
@@ -30,7 +30,7 @@
/* These styles override other user-agent styles for Chromium. */
-input:disabled, isindex:disabled, textarea:disabled {
+input:disabled, textarea:disabled {
color: #545454; /* Color::light() for #000000. See RenderTextControl.cpp:disabledTextColor */
}
diff --git a/chromium/third_party/WebKit/Source/core/css/themeChromiumAndroid.css b/chromium/third_party/WebKit/Source/core/css/themeChromiumAndroid.css
index be5488fc854..3ff3183058b 100644
--- a/chromium/third_party/WebKit/Source/core/css/themeChromiumAndroid.css
+++ b/chromium/third_party/WebKit/Source/core/css/themeChromiumAndroid.css
@@ -35,7 +35,22 @@ select[multiple],
select[size][multiple] {
-webkit-appearance: menulist;
align-items: center;
- border: 1px solid;
+ background-color: ButtonFace;
+ border: 1px solid #a9a9a9;
border-radius: initial;
white-space: pre;
}
+
+input[type="date"]:disabled,
+input[type="datetime-local"]:disabled,
+input[type="month"]:disabled,
+input[type="time"]:disabled,
+input[type="week"]:disabled,
+input[type="date"]:read-only,
+input[type="datetime-local"]:read-only,
+input[type="month"]:read-only,
+input[type="time"]:read-only,
+input[type="week"]:read-only {
+ background-color: ButtonFace;
+ color: GrayText;
+} \ No newline at end of file
diff --git a/chromium/third_party/WebKit/Source/core/css/themeMac.css b/chromium/third_party/WebKit/Source/core/css/themeMac.css
new file mode 100644
index 00000000000..64950d72c65
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/core/css/themeMac.css
@@ -0,0 +1,20 @@
+/* Copyright 2014 The Chromium Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+select, input[type="color"][list] {
+ background-color: #f8f8f8;
+ border: 1px solid #a6a6a6;
+}
+
+select[size],
+select[multiple],
+select[size][multiple] {
+ background: white;
+ border: 1px inset gray;
+}
+
+input::-webkit-inner-spin-button {
+ align-self: center;
+}
diff --git a/chromium/third_party/WebKit/Source/core/css/themeWin.css b/chromium/third_party/WebKit/Source/core/css/themeWin.css
index 3c727d33b66..09b348a35a7 100644
--- a/chromium/third_party/WebKit/Source/core/css/themeWin.css
+++ b/chromium/third_party/WebKit/Source/core/css/themeWin.css
@@ -33,7 +33,6 @@
making our form elements match Firefox's. */
input:not([type]),
-input[type="color"],
input[type="email"],
input[type="number"],
input[type="password"],
diff --git a/chromium/third_party/WebKit/Source/core/css/view-source.css b/chromium/third_party/WebKit/Source/core/css/view-source.css
index daebdbf4f67..6c2077c647c 100644
--- a/chromium/third_party/WebKit/Source/core/css/view-source.css
+++ b/chromium/third_party/WebKit/Source/core/css/view-source.css
@@ -82,6 +82,11 @@ tbody:last-child .webkit-line-content:empty:before {
padding: 0 5px !important;
}
+.webkit-highlight {
+ background-color: rgb(100%, 42%, 42%);
+ border: 2px solid rgb(100%, 31%, 31%);
+}
+
.webkit-html-tag {
/* Keep this in sync with inspector.css (.webkit-html-tag) */
color: rgb(136, 18, 128);