diff options
-rw-r--r-- | crates/ra_db/src/lib.rs | 6 | ||||
-rw-r--r-- | crates/ra_hir/src/db.rs | 4 | ||||
-rw-r--r-- | crates/ra_hir/src/ids.rs | 14 | ||||
-rw-r--r-- | crates/ra_ide_api/src/completion/completion_context.rs | 4 | ||||
-rw-r--r-- | crates/ra_ide_api/src/status.rs | 12 | ||||
-rw-r--r-- | crates/ra_ide_api/src/symbol_index.rs | 4 | ||||
-rw-r--r-- | crates/ra_mbe/src/syntax_bridge.rs | 52 | ||||
-rw-r--r-- | crates/ra_mbe/src/tests.rs | 30 | ||||
-rw-r--r-- | crates/ra_syntax/src/lib.rs | 51 | ||||
-rw-r--r-- | crates/ra_syntax/src/syntax_node.rs | 7 |
10 files changed, 103 insertions, 81 deletions
diff --git a/crates/ra_db/src/lib.rs b/crates/ra_db/src/lib.rs index 11e18a03d..b82d1bda0 100644 --- a/crates/ra_db/src/lib.rs +++ b/crates/ra_db/src/lib.rs | |||
@@ -5,7 +5,7 @@ mod input; | |||
5 | use std::{panic, sync::Arc}; | 5 | use std::{panic, sync::Arc}; |
6 | 6 | ||
7 | use ra_prof::profile; | 7 | use ra_prof::profile; |
8 | use ra_syntax::{Parse, SourceFile, TextRange, TextUnit}; | 8 | use ra_syntax::{ast, Parse, SourceFile, TextRange, TextUnit}; |
9 | use relative_path::RelativePathBuf; | 9 | use relative_path::RelativePathBuf; |
10 | 10 | ||
11 | pub use crate::{ | 11 | pub use crate::{ |
@@ -74,7 +74,7 @@ pub trait SourceDatabase: CheckCanceled + std::fmt::Debug { | |||
74 | fn file_text(&self, file_id: FileId) -> Arc<String>; | 74 | fn file_text(&self, file_id: FileId) -> Arc<String>; |
75 | // Parses the file into the syntax tree. | 75 | // Parses the file into the syntax tree. |
76 | #[salsa::invoke(parse_query)] | 76 | #[salsa::invoke(parse_query)] |
77 | fn parse(&self, file_id: FileId) -> Parse; | 77 | fn parse(&self, file_id: FileId) -> Parse<ast::SourceFile>; |
78 | /// Path to a file, relative to the root of its source root. | 78 | /// Path to a file, relative to the root of its source root. |
79 | #[salsa::input] | 79 | #[salsa::input] |
80 | fn file_relative_path(&self, file_id: FileId) -> RelativePathBuf; | 80 | fn file_relative_path(&self, file_id: FileId) -> RelativePathBuf; |
@@ -98,7 +98,7 @@ fn source_root_crates(db: &impl SourceDatabase, id: SourceRootId) -> Arc<Vec<Cra | |||
98 | Arc::new(res) | 98 | Arc::new(res) |
99 | } | 99 | } |
100 | 100 | ||
101 | fn parse_query(db: &impl SourceDatabase, file_id: FileId) -> Parse { | 101 | fn parse_query(db: &impl SourceDatabase, file_id: FileId) -> Parse<ast::SourceFile> { |
102 | let _p = profile("parse_query"); | 102 | let _p = profile("parse_query"); |
103 | let text = db.file_text(file_id); | 103 | let text = db.file_text(file_id); |
104 | SourceFile::parse(&*text) | 104 | SourceFile::parse(&*text) |
diff --git a/crates/ra_hir/src/db.rs b/crates/ra_hir/src/db.rs index 040c782e6..da9f3e32d 100644 --- a/crates/ra_hir/src/db.rs +++ b/crates/ra_hir/src/db.rs | |||
@@ -2,7 +2,7 @@ use std::sync::Arc; | |||
2 | 2 | ||
3 | use parking_lot::Mutex; | 3 | use parking_lot::Mutex; |
4 | use ra_db::{salsa, SourceDatabase}; | 4 | use ra_db::{salsa, SourceDatabase}; |
5 | use ra_syntax::{ast, SmolStr, SyntaxNode, TreeArc}; | 5 | use ra_syntax::{ast, Parse, SmolStr, SyntaxNode, TreeArc}; |
6 | 6 | ||
7 | use crate::{ | 7 | use crate::{ |
8 | adt::{EnumData, StructData}, | 8 | adt::{EnumData, StructData}, |
@@ -69,7 +69,7 @@ pub trait AstDatabase: InternDatabase { | |||
69 | fn parse_or_expand(&self, file_id: HirFileId) -> Option<TreeArc<SyntaxNode>>; | 69 | fn parse_or_expand(&self, file_id: HirFileId) -> Option<TreeArc<SyntaxNode>>; |
70 | 70 | ||
71 | #[salsa::invoke(crate::ids::HirFileId::parse_macro_query)] | 71 | #[salsa::invoke(crate::ids::HirFileId::parse_macro_query)] |
72 | fn parse_macro(&self, macro_file: ids::MacroFile) -> Option<TreeArc<SyntaxNode>>; | 72 | fn parse_macro(&self, macro_file: ids::MacroFile) -> Option<Parse<SyntaxNode>>; |
73 | 73 | ||
74 | #[salsa::invoke(crate::ids::macro_def_query)] | 74 | #[salsa::invoke(crate::ids::macro_def_query)] |
75 | fn macro_def(&self, macro_id: MacroDefId) -> Option<Arc<mbe::MacroRules>>; | 75 | fn macro_def(&self, macro_id: MacroDefId) -> Option<Arc<mbe::MacroRules>>; |
diff --git a/crates/ra_hir/src/ids.rs b/crates/ra_hir/src/ids.rs index 80e9cccd6..83f5c3f39 100644 --- a/crates/ra_hir/src/ids.rs +++ b/crates/ra_hir/src/ids.rs | |||
@@ -6,7 +6,7 @@ use std::{ | |||
6 | use mbe::MacroRules; | 6 | use mbe::MacroRules; |
7 | use ra_db::{salsa, FileId}; | 7 | use ra_db::{salsa, FileId}; |
8 | use ra_prof::profile; | 8 | use ra_prof::profile; |
9 | use ra_syntax::{ast, AstNode, SyntaxNode, TreeArc}; | 9 | use ra_syntax::{ast, AstNode, Parse, SyntaxNode, TreeArc}; |
10 | 10 | ||
11 | use crate::{AstDatabase, AstId, DefDatabase, FileAstId, InternDatabase, Module, Source}; | 11 | use crate::{AstDatabase, AstId, DefDatabase, FileAstId, InternDatabase, Module, Source}; |
12 | 12 | ||
@@ -61,14 +61,16 @@ impl HirFileId { | |||
61 | ) -> Option<TreeArc<SyntaxNode>> { | 61 | ) -> Option<TreeArc<SyntaxNode>> { |
62 | match file_id.0 { | 62 | match file_id.0 { |
63 | HirFileIdRepr::File(file_id) => Some(db.parse(file_id).tree().syntax().to_owned()), | 63 | HirFileIdRepr::File(file_id) => Some(db.parse(file_id).tree().syntax().to_owned()), |
64 | HirFileIdRepr::Macro(macro_file) => db.parse_macro(macro_file), | 64 | HirFileIdRepr::Macro(macro_file) => { |
65 | db.parse_macro(macro_file).map(|it| it.tree().to_owned()) | ||
66 | } | ||
65 | } | 67 | } |
66 | } | 68 | } |
67 | 69 | ||
68 | pub(crate) fn parse_macro_query( | 70 | pub(crate) fn parse_macro_query( |
69 | db: &impl AstDatabase, | 71 | db: &impl AstDatabase, |
70 | macro_file: MacroFile, | 72 | macro_file: MacroFile, |
71 | ) -> Option<TreeArc<SyntaxNode>> { | 73 | ) -> Option<Parse<SyntaxNode>> { |
72 | let _p = profile("parse_macro_query"); | 74 | let _p = profile("parse_macro_query"); |
73 | let macro_call_id = macro_file.macro_call_id; | 75 | let macro_call_id = macro_file.macro_call_id; |
74 | let tt = db | 76 | let tt = db |
@@ -85,10 +87,8 @@ impl HirFileId { | |||
85 | }) | 87 | }) |
86 | .ok()?; | 88 | .ok()?; |
87 | match macro_file.macro_file_kind { | 89 | match macro_file.macro_file_kind { |
88 | MacroFileKind::Items => Some(mbe::token_tree_to_ast_item_list(&tt).syntax().to_owned()), | 90 | MacroFileKind::Items => Some(Parse::to_syntax(mbe::token_tree_to_ast_item_list(&tt))), |
89 | MacroFileKind::Expr => { | 91 | MacroFileKind::Expr => mbe::token_tree_to_expr(&tt).ok().map(Parse::to_syntax), |
90 | mbe::token_tree_to_expr(&tt).ok().map(|it| it.syntax().to_owned()) | ||
91 | } | ||
92 | } | 92 | } |
93 | } | 93 | } |
94 | } | 94 | } |
diff --git a/crates/ra_ide_api/src/completion/completion_context.rs b/crates/ra_ide_api/src/completion/completion_context.rs index f6584cdd6..4aa84751f 100644 --- a/crates/ra_ide_api/src/completion/completion_context.rs +++ b/crates/ra_ide_api/src/completion/completion_context.rs | |||
@@ -43,7 +43,7 @@ pub(crate) struct CompletionContext<'a> { | |||
43 | impl<'a> CompletionContext<'a> { | 43 | impl<'a> CompletionContext<'a> { |
44 | pub(super) fn new( | 44 | pub(super) fn new( |
45 | db: &'a db::RootDatabase, | 45 | db: &'a db::RootDatabase, |
46 | original_parse: &'a Parse, | 46 | original_parse: &'a Parse<ast::SourceFile>, |
47 | position: FilePosition, | 47 | position: FilePosition, |
48 | ) -> Option<CompletionContext<'a>> { | 48 | ) -> Option<CompletionContext<'a>> { |
49 | let module = source_binder::module_from_position(db, position); | 49 | let module = source_binder::module_from_position(db, position); |
@@ -83,7 +83,7 @@ impl<'a> CompletionContext<'a> { | |||
83 | } | 83 | } |
84 | } | 84 | } |
85 | 85 | ||
86 | fn fill(&mut self, original_parse: &'a Parse, offset: TextUnit) { | 86 | fn fill(&mut self, original_parse: &'a Parse<ast::SourceFile>, offset: TextUnit) { |
87 | // Insert a fake ident to get a valid parse tree. We will use this file | 87 | // Insert a fake ident to get a valid parse tree. We will use this file |
88 | // to determine context, though the original_file will be used for | 88 | // to determine context, though the original_file will be used for |
89 | // actual completion. | 89 | // actual completion. |
diff --git a/crates/ra_ide_api/src/status.rs b/crates/ra_ide_api/src/status.rs index ce27f5ae2..a31e15245 100644 --- a/crates/ra_ide_api/src/status.rs +++ b/crates/ra_ide_api/src/status.rs | |||
@@ -9,7 +9,7 @@ use ra_db::{ | |||
9 | FileTextQuery, SourceRootId, | 9 | FileTextQuery, SourceRootId, |
10 | }; | 10 | }; |
11 | use ra_prof::{memory_usage, Bytes}; | 11 | use ra_prof::{memory_usage, Bytes}; |
12 | use ra_syntax::{AstNode, Parse, SyntaxNode, TreeArc}; | 12 | use ra_syntax::{ast, AstNode, Parse, SyntaxNode}; |
13 | 13 | ||
14 | use crate::{ | 14 | use crate::{ |
15 | db::RootDatabase, | 15 | db::RootDatabase, |
@@ -79,10 +79,10 @@ impl fmt::Display for SyntaxTreeStats { | |||
79 | } | 79 | } |
80 | } | 80 | } |
81 | 81 | ||
82 | impl FromIterator<TableEntry<FileId, Parse>> for SyntaxTreeStats { | 82 | impl FromIterator<TableEntry<FileId, Parse<ast::SourceFile>>> for SyntaxTreeStats { |
83 | fn from_iter<T>(iter: T) -> SyntaxTreeStats | 83 | fn from_iter<T>(iter: T) -> SyntaxTreeStats |
84 | where | 84 | where |
85 | T: IntoIterator<Item = TableEntry<FileId, Parse>>, | 85 | T: IntoIterator<Item = TableEntry<FileId, Parse<ast::SourceFile>>>, |
86 | { | 86 | { |
87 | let mut res = SyntaxTreeStats::default(); | 87 | let mut res = SyntaxTreeStats::default(); |
88 | for entry in iter { | 88 | for entry in iter { |
@@ -96,15 +96,15 @@ impl FromIterator<TableEntry<FileId, Parse>> for SyntaxTreeStats { | |||
96 | } | 96 | } |
97 | } | 97 | } |
98 | 98 | ||
99 | impl FromIterator<TableEntry<MacroFile, Option<TreeArc<SyntaxNode>>>> for SyntaxTreeStats { | 99 | impl FromIterator<TableEntry<MacroFile, Option<Parse<SyntaxNode>>>> for SyntaxTreeStats { |
100 | fn from_iter<T>(iter: T) -> SyntaxTreeStats | 100 | fn from_iter<T>(iter: T) -> SyntaxTreeStats |
101 | where | 101 | where |
102 | T: IntoIterator<Item = TableEntry<MacroFile, Option<TreeArc<SyntaxNode>>>>, | 102 | T: IntoIterator<Item = TableEntry<MacroFile, Option<Parse<SyntaxNode>>>>, |
103 | { | 103 | { |
104 | let mut res = SyntaxTreeStats::default(); | 104 | let mut res = SyntaxTreeStats::default(); |
105 | for entry in iter { | 105 | for entry in iter { |
106 | res.total += 1; | 106 | res.total += 1; |
107 | if let Some(tree) = entry.value.and_then(|it| it) { | 107 | if let Some(tree) = entry.value.and_then(|it| it).map(|it| it.tree().to_owned()) { |
108 | res.retained += 1; | 108 | res.retained += 1; |
109 | res.retained_size += tree.memory_size_of_subtree(); | 109 | res.retained_size += tree.memory_size_of_subtree(); |
110 | } | 110 | } |
diff --git a/crates/ra_ide_api/src/symbol_index.rs b/crates/ra_ide_api/src/symbol_index.rs index 1f2ba954e..9b3a45319 100644 --- a/crates/ra_ide_api/src/symbol_index.rs +++ b/crates/ra_ide_api/src/symbol_index.rs | |||
@@ -169,7 +169,9 @@ impl SymbolIndex { | |||
169 | self.map.as_fst().size() + self.symbols.len() * mem::size_of::<FileSymbol>() | 169 | self.map.as_fst().size() + self.symbols.len() * mem::size_of::<FileSymbol>() |
170 | } | 170 | } |
171 | 171 | ||
172 | pub(crate) fn for_files(files: impl ParallelIterator<Item = (FileId, Parse)>) -> SymbolIndex { | 172 | pub(crate) fn for_files( |
173 | files: impl ParallelIterator<Item = (FileId, Parse<ast::SourceFile>)>, | ||
174 | ) -> SymbolIndex { | ||
173 | let symbols = files | 175 | let symbols = files |
174 | .flat_map(|(file_id, file)| source_file_to_file_symbols(file.tree(), file_id)) | 176 | .flat_map(|(file_id, file)| source_file_to_file_symbols(file.tree(), file_id)) |
175 | .collect::<Vec<_>>(); | 177 | .collect::<Vec<_>>(); |
diff --git a/crates/ra_mbe/src/syntax_bridge.rs b/crates/ra_mbe/src/syntax_bridge.rs index 7560d215a..bfc351f81 100644 --- a/crates/ra_mbe/src/syntax_bridge.rs +++ b/crates/ra_mbe/src/syntax_bridge.rs | |||
@@ -2,8 +2,8 @@ use crate::subtree_source::SubtreeTokenSource; | |||
2 | use crate::ExpandError; | 2 | use crate::ExpandError; |
3 | use ra_parser::{ParseError, TreeSink}; | 3 | use ra_parser::{ParseError, TreeSink}; |
4 | use ra_syntax::{ | 4 | use ra_syntax::{ |
5 | ast, AstNode, SmolStr, SyntaxElement, SyntaxKind, SyntaxKind::*, SyntaxNode, SyntaxTreeBuilder, | 5 | ast, AstNode, Parse, SmolStr, SyntaxElement, SyntaxKind, SyntaxKind::*, SyntaxNode, |
6 | TextRange, TextUnit, TreeArc, T, | 6 | SyntaxTreeBuilder, TextRange, TextUnit, T, |
7 | }; | 7 | }; |
8 | use tt::buffer::{Cursor, TokenBuffer}; | 8 | use tt::buffer::{Cursor, TokenBuffer}; |
9 | 9 | ||
@@ -45,7 +45,7 @@ pub fn syntax_node_to_token_tree(node: &SyntaxNode) -> Option<(tt::Subtree, Toke | |||
45 | // | 45 | // |
46 | // | 46 | // |
47 | 47 | ||
48 | fn token_tree_to_syntax_node<F>(tt: &tt::Subtree, f: F) -> Result<TreeArc<SyntaxNode>, ExpandError> | 48 | fn token_tree_to_syntax_node<F>(tt: &tt::Subtree, f: F) -> Result<Parse<SyntaxNode>, ExpandError> |
49 | where | 49 | where |
50 | F: Fn(&mut dyn ra_parser::TokenSource, &mut dyn ra_parser::TreeSink), | 50 | F: Fn(&mut dyn ra_parser::TokenSource, &mut dyn ra_parser::TreeSink), |
51 | { | 51 | { |
@@ -58,50 +58,44 @@ where | |||
58 | return Err(ExpandError::ConversionError); | 58 | return Err(ExpandError::ConversionError); |
59 | } | 59 | } |
60 | //FIXME: would be cool to report errors | 60 | //FIXME: would be cool to report errors |
61 | let (tree, _errors) = tree_sink.inner.finish(); | 61 | let parse = tree_sink.inner.finish(); |
62 | Ok(tree) | 62 | Ok(parse) |
63 | } | 63 | } |
64 | 64 | ||
65 | /// Parses the token tree (result of macro expansion) to an expression | 65 | /// Parses the token tree (result of macro expansion) to an expression |
66 | pub fn token_tree_to_expr(tt: &tt::Subtree) -> Result<TreeArc<ast::Expr>, ExpandError> { | 66 | pub fn token_tree_to_expr(tt: &tt::Subtree) -> Result<Parse<ast::Expr>, ExpandError> { |
67 | let syntax = token_tree_to_syntax_node(tt, ra_parser::parse_expr)?; | 67 | let parse = token_tree_to_syntax_node(tt, ra_parser::parse_expr)?; |
68 | ast::Expr::cast(&syntax) | 68 | parse.cast().ok_or_else(|| crate::ExpandError::ConversionError) |
69 | .map(|m| m.to_owned()) | ||
70 | .ok_or_else(|| crate::ExpandError::ConversionError) | ||
71 | } | 69 | } |
72 | 70 | ||
73 | /// Parses the token tree (result of macro expansion) to a Pattern | 71 | /// Parses the token tree (result of macro expansion) to a Pattern |
74 | pub fn token_tree_to_pat(tt: &tt::Subtree) -> Result<TreeArc<ast::Pat>, ExpandError> { | 72 | pub fn token_tree_to_pat(tt: &tt::Subtree) -> Result<Parse<ast::Pat>, ExpandError> { |
75 | let syntax = token_tree_to_syntax_node(tt, ra_parser::parse_pat)?; | 73 | let parse = token_tree_to_syntax_node(tt, ra_parser::parse_pat)?; |
76 | ast::Pat::cast(&syntax).map(|m| m.to_owned()).ok_or_else(|| ExpandError::ConversionError) | 74 | parse.cast().ok_or_else(|| crate::ExpandError::ConversionError) |
77 | } | 75 | } |
78 | 76 | ||
79 | /// Parses the token tree (result of macro expansion) to a Type | 77 | /// Parses the token tree (result of macro expansion) to a Type |
80 | pub fn token_tree_to_ty(tt: &tt::Subtree) -> Result<TreeArc<ast::TypeRef>, ExpandError> { | 78 | pub fn token_tree_to_ty(tt: &tt::Subtree) -> Result<Parse<ast::TypeRef>, ExpandError> { |
81 | let syntax = token_tree_to_syntax_node(tt, ra_parser::parse_ty)?; | 79 | let parse = token_tree_to_syntax_node(tt, ra_parser::parse_ty)?; |
82 | ast::TypeRef::cast(&syntax).map(|m| m.to_owned()).ok_or_else(|| ExpandError::ConversionError) | 80 | parse.cast().ok_or_else(|| crate::ExpandError::ConversionError) |
83 | } | 81 | } |
84 | 82 | ||
85 | /// Parses the token tree (result of macro expansion) as a sequence of stmts | 83 | /// Parses the token tree (result of macro expansion) as a sequence of stmts |
86 | pub fn token_tree_to_macro_stmts( | 84 | pub fn token_tree_to_macro_stmts(tt: &tt::Subtree) -> Result<Parse<ast::MacroStmts>, ExpandError> { |
87 | tt: &tt::Subtree, | 85 | let parse = token_tree_to_syntax_node(tt, ra_parser::parse_macro_stmts)?; |
88 | ) -> Result<TreeArc<ast::MacroStmts>, ExpandError> { | 86 | parse.cast().ok_or_else(|| crate::ExpandError::ConversionError) |
89 | let syntax = token_tree_to_syntax_node(tt, ra_parser::parse_macro_stmts)?; | ||
90 | ast::MacroStmts::cast(&syntax).map(|m| m.to_owned()).ok_or_else(|| ExpandError::ConversionError) | ||
91 | } | 87 | } |
92 | 88 | ||
93 | /// Parses the token tree (result of macro expansion) as a sequence of items | 89 | /// Parses the token tree (result of macro expansion) as a sequence of items |
94 | pub fn token_tree_to_macro_items( | 90 | pub fn token_tree_to_macro_items(tt: &tt::Subtree) -> Result<Parse<ast::MacroItems>, ExpandError> { |
95 | tt: &tt::Subtree, | 91 | let parse = token_tree_to_syntax_node(tt, ra_parser::parse_macro_items)?; |
96 | ) -> Result<TreeArc<ast::MacroItems>, ExpandError> { | 92 | parse.cast().ok_or_else(|| crate::ExpandError::ConversionError) |
97 | let syntax = token_tree_to_syntax_node(tt, ra_parser::parse_macro_items)?; | ||
98 | ast::MacroItems::cast(&syntax).map(|m| m.to_owned()).ok_or_else(|| ExpandError::ConversionError) | ||
99 | } | 93 | } |
100 | 94 | ||
101 | /// Parses the token tree (result of macro expansion) as a sequence of items | 95 | /// Parses the token tree (result of macro expansion) as a sequence of items |
102 | pub fn token_tree_to_ast_item_list(tt: &tt::Subtree) -> TreeArc<ast::SourceFile> { | 96 | pub fn token_tree_to_ast_item_list(tt: &tt::Subtree) -> Parse<ast::SourceFile> { |
103 | let syntax = token_tree_to_syntax_node(tt, ra_parser::parse).unwrap(); | 97 | let parse = token_tree_to_syntax_node(tt, ra_parser::parse).unwrap(); |
104 | ast::SourceFile::cast(&syntax).unwrap().to_owned() | 98 | parse.cast().unwrap() |
105 | } | 99 | } |
106 | 100 | ||
107 | impl TokenMap { | 101 | impl TokenMap { |
diff --git a/crates/ra_mbe/src/tests.rs b/crates/ra_mbe/src/tests.rs index 5a1494fee..419b2c099 100644 --- a/crates/ra_mbe/src/tests.rs +++ b/crates/ra_mbe/src/tests.rs | |||
@@ -72,7 +72,7 @@ pub(crate) fn expand_to_items( | |||
72 | invocation: &str, | 72 | invocation: &str, |
73 | ) -> ra_syntax::TreeArc<ast::MacroItems> { | 73 | ) -> ra_syntax::TreeArc<ast::MacroItems> { |
74 | let expanded = expand(rules, invocation); | 74 | let expanded = expand(rules, invocation); |
75 | token_tree_to_macro_items(&expanded).unwrap() | 75 | token_tree_to_macro_items(&expanded).unwrap().tree().to_owned() |
76 | } | 76 | } |
77 | 77 | ||
78 | #[allow(unused)] | 78 | #[allow(unused)] |
@@ -81,7 +81,7 @@ pub(crate) fn expand_to_stmts( | |||
81 | invocation: &str, | 81 | invocation: &str, |
82 | ) -> ra_syntax::TreeArc<ast::MacroStmts> { | 82 | ) -> ra_syntax::TreeArc<ast::MacroStmts> { |
83 | let expanded = expand(rules, invocation); | 83 | let expanded = expand(rules, invocation); |
84 | token_tree_to_macro_stmts(&expanded).unwrap() | 84 | token_tree_to_macro_stmts(&expanded).unwrap().tree().to_owned() |
85 | } | 85 | } |
86 | 86 | ||
87 | pub(crate) fn expand_to_expr( | 87 | pub(crate) fn expand_to_expr( |
@@ -89,7 +89,7 @@ pub(crate) fn expand_to_expr( | |||
89 | invocation: &str, | 89 | invocation: &str, |
90 | ) -> ra_syntax::TreeArc<ast::Expr> { | 90 | ) -> ra_syntax::TreeArc<ast::Expr> { |
91 | let expanded = expand(rules, invocation); | 91 | let expanded = expand(rules, invocation); |
92 | token_tree_to_expr(&expanded).unwrap() | 92 | token_tree_to_expr(&expanded).unwrap().tree().to_owned() |
93 | } | 93 | } |
94 | 94 | ||
95 | pub(crate) fn text_to_tokentree(text: &str) -> tt::Subtree { | 95 | pub(crate) fn text_to_tokentree(text: &str) -> tt::Subtree { |
@@ -164,22 +164,22 @@ pub(crate) fn assert_expansion( | |||
164 | 164 | ||
165 | let (expanded_tree, expected_tree) = match kind { | 165 | let (expanded_tree, expected_tree) = match kind { |
166 | MacroKind::Items => { | 166 | MacroKind::Items => { |
167 | let expanded_tree = token_tree_to_macro_items(&expanded); | 167 | let expanded_tree = token_tree_to_macro_items(&expanded).unwrap().tree().to_owned(); |
168 | let expected_tree = token_tree_to_macro_items(&expected); | 168 | let expected_tree = token_tree_to_macro_items(&expected).unwrap().tree().to_owned(); |
169 | 169 | ||
170 | ( | 170 | ( |
171 | debug_dump_ignore_spaces(expanded_tree.unwrap().syntax()).trim().to_string(), | 171 | debug_dump_ignore_spaces(expanded_tree.syntax()).trim().to_string(), |
172 | debug_dump_ignore_spaces(expected_tree.unwrap().syntax()).trim().to_string(), | 172 | debug_dump_ignore_spaces(expected_tree.syntax()).trim().to_string(), |
173 | ) | 173 | ) |
174 | } | 174 | } |
175 | 175 | ||
176 | MacroKind::Stmts => { | 176 | MacroKind::Stmts => { |
177 | let expanded_tree = token_tree_to_macro_stmts(&expanded); | 177 | let expanded_tree = token_tree_to_macro_stmts(&expanded).unwrap().tree().to_owned(); |
178 | let expected_tree = token_tree_to_macro_stmts(&expected); | 178 | let expected_tree = token_tree_to_macro_stmts(&expected).unwrap().tree().to_owned(); |
179 | 179 | ||
180 | ( | 180 | ( |
181 | debug_dump_ignore_spaces(expanded_tree.unwrap().syntax()).trim().to_string(), | 181 | debug_dump_ignore_spaces(expanded_tree.syntax()).trim().to_string(), |
182 | debug_dump_ignore_spaces(expected_tree.unwrap().syntax()).trim().to_string(), | 182 | debug_dump_ignore_spaces(expected_tree.syntax()).trim().to_string(), |
183 | ) | 183 | ) |
184 | } | 184 | } |
185 | }; | 185 | }; |
@@ -419,9 +419,9 @@ fn test_expand_to_item_list() { | |||
419 | ", | 419 | ", |
420 | ); | 420 | ); |
421 | let expansion = expand(&rules, "structs!(Foo, Bar);"); | 421 | let expansion = expand(&rules, "structs!(Foo, Bar);"); |
422 | let tree = token_tree_to_macro_items(&expansion); | 422 | let tree = token_tree_to_macro_items(&expansion).unwrap().tree().to_owned(); |
423 | assert_eq!( | 423 | assert_eq!( |
424 | tree.unwrap().syntax().debug_dump().trim(), | 424 | tree.syntax().debug_dump().trim(), |
425 | r#" | 425 | r#" |
426 | MACRO_ITEMS@[0; 40) | 426 | MACRO_ITEMS@[0; 40) |
427 | STRUCT_DEF@[0; 20) | 427 | STRUCT_DEF@[0; 20) |
@@ -537,10 +537,10 @@ fn test_tt_to_stmts() { | |||
537 | ); | 537 | ); |
538 | 538 | ||
539 | let expanded = expand(&rules, "foo!{}"); | 539 | let expanded = expand(&rules, "foo!{}"); |
540 | let stmts = token_tree_to_macro_stmts(&expanded); | 540 | let stmts = token_tree_to_macro_stmts(&expanded).unwrap().tree().to_owned(); |
541 | 541 | ||
542 | assert_eq!( | 542 | assert_eq!( |
543 | stmts.unwrap().syntax().debug_dump().trim(), | 543 | stmts.syntax().debug_dump().trim(), |
544 | r#"MACRO_STMTS@[0; 15) | 544 | r#"MACRO_STMTS@[0; 15) |
545 | LET_STMT@[0; 7) | 545 | LET_STMT@[0; 7) |
546 | LET_KW@[0; 3) "let" | 546 | LET_KW@[0; 3) "let" |
diff --git a/crates/ra_syntax/src/lib.rs b/crates/ra_syntax/src/lib.rs index 0fa2fe382..534c206a6 100644 --- a/crates/ra_syntax/src/lib.rs +++ b/crates/ra_syntax/src/lib.rs | |||
@@ -43,8 +43,8 @@ pub use crate::{ | |||
43 | ptr::{AstPtr, SyntaxNodePtr}, | 43 | ptr::{AstPtr, SyntaxNodePtr}, |
44 | syntax_error::{Location, SyntaxError, SyntaxErrorKind}, | 44 | syntax_error::{Location, SyntaxError, SyntaxErrorKind}, |
45 | syntax_node::{ | 45 | syntax_node::{ |
46 | Direction, InsertPosition, SyntaxElement, SyntaxNode, SyntaxToken, SyntaxTreeBuilder, | 46 | Direction, InsertPosition, SyntaxElement, SyntaxNode, SyntaxNodeWrapper, SyntaxToken, |
47 | TreeArc, WalkEvent, | 47 | SyntaxTreeBuilder, TreeArc, WalkEvent, |
48 | }, | 48 | }, |
49 | syntax_text::SyntaxText, | 49 | syntax_text::SyntaxText, |
50 | }; | 50 | }; |
@@ -57,14 +57,24 @@ pub use rowan::{SmolStr, TextRange, TextUnit}; | |||
57 | /// | 57 | /// |
58 | /// Note that we always produce a syntax tree, even for completely invalid | 58 | /// Note that we always produce a syntax tree, even for completely invalid |
59 | /// files. | 59 | /// files. |
60 | #[derive(Debug, Clone, PartialEq, Eq)] | 60 | #[derive(Debug, PartialEq, Eq)] |
61 | pub struct Parse { | 61 | pub struct Parse<T: SyntaxNodeWrapper> { |
62 | tree: TreeArc<SourceFile>, | 62 | tree: TreeArc<T>, |
63 | errors: Arc<Vec<SyntaxError>>, | 63 | errors: Arc<Vec<SyntaxError>>, |
64 | } | 64 | } |
65 | 65 | ||
66 | impl Parse { | 66 | impl<T: SyntaxNodeWrapper> Clone for Parse<T> { |
67 | pub fn tree(&self) -> &SourceFile { | 67 | fn clone(&self) -> Parse<T> { |
68 | Parse { tree: self.tree.clone(), errors: self.errors.clone() } | ||
69 | } | ||
70 | } | ||
71 | |||
72 | impl<T: SyntaxNodeWrapper> Parse<T> { | ||
73 | fn new(tree: TreeArc<T>, errors: Vec<SyntaxError>) -> Parse<T> { | ||
74 | Parse { tree, errors: Arc::new(errors) } | ||
75 | } | ||
76 | |||
77 | pub fn tree(&self) -> &T { | ||
68 | &*self.tree | 78 | &*self.tree |
69 | } | 79 | } |
70 | 80 | ||
@@ -72,18 +82,22 @@ impl Parse { | |||
72 | &*self.errors | 82 | &*self.errors |
73 | } | 83 | } |
74 | 84 | ||
75 | pub fn ok(self) -> Result<TreeArc<SourceFile>, Arc<Vec<SyntaxError>>> { | 85 | pub fn ok(self) -> Result<TreeArc<T>, Arc<Vec<SyntaxError>>> { |
76 | if self.errors.is_empty() { | 86 | if self.errors.is_empty() { |
77 | Ok(self.tree) | 87 | Ok(self.tree) |
78 | } else { | 88 | } else { |
79 | Err(self.errors) | 89 | Err(self.errors) |
80 | } | 90 | } |
81 | } | 91 | } |
92 | } | ||
82 | 93 | ||
83 | pub fn reparse(&self, edit: &AtomTextEdit) -> Parse { | 94 | impl<T: AstNode> Parse<T> { |
84 | self.incremental_reparse(edit).unwrap_or_else(|| self.full_reparse(edit)) | 95 | pub fn to_syntax(this: Self) -> Parse<SyntaxNode> { |
96 | Parse { tree: this.tree().syntax().to_owned(), errors: this.errors } | ||
85 | } | 97 | } |
98 | } | ||
86 | 99 | ||
100 | impl Parse<SourceFile> { | ||
87 | pub fn debug_dump(&self) -> String { | 101 | pub fn debug_dump(&self) -> String { |
88 | let mut buf = self.tree.syntax().debug_dump(); | 102 | let mut buf = self.tree.syntax().debug_dump(); |
89 | for err in self.errors.iter() { | 103 | for err in self.errors.iter() { |
@@ -92,7 +106,11 @@ impl Parse { | |||
92 | buf | 106 | buf |
93 | } | 107 | } |
94 | 108 | ||
95 | fn incremental_reparse(&self, edit: &AtomTextEdit) -> Option<Parse> { | 109 | pub fn reparse(&self, edit: &AtomTextEdit) -> Parse<SourceFile> { |
110 | self.incremental_reparse(edit).unwrap_or_else(|| self.full_reparse(edit)) | ||
111 | } | ||
112 | |||
113 | fn incremental_reparse(&self, edit: &AtomTextEdit) -> Option<Parse<SourceFile>> { | ||
96 | // FIXME: validation errors are not handled here | 114 | // FIXME: validation errors are not handled here |
97 | parsing::incremental_reparse(self.tree.syntax(), edit, self.errors.to_vec()).map( | 115 | parsing::incremental_reparse(self.tree.syntax(), edit, self.errors.to_vec()).map( |
98 | |(green_node, errors, _reparsed_range)| Parse { | 116 | |(green_node, errors, _reparsed_range)| Parse { |
@@ -102,12 +120,19 @@ impl Parse { | |||
102 | ) | 120 | ) |
103 | } | 121 | } |
104 | 122 | ||
105 | fn full_reparse(&self, edit: &AtomTextEdit) -> Parse { | 123 | fn full_reparse(&self, edit: &AtomTextEdit) -> Parse<SourceFile> { |
106 | let text = edit.apply(self.tree.syntax().text().to_string()); | 124 | let text = edit.apply(self.tree.syntax().text().to_string()); |
107 | SourceFile::parse(&text) | 125 | SourceFile::parse(&text) |
108 | } | 126 | } |
109 | } | 127 | } |
110 | 128 | ||
129 | impl Parse<SyntaxNode> { | ||
130 | pub fn cast<T: AstNode>(self) -> Option<Parse<T>> { | ||
131 | let node = T::cast(&self.tree)?; | ||
132 | Some(Parse { tree: node.to_owned(), errors: self.errors }) | ||
133 | } | ||
134 | } | ||
135 | |||
111 | /// `SourceFile` represents a parse tree for a single Rust file. | 136 | /// `SourceFile` represents a parse tree for a single Rust file. |
112 | pub use crate::ast::SourceFile; | 137 | pub use crate::ast::SourceFile; |
113 | 138 | ||
@@ -121,7 +146,7 @@ impl SourceFile { | |||
121 | TreeArc::cast(root) | 146 | TreeArc::cast(root) |
122 | } | 147 | } |
123 | 148 | ||
124 | pub fn parse(text: &str) -> Parse { | 149 | pub fn parse(text: &str) -> Parse<SourceFile> { |
125 | let (green, mut errors) = parsing::parse_text(text); | 150 | let (green, mut errors) = parsing::parse_text(text); |
126 | let tree = SourceFile::new(green); | 151 | let tree = SourceFile::new(green); |
127 | errors.extend(validation::validate(&tree)); | 152 | errors.extend(validation::validate(&tree)); |
diff --git a/crates/ra_syntax/src/syntax_node.rs b/crates/ra_syntax/src/syntax_node.rs index a1f9a59b6..e57813a94 100644 --- a/crates/ra_syntax/src/syntax_node.rs +++ b/crates/ra_syntax/src/syntax_node.rs | |||
@@ -18,7 +18,8 @@ use rowan::{GreenNodeBuilder, TransparentNewType}; | |||
18 | 18 | ||
19 | use crate::{ | 19 | use crate::{ |
20 | syntax_error::{SyntaxError, SyntaxErrorKind}, | 20 | syntax_error::{SyntaxError, SyntaxErrorKind}, |
21 | AstNode, SmolStr, SourceFile, SyntaxKind, SyntaxNodePtr, SyntaxText, TextRange, TextUnit, | 21 | AstNode, Parse, SmolStr, SourceFile, SyntaxKind, SyntaxNodePtr, SyntaxText, TextRange, |
22 | TextUnit, | ||
22 | }; | 23 | }; |
23 | 24 | ||
24 | pub use rowan::WalkEvent; | 25 | pub use rowan::WalkEvent; |
@@ -594,13 +595,13 @@ impl SyntaxTreeBuilder { | |||
594 | (green, self.errors) | 595 | (green, self.errors) |
595 | } | 596 | } |
596 | 597 | ||
597 | pub fn finish(self) -> (TreeArc<SyntaxNode>, Vec<SyntaxError>) { | 598 | pub fn finish(self) -> Parse<SyntaxNode> { |
598 | let (green, errors) = self.finish_raw(); | 599 | let (green, errors) = self.finish_raw(); |
599 | let node = SyntaxNode::new(green); | 600 | let node = SyntaxNode::new(green); |
600 | if cfg!(debug_assertions) { | 601 | if cfg!(debug_assertions) { |
601 | crate::validation::validate_block_structure(&node); | 602 | crate::validation::validate_block_structure(&node); |
602 | } | 603 | } |
603 | (node, errors) | 604 | Parse::new(node, errors) |
604 | } | 605 | } |
605 | 606 | ||
606 | pub fn token(&mut self, kind: SyntaxKind, text: SmolStr) { | 607 | pub fn token(&mut self, kind: SyntaxKind, text: SmolStr) { |