Skip to content

Commit

Permalink
Always upgrade existing weak child references in the rule tree
Browse files Browse the repository at this point in the history
Just because we didn't find a child when read-locking a node children list
doesn't mean it still won't exist while we wait to upgrade the read lock
into a write lock to create the child.
  • Loading branch information
nox committed Apr 18, 2020
1 parent a30da7a commit c113fbb
Showing 1 changed file with 25 additions and 12 deletions.
37 changes: 25 additions & 12 deletions components/style/rule_tree/core.rs
Expand Up @@ -402,18 +402,31 @@ impl StrongRuleNode {
return child.upgrade();
}
let mut children = RwLockUpgradableReadGuard::upgrade(children);
let weak = children.get_or_insert_with(
key,
|node| node.p.key(),
move || {
let root = unsafe { root.downgrade() };
let strong =
StrongRuleNode::new(Box::new(RuleNode::new(root, self.clone(), source, level)));
let weak = unsafe { strong.downgrade() };
mem::forget(strong);
weak
},
);
let mut is_new = false;
let weak = {
let is_new = &mut is_new;
children.get_or_insert_with(
key,
|node| node.p.key(),
move || {
*is_new = true;
let root = unsafe { root.downgrade() };
let strong = StrongRuleNode::new(Box::new(RuleNode::new(
root,
self.clone(),
source,
level,
)));
let weak = unsafe { strong.downgrade() };
mem::forget(strong);
weak
},
)
};

if !is_new {
return weak.upgrade();
}

unsafe { StrongRuleNode::from_unsafe_box(UnsafeBox::clone(&weak.p)) }
}
Expand Down

0 comments on commit c113fbb

Please sign in to comment.