ladybird/Userland/Libraries/LibWeb/CSS
Andreas Kling afe6abfc09 LibWeb: Use an ancestor filter to quickly reject many CSS selectors
Given a selector like `.foo .bar #baz`, we know that elements with
the class names `foo` and `bar` must be present in the ancestor chain of
the candidate element, or the selector cannot match.

By keeping track of the current ancestor chain during style computation,
and which strings are used in tag names and attribute names, we can do
a quick check before evaluating the selector itself, to see if all the
required ancestors are present.

The way this works:

1. CSS::Selector now has a cache of up to 8 strings that must be present
   in the ancestor chain of a matching element. Note that we actually
   store string *hashes*, not the strings themselves.

2. When Document performs a recursive style update, we now push and pop
   elements to the ancestor chain stack as they are entered and exited.

3. When entering/exiting an ancestor, StyleComputer collects all the
   relevant string hashes from that ancestor element and updates a
   counting bloom filter.

4. Before evaluating a selector, we first check if any of the hashes
   required by the selector are definitely missing from the ancestor
   filter. If so, it cannot be a match, and we reject it immediately.

5. Otherwise, we carry on and evaluate the selector as usual.

I originally tried doing this with a HashMap, but we ended up losing
a huge chunk of the time saved to HashMap instead. As it turns out,
a simple counting bloom filter is way better at handling this.
The cost is a flat 8KB per StyleComputer, and since it's a bloom filter,
false positives are a thing.

This is extremely efficient, and allows us to quickly reject the
majority of selectors on many huge websites.

Some example rejection rates:
- https://amazon.com: 77%
- https://github.com/SerenityOS/serenity: 61%
- https://nytimes.com: 57%
- https://store.steampowered.com: 55%
- https://en.wikipedia.org: 45%
- https://youtube.com: 32%
- https://shopify.com: 25%

This also yields a chunky 37% speedup on StyleBench. :^)
2024-03-22 18:27:32 +01:00
..
Parser LibWeb: Remove Badge from CSS::Parser::resolve_unresolved_style_value 2024-03-20 09:17:33 +01:00
StyleValues AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
SyntaxHighlighter LibSyntax+Userland: Make LibSyntax not depend on LibGUI 2023-08-29 07:57:39 -04:00
Angle.cpp AK: Add to_radians and to_degrees math functions 2023-09-10 08:38:29 +01:00
Angle.h LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
AnimationEvent.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
AnimationEvent.h LibWeb: Add the AnimationEvent IDL objects 2024-02-16 12:02:11 -07:00
AnimationEvent.idl LibWeb: Add the AnimationEvent IDL objects 2024-02-16 12:02:11 -07:00
BackdropFilter.h LibWeb: Split FilterValueListStyleValue out of StyleValue.{h,cpp} 2023-03-25 16:56:04 +00:00
CalculatedOr.cpp LibWeb: Add method for converting a FooOrCalculated to a StyleValue 2023-12-30 20:11:24 +01:00
CalculatedOr.h LibWeb: Add method for converting a FooOrCalculated to a StyleValue 2023-12-30 20:11:24 +01:00
Clip.cpp LibWeb: Move CSS::EdgeRect into its own files 2023-03-30 21:29:50 +02:00
Clip.h LibWeb: Move CSS::EdgeRect into its own files 2023-03-30 21:29:50 +02:00
ColumnCount.h LibWeb: Implement support for parsing CSS column-count property 2023-09-07 20:16:33 +02:00
ComputedValues.h AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
CSS.cpp LibWeb: Make Serialize functions infallible 2023-08-22 17:51:48 +01:00
CSS.h LibWeb: Port the CSS namespace to IDL 2023-03-15 12:48:25 -04:00
CSS.idl LibWeb: Port the CSS namespace to IDL 2023-03-15 12:48:25 -04:00
CSSAnimation.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSAnimation.h LibWeb: Implement animation class-specific composite order 2024-02-21 19:52:35 +01:00
CSSAnimation.idl LibWeb: Add the CSSAnimation IDL object 2024-02-16 12:02:11 -07:00
CSSConditionRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSConditionRule.h LibWeb: Make CSSConditionRule.conditionText read-only 2024-02-28 22:14:58 +01:00
CSSConditionRule.idl LibWeb: Make CSSConditionRule.conditionText read-only 2024-02-28 22:14:58 +01:00
CSSFontFaceRule.cpp AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
CSSFontFaceRule.h LibWeb: Port CSSRule::serialized from DeprecatedString to String 2023-11-28 17:15:27 -05:00
CSSFontFaceRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSGroupingRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSGroupingRule.h LibJS: Make Cell::initialize() return void 2023-08-08 07:39:11 +02:00
CSSGroupingRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSImportRule.cpp AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
CSSImportRule.h AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
CSSImportRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSKeyframeRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSKeyframeRule.h LibWeb: Port CSSRule::serialized from DeprecatedString to String 2023-11-28 17:15:27 -05:00
CSSKeyframeRule.idl IDL: Add missing #imports 2023-11-11 08:51:51 +01:00
CSSKeyframesRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSKeyframesRule.h LibWeb: Port CSSRule::serialized from DeprecatedString to String 2023-11-28 17:15:27 -05:00
CSSKeyframesRule.idl IDL: Add missing #imports 2023-11-11 08:51:51 +01:00
CSSMediaRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSMediaRule.h LibWeb: Make CSSConditionRule.conditionText read-only 2024-02-28 22:14:58 +01:00
CSSMediaRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSNamespaceRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSNamespaceRule.h LibWeb: Port CSSNamespaceRule to FlyString 2023-12-01 16:03:58 +01:00
CSSNamespaceRule.idl LibWeb: Format all .idl files to use four space indentation 2024-01-18 14:00:06 +01:00
CSSNumericType.cpp LibWeb: Merge background-position parsing into position code 2023-11-21 01:29:26 +01:00
CSSNumericType.h LibWeb: Implement Flex and FlexStyleValue types 2023-09-28 20:33:20 +01:00
CSSRule.cpp LibWeb: Port CSSRule::serialized from DeprecatedString to String 2023-11-28 17:15:27 -05:00
CSSRule.h LibWeb: Return String from CSSStyleRule::selector_text() 2023-12-01 20:48:13 +01:00
CSSRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSRuleList.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSRuleList.h LibWeb: Ensure CSSStyleSheet::css_rules() always returns the same object 2024-02-24 21:59:28 +01:00
CSSRuleList.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSStyleDeclaration.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSStyleDeclaration.h LibWeb: Move use pseudo element styles from TreeBuilder to StyleComputer 2023-12-17 23:12:34 +01:00
CSSStyleDeclaration.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSStyleRule.cpp LibWeb: Make CSSStyleRule::declaration() return a more specific type 2024-03-19 16:48:22 +01:00
CSSStyleRule.h LibWeb: Make CSSStyleRule::declaration() return a more specific type 2024-03-19 16:48:22 +01:00
CSSStyleRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
CSSStyleSheet.cpp AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
CSSStyleSheet.h AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
CSSStyleSheet.idl LibWeb: Remove first rule if no argument is given for remove_rule() 2024-02-24 21:59:28 +01:00
CSSSupportsRule.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
CSSSupportsRule.h LibWeb: Make CSSConditionRule.conditionText read-only 2024-02-28 22:14:58 +01:00
CSSSupportsRule.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
Default.css LibWeb: Move textarea cols rows attr size from css to create_layout_node 2024-03-07 10:38:17 +00:00
Display.cpp LibWeb: Move <display-foo> definitions into Enums.json 2023-09-11 17:03:22 +01:00
Display.h LibWeb: Add display: math 2023-09-11 17:03:22 +01:00
EasingFunctions.json Meta/CodeGenerators+LibWeb: Implement parsing CSS easing functions 2023-07-13 05:10:41 +02:00
EdgeRect.cpp LibWeb: Don't convert to floating point in CSS::EdgeRect 2023-09-01 09:40:14 +02:00
EdgeRect.h LibWeb: Don't convert to floating point in CSS::EdgeRect 2023-09-01 09:40:14 +02:00
ElementCSSInlineStyle.idl LibWeb: Move Element.prototype.style to ElementCSSInlineStyle mixin 2023-03-20 20:37:40 -04:00
Enums.json LibWeb/CSS: Add "text" into list of possible "background-box" values 2024-03-03 15:33:12 +01:00
Flex.cpp LibWeb: Implement Flex and FlexStyleValue types 2023-09-28 20:33:20 +01:00
Flex.h LibWeb: Implement Flex and FlexStyleValue types 2023-09-28 20:33:20 +01:00
FontFace.cpp LibWeb+LibGfx: Move UnicodeRange from LibWeb to LibGfx 2023-12-10 17:32:04 +01:00
FontFace.h AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
Frequency.cpp LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
Frequency.h LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
GeneralEnclosed.h LibWeb: Port GeneralEnclosed to new Strings 2023-02-19 00:51:16 +01:00
GridTrackPlacement.cpp LibWeb: Define if identifier represent area or line during layout [GFC] 2023-08-28 09:19:41 +02:00
GridTrackPlacement.h LibWeb: Define if identifier represent area or line during layout [GFC] 2023-08-28 09:19:41 +02:00
GridTrackSize.cpp LibWeb: Fix grid line name placement when repeat() is used 2024-01-05 13:21:09 +01:00
GridTrackSize.h LibWeb: Fix grid line name placement when repeat() is used 2024-01-05 13:21:09 +01:00
Identifiers.json LibWeb: Parse the CSS transform-box property 2024-01-27 07:46:37 +01:00
Length.cpp LibWeb: Limit length values to 5 decimal places when serializing 2024-03-03 19:50:25 +01:00
Length.h LibWeb: Let Length::to_px(Layout::Node) be inline for absolute lengths 2024-03-02 13:00:09 +01:00
LengthBox.cpp LibWeb: Move PercentageOr and subclasses into PercentageOr.{h,cpp} 2023-03-30 21:29:50 +02:00
LengthBox.h Everywhere: Remove needless trailing semi-colons after functions 2023-07-08 10:32:56 +01:00
LinkStyle.idl LibWeb: Extract the LinkStyle IDL mixin 2022-07-29 17:15:49 +01:00
MathFunctions.json LibWeb: Generate parsing code for CSS math functions 2023-07-15 10:23:33 +02:00
MediaFeatures.json LibWeb: Reformat inconsistent CSS JSON files 2023-08-02 12:49:46 +01:00
MediaList.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
MediaList.h LibWeb: Add CSSStyleSheet constructor binding 2024-02-24 21:59:28 +01:00
MediaList.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
MediaQuery.cpp LibWeb: Bring CSS line-height closer to other engines 2024-01-12 15:04:06 +01:00
MediaQuery.h LibWeb: Make serializing media-queries infallible 2023-08-22 17:51:48 +01:00
MediaQueryList.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
MediaQueryList.h LibWeb: Use String for getting/setting MediaQueryList media 2023-12-01 20:48:13 +01:00
MediaQueryList.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
MediaQueryListEvent.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
MediaQueryListEvent.h LibWeb: Put most LibWeb GC objects in type-specific heap blocks 2023-11-19 22:00:48 +01:00
MediaQueryListEvent.idl LibWeb: Switch IDL from UseNewAKString to UseDeprecatedAKString 2023-09-02 19:23:41 +01:00
Number.h LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
Percentage.h LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
PercentageOr.cpp LibWeb: Add Length::resolved() overload for CSSPixels 2023-08-30 20:09:15 +02:00
PercentageOr.h LibWeb: Add PercentageOr<Length>::to_px() fast path for absolute lengths 2024-03-02 13:00:09 +01:00
PreferredColorScheme.cpp Everywhere: Rename equals_ignoring_case => equals_ignoring_ascii_case 2023-03-10 13:15:44 +01:00
PreferredColorScheme.h LibWeb: Use StringView in CSS::PreferredColorScheme 2023-02-15 12:48:26 -05:00
Properties.json LibWeb: Add support for the inline-size CSS property 2024-03-09 16:02:17 +01:00
PseudoClasses.json LibWeb: Implement the :open and :closed pseudo-classes 2023-09-13 19:55:22 +02:00
QuirksMode.css LibWeb: Flesh out the default "quirks mode" style sheet 2022-09-20 14:48:07 +02:00
Ratio.cpp LibWeb: Limit ratio parts to 5 decimal places when printing 2024-03-03 19:50:25 +01:00
Ratio.h LibWeb: Use CSSPixelFraction to represent aspect ratios 2023-09-04 12:40:17 +02:00
Resolution.cpp LibWeb: Make resolution calculable 2023-12-30 20:11:24 +01:00
Resolution.h LibWeb: Make resolution calculable 2023-12-30 20:11:24 +01:00
ResolvedCSSStyleDeclaration.cpp LibWeb: Make CSS::string_from_property_id() return FlyString const& 2024-03-16 14:27:59 +01:00
ResolvedCSSStyleDeclaration.h LibWeb: Move use pseudo element styles from TreeBuilder to StyleComputer 2023-12-17 23:12:34 +01:00
Screen.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
Screen.h LibWeb: Put most LibWeb GC objects in type-specific heap blocks 2023-11-19 22:00:48 +01:00
Screen.idl LibWeb: Add Exposed attribute and IDL spec links where missing 2022-10-09 10:14:57 +02:00
Selector.cpp LibWeb: Use an ancestor filter to quickly reject many CSS selectors 2024-03-22 18:27:32 +01:00
Selector.h LibWeb: Use an ancestor filter to quickly reject many CSS selectors 2024-03-22 18:27:32 +01:00
SelectorEngine.cpp LibWeb: Remove FLATTEN attribute from SelectorEngine::fast_matches 2024-03-20 10:33:16 -04:00
SelectorEngine.h LibWeb: Add a fast (iterative) selector matcher for trivial selectors 2024-03-19 16:48:22 +01:00
Serialize.cpp LibWeb: Limit color alpha values to 4 decimal places when serializing 2024-03-03 19:50:25 +01:00
Serialize.h LibWeb+LibGfx: Move UnicodeRange from LibWeb to LibGfx 2023-12-10 17:32:04 +01:00
Size.cpp LibWeb: Forbid using CSS::Length as reference value in resolved() 2024-01-07 09:03:57 +01:00
Size.h LibWeb: Forbid using CSS::Length as reference value in resolved() 2024-01-07 09:03:57 +01:00
StyleComputer.cpp LibWeb: Use an ancestor filter to quickly reject many CSS selectors 2024-03-22 18:27:32 +01:00
StyleComputer.h LibWeb: Use an ancestor filter to quickly reject many CSS selectors 2024-03-22 18:27:32 +01:00
StyleInvalidation.cpp LibWeb: Add fast path to calculate invalidations for animated css props 2024-03-19 17:30:34 +01:00
StyleInvalidation.h LibWeb: Add fast path to calculate invalidations for animated css props 2024-03-19 17:30:34 +01:00
StyleProperties.cpp LibWeb: Add fast path to calculate invalidations for animated css props 2024-03-19 17:30:34 +01:00
StyleProperties.h LibWeb: Add fast path to calculate invalidations for animated css props 2024-03-19 17:30:34 +01:00
StyleProperty.cpp LibWeb: Don't include Layout/Node.h from DOM/Element.h 2023-05-08 09:29:44 +02:00
StyleProperty.h LibWeb: Port custom properties to FlyString 2023-11-07 11:33:41 +01:00
StyleSheet.cpp LibWeb: Respect media attribute of style tag 2022-11-14 14:47:37 +00:00
StyleSheet.h LibWeb: Use String for getting/setting MediaQueryList media 2023-12-01 20:48:13 +01:00
StyleSheet.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
StyleSheetList.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
StyleSheetList.h LibWeb: Delete LegacyPlatformObject and move behavior to PlatformObject 2024-01-12 09:11:18 +01:00
StyleSheetList.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00
StyleValue.cpp LibGfx+Userland: Move FontWeight enum into its own file 2024-01-21 09:32:10 -05:00
StyleValue.h AK+LibURL: Move AK::URL into a new URL library 2024-03-18 14:06:28 -04:00
Supports.cpp LibWeb: Make serializing Supports rules infallible 2023-08-22 17:51:48 +01:00
Supports.h LibWeb: Make serializing Supports rules infallible 2023-08-22 17:51:48 +01:00
SystemColor.cpp LibWeb: Implement <system-color> and <deprecated-color> keywords 2023-08-25 20:30:20 +01:00
SystemColor.h LibWeb: Implement <system-color> and <deprecated-color> keywords 2023-08-25 20:30:20 +01:00
Time.cpp LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
Time.h LibWeb: Make serializing basic CSS types infallible 2023-08-22 17:51:48 +01:00
Transformation.cpp LibWeb/CSS: Ensure length is absolute before converting to pixels 2024-02-21 19:38:17 +01:00
Transformation.h LibWeb: Allow percentages on CSS transform scale functions 2024-01-10 09:48:25 +01:00
TransformFunctions.json LibWeb: Add missing CSS Transforms Module Level 2 functions 2024-01-10 09:48:25 +01:00
VisualViewport.cpp LibWeb: Avoid FlyString lookups when setting IDL interface prototypes 2024-03-16 16:35:54 +01:00
VisualViewport.h LibWeb: Put most LibWeb GC objects in type-specific heap blocks 2023-11-19 22:00:48 +01:00
VisualViewport.idl LibWeb: Add comments and missing items of various IDL files 2023-10-25 19:45:41 +02:00