Title: [203211] trunk/Source/WebCore
- Revision
- 203211
- Author
- benja...@webkit.org
- Date
- 2016-07-13 20:45:13 -0700 (Wed, 13 Jul 2016)
Log Message
[CSS][ARMv7] :nth-child() do not reserve enough registers if it is in backtracking chain
https://bugs.webkit.org/show_bug.cgi?id=159746
rdar://problem/26156169
Reviewed by Andreas Kling.
The generator generateElementIsNthChild() requires 6 registers in style resolution
to mark previous siblings with generateAddStyleRelationIfResolvingStyle() in the loop.
We were only reserving 5, which is a problem is the sixth is taken by the backtracking
register. x86_64 was already requiring 6 for unrelated reasons and ARM64 has so many registers
that you cannot possibly run out of them in CSS JIT.
I generalized the x86_64 path to all architectures.
I did not limit this case to style resolution because the extra register is irrelevant
in most cases. The only difference is one extra push/pop on ARMv7 if you use querySelector
with :nth-child in a backtracking chain.
This problem is covered by the existing test fast/selectors/nth-child-with-backtracking.html
* cssjit/SelectorCompiler.cpp:
(WebCore::SelectorCompiler::minimumRegisterRequirements): Deleted.
Modified Paths
Diff
Modified: trunk/Source/WebCore/ChangeLog (203210 => 203211)
--- trunk/Source/WebCore/ChangeLog 2016-07-14 03:43:07 UTC (rev 203210)
+++ trunk/Source/WebCore/ChangeLog 2016-07-14 03:45:13 UTC (rev 203211)
@@ -1,3 +1,28 @@
+2016-07-13 Benjamin Poulain <benja...@webkit.org>
+
+ [CSS][ARMv7] :nth-child() do not reserve enough registers if it is in backtracking chain
+ https://bugs.webkit.org/show_bug.cgi?id=159746
+ rdar://problem/26156169
+
+ Reviewed by Andreas Kling.
+
+ The generator generateElementIsNthChild() requires 6 registers in style resolution
+ to mark previous siblings with generateAddStyleRelationIfResolvingStyle() in the loop.
+
+ We were only reserving 5, which is a problem is the sixth is taken by the backtracking
+ register. x86_64 was already requiring 6 for unrelated reasons and ARM64 has so many registers
+ that you cannot possibly run out of them in CSS JIT.
+
+ I generalized the x86_64 path to all architectures.
+ I did not limit this case to style resolution because the extra register is irrelevant
+ in most cases. The only difference is one extra push/pop on ARMv7 if you use querySelector
+ with :nth-child in a backtracking chain.
+
+ This problem is covered by the existing test fast/selectors/nth-child-with-backtracking.html
+
+ * cssjit/SelectorCompiler.cpp:
+ (WebCore::SelectorCompiler::minimumRegisterRequirements): Deleted.
+
2016-07-13 Chris Dumez <cdu...@apple.com>
Drop unnecessary check from ContainerNode::removeChild()
Modified: trunk/Source/WebCore/cssjit/SelectorCompiler.cpp (203210 => 203211)
--- trunk/Source/WebCore/cssjit/SelectorCompiler.cpp 2016-07-14 03:43:07 UTC (rev 203210)
+++ trunk/Source/WebCore/cssjit/SelectorCompiler.cpp 2016-07-14 03:45:13 UTC (rev 203211)
@@ -1066,10 +1066,10 @@
static const unsigned minimumRequiredRegisterCount = 5;
// Element + ElementData + scratchRegister + attributeArrayPointer + expectedLocalName + (qualifiedNameImpl && expectedValue).
static const unsigned minimumRequiredRegisterCountForAttributeFilter = 6;
-#if CPU(X86_64)
-// Element + SiblingCounter + SiblingCounterCopy + divisor + dividend + remainder.
+// On x86, we always need 6 registers: Element + SiblingCounter + SiblingCounterCopy + divisor + dividend + remainder.
+// On other architectures, we need 6 registers for style resolution:
+// Element + elementCounter + previousSibling + checkingContext + lastRelation + nextSiblingElement.
static const unsigned minimumRequiredRegisterCountForNthChildFilter = 6;
-#endif
static unsigned minimumRegisterRequirements(const SelectorFragment& selectorFragment)
{
@@ -1093,10 +1093,8 @@
minimum = std::max(minimum, attributeMinimum);
}
-#if CPU(X86_64)
if (!selectorFragment.nthChildFilters.isEmpty() || !selectorFragment.nthChildOfFilters.isEmpty() || !selectorFragment.nthLastChildFilters.isEmpty() || !selectorFragment.nthLastChildOfFilters.isEmpty())
minimum = std::max(minimum, minimumRequiredRegisterCountForNthChildFilter);
-#endif
// :any pseudo class filters cause some register pressure.
for (const auto& subFragments : selectorFragment.anyFilters) {
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes