From b4463c1fb293dd193889d629f48fbb905eaa25fa Mon Sep 17 00:00:00 2001 From: Tetsuharu OHZEKI Date: Wed, 28 May 2014 06:02:08 +0900 Subject: [PATCH] Use Cell/RefCell for interior mutability of Node. --- src/components/main/layout/wrapper.rs | 14 +-- src/components/script/dom/node.rs | 118 +++++++++++++------------- 2 files changed, 66 insertions(+), 66 deletions(-) diff --git a/src/components/main/layout/wrapper.rs b/src/components/main/layout/wrapper.rs index 6cc4037b13e..3fa7b918785 100644 --- a/src/components/main/layout/wrapper.rs +++ b/src/components/main/layout/wrapper.rs @@ -181,7 +181,7 @@ impl<'ln> TLayoutNode for LayoutNode<'ln> { fn first_child(&self) -> Option> { unsafe { - self.get_jsmanaged().first_child_ref().map(|node| self.new_with_this_lifetime(node)) + self.get_jsmanaged().first_child_ref().map(|node| self.new_with_this_lifetime(&node)) } } @@ -230,19 +230,19 @@ impl<'ln> LayoutNode<'ln> { impl<'ln> TNode> for LayoutNode<'ln> { fn parent_node(&self) -> Option> { unsafe { - self.node.parent_node_ref().map(|node| self.new_with_this_lifetime(node)) + self.node.parent_node_ref().map(|node| self.new_with_this_lifetime(&node)) } } fn prev_sibling(&self) -> Option> { unsafe { - self.node.prev_sibling_ref().map(|node| self.new_with_this_lifetime(node)) + self.node.prev_sibling_ref().map(|node| self.new_with_this_lifetime(&node)) } } fn next_sibling(&self) -> Option> { unsafe { - self.node.next_sibling_ref().map(|node| self.new_with_this_lifetime(node)) + self.node.next_sibling_ref().map(|node| self.new_with_this_lifetime(&node)) } } @@ -471,7 +471,7 @@ impl<'ln> TLayoutNode for ThreadSafeLayoutNode<'ln> { } unsafe { - self.get_jsmanaged().first_child_ref().map(|node| self.new_with_this_lifetime(node)) + self.get_jsmanaged().first_child_ref().map(|node| self.new_with_this_lifetime(&node)) } } @@ -521,10 +521,10 @@ impl<'ln> ThreadSafeLayoutNode<'ln> { /// Returns the next sibling of this node. Unsafe and private because this can lead to races. unsafe fn next_sibling(&self) -> Option> { if self.pseudo == Before || self.pseudo == BeforeBlock { - return self.get_jsmanaged().first_child_ref().map(|node| self.new_with_this_lifetime(node)) + return self.get_jsmanaged().first_child_ref().map(|node| self.new_with_this_lifetime(&node)) } - self.get_jsmanaged().next_sibling_ref().map(|node| self.new_with_this_lifetime(node)) + self.get_jsmanaged().next_sibling_ref().map(|node| self.new_with_this_lifetime(&node)) } /// Returns an iterator over this node's children. diff --git a/src/components/script/dom/node.rs b/src/components/script/dom/node.rs index 9cf721d389d..87a5229b2d5 100644 --- a/src/components/script/dom/node.rs +++ b/src/components/script/dom/node.rs @@ -41,7 +41,7 @@ use libc; use libc::uintptr_t; use std::cast::transmute; use std::cast; -use std::cell::{RefCell, Ref, RefMut}; +use std::cell::{Cell, RefCell, Ref, RefMut}; use std::iter::{Map, Filter}; use std::mem; use style::ComputedValues; @@ -63,25 +63,25 @@ pub struct Node { pub type_id: NodeTypeId, /// The parent of this node. - pub parent_node: Option>, + pub parent_node: Cell>>, /// The first child of this node. - pub first_child: Option>, + pub first_child: Cell>>, /// The last child of this node. - pub last_child: Option>, + pub last_child: Cell>>, /// The next sibling of this node. - pub next_sibling: Option>, + pub next_sibling: Cell>>, /// The previous sibling of this node. - pub prev_sibling: Option>, + pub prev_sibling: Cell>>, /// The document that this node belongs to. - owner_doc: Option>, + owner_doc: Cell>>, /// The live list of children return by .childNodes. - pub child_list: Option>, + pub child_list: Cell>>, /// A bitfield of flags for node items. flags: NodeFlags, @@ -327,26 +327,26 @@ impl<'a> PrivateNodeHelpers for JSRef<'a, Node> { /// /// Fails unless `child` is a child of this node. (FIXME: This is not yet checked.) fn remove_child(&mut self, child: &mut JSRef) { - assert!(child.parent_node.is_some()); + assert!(child.parent_node.get().is_some()); - match child.prev_sibling.root() { + match child.prev_sibling.get().root() { None => { - let next_sibling = child.next_sibling.root(); + let next_sibling = child.next_sibling.get().root(); self.set_first_child(next_sibling.root_ref()); } Some(ref mut prev_sibling) => { - let next_sibling = child.next_sibling.root(); + let next_sibling = child.next_sibling.get().root(); prev_sibling.set_next_sibling(next_sibling.root_ref()); } } - match child.next_sibling.root() { + match child.next_sibling.get().root() { None => { - let prev_sibling = child.prev_sibling.root(); + let prev_sibling = child.prev_sibling.get().root(); self.set_last_child(prev_sibling.root_ref()); } Some(ref mut next_sibling) => { - let prev_sibling = child.prev_sibling.root(); + let prev_sibling = child.prev_sibling.get().root(); next_sibling.set_prev_sibling(prev_sibling.root_ref()); } } @@ -475,25 +475,25 @@ impl<'a> NodeHelpers for JSRef<'a, Node> { } fn parent_node(&self) -> Option> { - self.deref().parent_node.clone().map(|node| Temporary::new(node)) + self.deref().parent_node.get().map(|node| Temporary::new(node)) } fn first_child(&self) -> Option> { - self.deref().first_child.clone().map(|node| Temporary::new(node)) + self.deref().first_child.get().map(|node| Temporary::new(node)) } fn last_child(&self) -> Option> { - self.deref().last_child.clone().map(|node| Temporary::new(node)) + self.deref().last_child.get().map(|node| Temporary::new(node)) } /// Returns the previous sibling of this node. Fails if this node is borrowed mutably. fn prev_sibling(&self) -> Option> { - self.deref().prev_sibling.clone().map(|node| Temporary::new(node)) + self.deref().prev_sibling.get().map(|node| Temporary::new(node)) } /// Returns the next sibling of this node. Fails if this node is borrowed mutably. fn next_sibling(&self) -> Option> { - self.deref().next_sibling.clone().map(|node| Temporary::new(node)) + self.deref().next_sibling.get().map(|node| Temporary::new(node)) } #[inline] @@ -593,12 +593,12 @@ impl<'a> NodeHelpers for JSRef<'a, Node> { fn ancestors(&self) -> AncestorIterator { AncestorIterator { - current: self.parent_node.clone().map(|node| (*node.root()).clone()), + current: self.parent_node.get().map(|node| (*node.root()).clone()), } } fn owner_doc(&self) -> Temporary { - Temporary::new(self.owner_doc.get_ref().clone()) + Temporary::new(self.owner_doc.get().get_ref().clone()) } fn set_owner_doc(&mut self, document: &JSRef) { @@ -607,7 +607,7 @@ impl<'a> NodeHelpers for JSRef<'a, Node> { fn children(&self) -> AbstractNodeChildrenIterator { AbstractNodeChildrenIterator { - current_node: self.first_child.clone().map(|node| (*node.root()).clone()), + current_node: self.first_child.get().map(|node| (*node.root()).clone()), } } @@ -654,13 +654,13 @@ pub fn from_untrusted_node_address(runtime: *mut JSRuntime, candidate: Untrusted pub trait LayoutNodeHelpers { unsafe fn type_id_for_layout(&self) -> NodeTypeId; - unsafe fn parent_node_ref<'a>(&'a self) -> Option<&'a JS>; - unsafe fn first_child_ref<'a>(&'a self) -> Option<&'a JS>; - unsafe fn last_child_ref<'a>(&'a self) -> Option<&'a JS>; - unsafe fn prev_sibling_ref<'a>(&'a self) -> Option<&'a JS>; - unsafe fn next_sibling_ref<'a>(&'a self) -> Option<&'a JS>; + unsafe fn parent_node_ref<'a>(&'a self) -> Option>; + unsafe fn first_child_ref<'a>(&'a self) -> Option>; + unsafe fn last_child_ref<'a>(&'a self) -> Option>; + unsafe fn prev_sibling_ref<'a>(&'a self) -> Option>; + unsafe fn next_sibling_ref<'a>(&'a self) -> Option>; - unsafe fn owner_doc_for_layout<'a>(&'a self) -> &'a JS; + unsafe fn owner_doc_for_layout<'a>(&'a self) -> JS; unsafe fn is_element_for_layout(&self) -> bool; } @@ -675,32 +675,32 @@ impl LayoutNodeHelpers for JS { } #[inline] - unsafe fn parent_node_ref<'a>(&'a self) -> Option<&'a JS> { - (*self.unsafe_get()).parent_node.as_ref() + unsafe fn parent_node_ref<'a>(&'a self) -> Option> { + (*self.unsafe_get()).parent_node.get() } #[inline] - unsafe fn first_child_ref<'a>(&'a self) -> Option<&'a JS> { - (*self.unsafe_get()).first_child.as_ref() + unsafe fn first_child_ref<'a>(&'a self) -> Option> { + (*self.unsafe_get()).first_child.get() } #[inline] - unsafe fn last_child_ref<'a>(&'a self) -> Option<&'a JS> { - (*self.unsafe_get()).last_child.as_ref() + unsafe fn last_child_ref<'a>(&'a self) -> Option> { + (*self.unsafe_get()).last_child.get() } #[inline] - unsafe fn prev_sibling_ref<'a>(&'a self) -> Option<&'a JS> { - (*self.unsafe_get()).prev_sibling.as_ref() + unsafe fn prev_sibling_ref<'a>(&'a self) -> Option> { + (*self.unsafe_get()).prev_sibling.get() } #[inline] - unsafe fn next_sibling_ref<'a>(&'a self) -> Option<&'a JS> { - (*self.unsafe_get()).next_sibling.as_ref() + unsafe fn next_sibling_ref<'a>(&'a self) -> Option> { + (*self.unsafe_get()).next_sibling.get() } - unsafe fn owner_doc_for_layout<'a>(&'a self) -> &'a JS { - (*self.unsafe_get()).owner_doc.get_ref() + unsafe fn owner_doc_for_layout<'a>(&'a self) -> JS { + (*self.unsafe_get()).owner_doc.get().unwrap() } } @@ -822,7 +822,7 @@ impl<'a> Iterator> for NodeIterator { self.current_node = match self.current_node.as_ref().map(|node| node.root()) { None => { if self.include_start { - Some(self.start_node.clone()) + Some(self.start_node) } else { self.next_child(&*self.start_node.root()) .map(|child| child.unrooted()) @@ -860,7 +860,7 @@ impl<'a> Iterator> for NodeIterator { } } }; - self.current_node.clone().map(|node| (*node.root()).clone()) + self.current_node.map(|node| (*node.root()).clone()) } } @@ -911,14 +911,14 @@ impl Node { eventtarget: EventTarget::new_inherited(NodeTargetTypeId(type_id)), type_id: type_id, - parent_node: None, - first_child: None, - last_child: None, - next_sibling: None, - prev_sibling: None, + parent_node: Cell::new(None), + first_child: Cell::new(None), + last_child: Cell::new(None), + next_sibling: Cell::new(None), + prev_sibling: Cell::new(None), - owner_doc: doc.unrooted(), - child_list: None, + owner_doc: Cell::new(doc.unrooted()), + child_list: Cell::new(None), flags: NodeFlags::new(type_id), @@ -1427,12 +1427,12 @@ impl<'a> NodeMethods for JSRef<'a, Node> { // http://dom.spec.whatwg.org/#dom-node-parentnode fn GetParentNode(&self) -> Option> { - self.parent_node.clone().map(|node| Temporary::new(node)) + self.parent_node.get().map(|node| Temporary::new(node)) } // http://dom.spec.whatwg.org/#dom-node-parentelement fn GetParentElement(&self) -> Option> { - self.parent_node.clone() + self.parent_node.get() .and_then(|parent| { let parent = parent.root(); ElementCast::to_ref(&*parent).map(|elem| { @@ -1443,12 +1443,12 @@ impl<'a> NodeMethods for JSRef<'a, Node> { // http://dom.spec.whatwg.org/#dom-node-haschildnodes fn HasChildNodes(&self) -> bool { - self.first_child.is_some() + self.first_child.get().is_some() } // http://dom.spec.whatwg.org/#dom-node-childnodes fn ChildNodes(&mut self) -> Temporary { - match self.child_list { + match self.child_list.get() { None => (), Some(ref list) => return Temporary::new(list.clone()), } @@ -1457,27 +1457,27 @@ impl<'a> NodeMethods for JSRef<'a, Node> { let window = doc.deref().window.root(); let child_list = NodeList::new_child_list(&*window, self); self.child_list.assign(Some(child_list)); - Temporary::new(self.child_list.get_ref().clone()) + Temporary::new(self.child_list.get().get_ref().clone()) } // http://dom.spec.whatwg.org/#dom-node-firstchild fn GetFirstChild(&self) -> Option> { - self.first_child.clone().map(|node| Temporary::new(node)) + self.first_child.get().map(|node| Temporary::new(node)) } // http://dom.spec.whatwg.org/#dom-node-lastchild fn GetLastChild(&self) -> Option> { - self.last_child.clone().map(|node| Temporary::new(node)) + self.last_child.get().map(|node| Temporary::new(node)) } // http://dom.spec.whatwg.org/#dom-node-previoussibling fn GetPreviousSibling(&self) -> Option> { - self.prev_sibling.clone().map(|node| Temporary::new(node)) + self.prev_sibling.get().map(|node| Temporary::new(node)) } // http://dom.spec.whatwg.org/#dom-node-nextsibling fn GetNextSibling(&self) -> Option> { - self.next_sibling.clone().map(|node| Temporary::new(node)) + self.next_sibling.get().map(|node| Temporary::new(node)) } // http://dom.spec.whatwg.org/#dom-node-nodevalue