aboutsummaryrefslogtreecommitdiff
path: root/crates
diff options
context:
space:
mode:
authorAleksey Kladov <[email protected]>2019-01-01 16:23:03 +0000
committerAleksey Kladov <[email protected]>2019-01-01 19:15:35 +0000
commite5b2fd67711eeab6146021542937028dff3bf8a7 (patch)
tree01b9e5dadc6a81c94cba5da4a19daea0b6ed7101 /crates
parent832bae8e28768759ba3dc75cf6a10fb333741d8e (diff)
hard-code expansion of query_group
Diffstat (limited to 'crates')
-rw-r--r--crates/ra_analysis/src/syntax_highlighting.rs24
-rw-r--r--crates/ra_hir/src/macros.rs44
2 files changed, 60 insertions, 8 deletions
diff --git a/crates/ra_analysis/src/syntax_highlighting.rs b/crates/ra_analysis/src/syntax_highlighting.rs
index a644b3fe0..ccea4aee3 100644
--- a/crates/ra_analysis/src/syntax_highlighting.rs
+++ b/crates/ra_analysis/src/syntax_highlighting.rs
@@ -44,7 +44,7 @@ mod tests {
44 fn main() { 44 fn main() {
45 ctry!({ let x = 92; x}); 45 ctry!({ let x = 92; x});
46 } 46 }
47 ", 47 ",
48 ); 48 );
49 let highlights = analysis.highlight(file_id).unwrap(); 49 let highlights = analysis.highlight(file_id).unwrap();
50 assert_eq_dbg( 50 assert_eq_dbg(
@@ -60,4 +60,26 @@ mod tests {
60 &highlights, 60 &highlights,
61 ) 61 )
62 } 62 }
63
64 // FIXME: this test is not really necessary: artifact of the inital hacky
65 // macros implementation.
66 #[test]
67 fn highlight_query_group_macro() {
68 let (analysis, file_id) = single_file(
69 "
70 salsa::query_group! {
71 pub trait HirDatabase: SyntaxDatabase {}
72 }
73 ",
74 );
75 let highlights = analysis.highlight(file_id).unwrap();
76 assert_eq_dbg(
77 r#"[HighlightedRange { range: [20; 32), tag: "macro" },
78 HighlightedRange { range: [13; 18), tag: "text" },
79 HighlightedRange { range: [51; 54), tag: "keyword" },
80 HighlightedRange { range: [55; 60), tag: "keyword" },
81 HighlightedRange { range: [61; 72), tag: "function" }]"#,
82 &highlights,
83 )
84 }
63} 85}
diff --git a/crates/ra_hir/src/macros.rs b/crates/ra_hir/src/macros.rs
index d9de2d8bd..932e2b574 100644
--- a/crates/ra_hir/src/macros.rs
+++ b/crates/ra_hir/src/macros.rs
@@ -3,7 +3,7 @@ use std::sync::Arc;
3use ra_db::{LocalSyntaxPtr, LocationIntener}; 3use ra_db::{LocalSyntaxPtr, LocationIntener};
4use ra_syntax::{ 4use ra_syntax::{
5 TextRange, TextUnit, SourceFileNode, AstNode, SyntaxNode, 5 TextRange, TextUnit, SourceFileNode, AstNode, SyntaxNode,
6 ast, 6 ast::{self, NameOwner},
7}; 7};
8 8
9use crate::{SourceRootId, module::ModuleId, SourceItemId, HirDatabase}; 9use crate::{SourceRootId, module::ModuleId, SourceItemId, HirDatabase};
@@ -44,6 +44,7 @@ impl MacroCallLoc {
44#[derive(Debug, Clone, PartialEq, Eq, Hash)] 44#[derive(Debug, Clone, PartialEq, Eq, Hash)]
45pub enum MacroDef { 45pub enum MacroDef {
46 CTry, 46 CTry,
47 QueryGroup,
47} 48}
48 49
49impl MacroDef { 50impl MacroDef {
@@ -57,14 +58,14 @@ impl MacroDef {
57 fn from_call(macro_call: ast::MacroCall) -> Option<(MacroDef, MacroInput)> { 58 fn from_call(macro_call: ast::MacroCall) -> Option<(MacroDef, MacroInput)> {
58 let def = { 59 let def = {
59 let path = macro_call.path()?; 60 let path = macro_call.path()?;
60 if path.qualifier().is_some() {
61 return None;
62 }
63 let name_ref = path.segment()?.name_ref()?; 61 let name_ref = path.segment()?.name_ref()?;
64 if name_ref.text() != "ctry" { 62 if name_ref.text() == "ctry" {
63 MacroDef::CTry
64 } else if name_ref.text() == "query_group" {
65 MacroDef::QueryGroup
66 } else {
65 return None; 67 return None;
66 } 68 }
67 MacroDef::CTry
68 }; 69 };
69 70
70 let input = { 71 let input = {
@@ -77,7 +78,12 @@ impl MacroDef {
77 } 78 }
78 79
79 fn expand(self, input: MacroInput) -> Option<MacroExpansion> { 80 fn expand(self, input: MacroInput) -> Option<MacroExpansion> {
80 let MacroDef::CTry = self; 81 match self {
82 MacroDef::CTry => self.expand_ctry(input),
83 MacroDef::QueryGroup => self.expand_query_group(input),
84 }
85 }
86 fn expand_ctry(self, input: MacroInput) -> Option<MacroExpansion> {
81 let text = format!( 87 let text = format!(
82 r" 88 r"
83 fn dummy() {{ 89 fn dummy() {{
@@ -101,6 +107,30 @@ impl MacroDef {
101 }; 107 };
102 Some(res) 108 Some(res)
103 } 109 }
110 fn expand_query_group(self, input: MacroInput) -> Option<MacroExpansion> {
111 let anchor = "trait ";
112 let pos = input.text.find(anchor)? + anchor.len();
113 let trait_name = input.text[pos..]
114 .chars()
115 .take_while(|c| c.is_alphabetic())
116 .collect::<String>();
117 if trait_name.is_empty() {
118 return None;
119 }
120 let src_range = TextRange::offset_len((pos as u32).into(), TextUnit::of_str(&trait_name));
121 let text = format!(r"trait {} {{ }}", trait_name);
122 let file = SourceFileNode::parse(&text);
123 let trait_def = file.syntax().descendants().find_map(ast::TraitDef::cast)?;
124 let name = trait_def.name()?;
125 let ptr = LocalSyntaxPtr::new(trait_def.syntax());
126 let ranges_map = vec![(src_range, name.syntax().range())];
127 let res = MacroExpansion {
128 text,
129 ranges_map,
130 ptr,
131 };
132 Some(res)
133 }
104} 134}
105 135
106#[derive(Debug, Clone, PartialEq, Eq, Hash)] 136#[derive(Debug, Clone, PartialEq, Eq, Hash)]