aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBobby Holley <bobbyholley@gmail.com>2017-04-27 14:51:23 -0700
committerBobby Holley <bobbyholley@gmail.com>2017-04-29 16:07:41 -0700
commit71ecff849bf7fb6e40dcb74092b36315c3ba5c33 (patch)
tree5c7a7cd577427d6251182662972dbc8649f0ae8f
parent080ff126b57248898422b1118f3776863b047aef (diff)
downloadservo-71ecff849bf7fb6e40dcb74092b36315c3ba5c33.tar.gz
servo-71ecff849bf7fb6e40dcb74092b36315c3ba5c33.zip
Use a single rule hash for both lower_name and name.
Right now in the common case we're doing twice the work during stylist update, and also checking is_html_element_in_html_document twice during lookup. This patch aligns us with what Gecko does. MozReview-Commit-ID: D4TyG30BP8C
-rw-r--r--components/style/stylist.rs29
1 files changed, 17 insertions, 12 deletions
diff --git a/components/style/stylist.rs b/components/style/stylist.rs
index d26d617d8c9..65d04630fd3 100644
--- a/components/style/stylist.rs
+++ b/components/style/stylist.rs
@@ -1050,9 +1050,6 @@ pub struct SelectorMap {
pub class_hash: FnvHashMap<Atom, Vec<Rule>>,
/// A hash from local name to rules which contain that local name selector.
pub local_name_hash: FnvHashMap<LocalName, Vec<Rule>>,
- /// Same as local_name_hash, but keys are lower-cased.
- /// For HTML elements in HTML documents.
- pub lower_local_name_hash: FnvHashMap<LocalName, Vec<Rule>>,
/// Rules that don't have ID, class, or element selectors.
pub other_rules: Vec<Rule>,
/// Whether this hash is empty.
@@ -1071,7 +1068,6 @@ impl SelectorMap {
id_hash: HashMap::default(),
class_hash: HashMap::default(),
local_name_hash: HashMap::default(),
- lower_local_name_hash: HashMap::default(),
other_rules: Vec::new(),
empty: true,
}
@@ -1120,14 +1116,9 @@ impl SelectorMap {
cascade_level);
});
- let local_name_hash = if element.is_html_element_in_html_document() {
- &self.lower_local_name_hash
- } else {
- &self.local_name_hash
- };
SelectorMap::get_matching_rules_from_hash(element,
parent_bf,
- local_name_hash,
+ &self.local_name_hash,
element.get_local_name(),
matching_rules_list,
relations,
@@ -1260,8 +1251,22 @@ impl SelectorMap {
}
if let Some(LocalNameSelector { name, lower_name }) = SelectorMap::get_local_name(&rule) {
- find_push(&mut self.local_name_hash, name, rule.clone());
- find_push(&mut self.lower_local_name_hash, lower_name, rule);
+ // If the local name in the selector isn't lowercase, insert it into
+ // the rule hash twice. This means that, during lookup, we can always
+ // find the rules based on the local name of the element, regardless
+ // of whether it's an html element in an html document (in which case
+ // we match against lower_name) or not (in which case we match against
+ // name).
+ //
+ // In the case of a non-html-element-in-html-document with a
+ // lowercase localname and a non-lowercase selector, the rulehash
+ // lookup may produce superfluous selectors, but the subsequent
+ // selector matching work will filter them out.
+ if name != lower_name {
+ find_push(&mut self.local_name_hash, lower_name, rule.clone());
+ }
+ find_push(&mut self.local_name_hash, name, rule);
+
return;
}