diff options
author | Aleksey Kladov <[email protected]> | 2018-07-31 11:49:03 +0100 |
---|---|---|
committer | Aleksey Kladov <[email protected]> | 2018-07-31 11:49:03 +0100 |
commit | 407ebbc552fd9a8e73a9e46873ab834c54cea967 (patch) | |
tree | b68be1e094307d54ac060181a8c752d9d7fb1db8 | |
parent | 87b5e14c75dbc02b5bc610dfa33d5789570df5db (diff) |
More fool-proof API
-rw-r--r-- | src/yellow/red.rs | 9 | ||||
-rw-r--r-- | src/yellow/syntax.rs | 17 |
2 files changed, 14 insertions, 12 deletions
diff --git a/src/yellow/red.rs b/src/yellow/red.rs index 8329ec5b2..a30318c6e 100644 --- a/src/yellow/red.rs +++ b/src/yellow/red.rs | |||
@@ -61,9 +61,12 @@ impl RedNode { | |||
61 | self.green.children().len() | 61 | self.green.children().len() |
62 | } | 62 | } |
63 | 63 | ||
64 | pub(crate) fn nth_child(&self, idx: usize) -> ptr::NonNull<RedNode> { | 64 | pub(crate) fn get_child(&self, idx: usize) -> Option<ptr::NonNull<RedNode>> { |
65 | if idx >= self.n_children() { | ||
66 | return None | ||
67 | } | ||
65 | match &self.children.read().unwrap()[idx] { | 68 | match &self.children.read().unwrap()[idx] { |
66 | Some(child) => return child.into(), | 69 | Some(child) => return Some(child.into()), |
67 | None => (), | 70 | None => (), |
68 | } | 71 | } |
69 | let mut children = self.children.write().unwrap(); | 72 | let mut children = self.children.write().unwrap(); |
@@ -78,7 +81,7 @@ impl RedNode { | |||
78 | RedNode::new_child(green_children[idx].clone(), self.into(), start_offset, idx); | 81 | RedNode::new_child(green_children[idx].clone(), self.into(), start_offset, idx); |
79 | children[idx] = Some(child) | 82 | children[idx] = Some(child) |
80 | } | 83 | } |
81 | children[idx].as_ref().unwrap().into() | 84 | Some(children[idx].as_ref().unwrap().into()) |
82 | } | 85 | } |
83 | 86 | ||
84 | pub(crate) fn parent(&self) -> Option<ptr::NonNull<RedNode>> { | 87 | pub(crate) fn parent(&self) -> Option<ptr::NonNull<RedNode>> { |
diff --git a/src/yellow/syntax.rs b/src/yellow/syntax.rs index 58e8ab9b6..41dcf3761 100644 --- a/src/yellow/syntax.rs +++ b/src/yellow/syntax.rs | |||
@@ -6,8 +6,10 @@ use { | |||
6 | TextRange, TextUnit, | 6 | TextRange, TextUnit, |
7 | }; | 7 | }; |
8 | 8 | ||
9 | pub trait TreeRoot: Deref<Target = SyntaxRoot> + Clone {} | 9 | pub trait TreeRoot: Deref<Target=SyntaxRoot> + Clone {} |
10 | |||
10 | impl TreeRoot for Arc<SyntaxRoot> {} | 11 | impl TreeRoot for Arc<SyntaxRoot> {} |
12 | |||
11 | impl<'a> TreeRoot for &'a SyntaxRoot {} | 13 | impl<'a> TreeRoot for &'a SyntaxRoot {} |
12 | 14 | ||
13 | #[derive(Clone, Copy)] | 15 | #[derive(Clone, Copy)] |
@@ -18,14 +20,13 @@ pub struct SyntaxNode<R: TreeRoot = Arc<SyntaxRoot>> { | |||
18 | red: ptr::NonNull<RedNode>, | 20 | red: ptr::NonNull<RedNode>, |
19 | } | 21 | } |
20 | 22 | ||
21 | impl <R1: TreeRoot, R2: TreeRoot> PartialEq<SyntaxNode<R1>> for SyntaxNode<R2> { | 23 | impl<R1: TreeRoot, R2: TreeRoot> PartialEq<SyntaxNode<R1>> for SyntaxNode<R2> { |
22 | fn eq(&self, other: &SyntaxNode<R1>) -> bool { | 24 | fn eq(&self, other: &SyntaxNode<R1>) -> bool { |
23 | self.red == other.red | 25 | self.red == other.red |
24 | } | 26 | } |
25 | } | 27 | } |
26 | 28 | ||
27 | impl <R: TreeRoot> Eq for SyntaxNode<R> { | 29 | impl<R: TreeRoot> Eq for SyntaxNode<R> {} |
28 | } | ||
29 | 30 | ||
30 | pub type SyntaxNodeRef<'a> = SyntaxNode<&'a SyntaxRoot>; | 31 | pub type SyntaxNodeRef<'a> = SyntaxNode<&'a SyntaxRoot>; |
31 | 32 | ||
@@ -88,7 +89,7 @@ impl<R: TreeRoot> SyntaxNode<R> { | |||
88 | (0..n_children).map(move |i| { | 89 | (0..n_children).map(move |i| { |
89 | SyntaxNode { | 90 | SyntaxNode { |
90 | root: self.root.clone(), | 91 | root: self.root.clone(), |
91 | red: red.nth_child(i), | 92 | red: red.get_child(i).unwrap(), |
92 | } | 93 | } |
93 | }) | 94 | }) |
94 | } | 95 | } |
@@ -109,12 +110,10 @@ impl<R: TreeRoot> SyntaxNode<R> { | |||
109 | let red = self.red(); | 110 | let red = self.red(); |
110 | let parent = self.parent()?; | 111 | let parent = self.parent()?; |
111 | let next_sibling_idx = red.index_in_parent()? + 1; | 112 | let next_sibling_idx = red.index_in_parent()? + 1; |
112 | if next_sibling_idx == parent.red().n_children() { | 113 | let sibling_red = parent.red().get_child(next_sibling_idx)?; |
113 | return None; | ||
114 | } | ||
115 | Some(SyntaxNode { | 114 | Some(SyntaxNode { |
116 | root: self.root.clone(), | 115 | root: self.root.clone(), |
117 | red: parent.red().nth_child(next_sibling_idx), | 116 | red: sibling_red, |
118 | }) | 117 | }) |
119 | } | 118 | } |
120 | 119 | ||