aboutsummaryrefslogtreecommitdiff
path: root/crates/mbe
diff options
context:
space:
mode:
Diffstat (limited to 'crates/mbe')
-rw-r--r--crates/mbe/src/syntax_bridge.rs36
-rw-r--r--crates/mbe/src/tests.rs10
2 files changed, 26 insertions, 20 deletions
diff --git a/crates/mbe/src/syntax_bridge.rs b/crates/mbe/src/syntax_bridge.rs
index e648519f9..0cdc175be 100644
--- a/crates/mbe/src/syntax_bridge.rs
+++ b/crates/mbe/src/syntax_bridge.rs
@@ -16,16 +16,18 @@ use crate::ExpandError;
16#[derive(Debug, PartialEq, Eq, Clone, Copy)] 16#[derive(Debug, PartialEq, Eq, Clone, Copy)]
17pub enum TokenTextRange { 17pub enum TokenTextRange {
18 Token(TextRange), 18 Token(TextRange),
19 Delimiter(TextRange, TextRange), 19 Delimiter(TextRange),
20} 20}
21 21
22impl TokenTextRange { 22impl TokenTextRange {
23 pub fn by_kind(self, kind: SyntaxKind) -> Option<TextRange> { 23 pub fn by_kind(self, kind: SyntaxKind) -> Option<TextRange> {
24 match self { 24 match self {
25 TokenTextRange::Token(it) => Some(it), 25 TokenTextRange::Token(it) => Some(it),
26 TokenTextRange::Delimiter(open, close) => match kind { 26 TokenTextRange::Delimiter(it) => match kind {
27 T!['{'] | T!['('] | T!['['] => Some(open), 27 T!['{'] | T!['('] | T!['['] => Some(TextRange::at(it.start(), 1.into())),
28 T!['}'] | T![')'] | T![']'] => Some(close), 28 T!['}'] | T![')'] | T![']'] => {
29 Some(TextRange::at(it.end() - TextSize::of('}'), 1.into()))
30 }
29 _ => None, 31 _ => None,
30 }, 32 },
31 } 33 }
@@ -51,6 +53,7 @@ pub fn syntax_node_to_token_tree(node: &SyntaxNode) -> Option<(tt::Subtree, Toke
51 let global_offset = node.text_range().start(); 53 let global_offset = node.text_range().start();
52 let mut c = Convertor::new(node, global_offset); 54 let mut c = Convertor::new(node, global_offset);
53 let subtree = c.go()?; 55 let subtree = c.go()?;
56 c.id_alloc.map.entries.shrink_to_fit();
54 Some((subtree, c.id_alloc.map)) 57 Some((subtree, c.id_alloc.map))
55} 58}
56 59
@@ -113,8 +116,10 @@ impl TokenMap {
113 pub fn token_by_range(&self, relative_range: TextRange) -> Option<tt::TokenId> { 116 pub fn token_by_range(&self, relative_range: TextRange) -> Option<tt::TokenId> {
114 let &(token_id, _) = self.entries.iter().find(|(_, range)| match range { 117 let &(token_id, _) = self.entries.iter().find(|(_, range)| match range {
115 TokenTextRange::Token(it) => *it == relative_range, 118 TokenTextRange::Token(it) => *it == relative_range,
116 TokenTextRange::Delimiter(open, close) => { 119 TokenTextRange::Delimiter(it) => {
117 *open == relative_range || *close == relative_range 120 let open = TextRange::at(it.start(), 1.into());
121 let close = TextRange::at(it.end() - TextSize::of('}'), 1.into());
122 open == relative_range || close == relative_range
118 } 123 }
119 })?; 124 })?;
120 Some(token_id) 125 Some(token_id)
@@ -136,15 +141,17 @@ impl TokenMap {
136 close_relative_range: TextRange, 141 close_relative_range: TextRange,
137 ) -> usize { 142 ) -> usize {
138 let res = self.entries.len(); 143 let res = self.entries.len();
139 self.entries 144 let cover = open_relative_range.cover(close_relative_range);
140 .push((token_id, TokenTextRange::Delimiter(open_relative_range, close_relative_range))); 145
146 self.entries.push((token_id, TokenTextRange::Delimiter(cover)));
141 res 147 res
142 } 148 }
143 149
144 fn update_close_delim(&mut self, idx: usize, close_relative_range: TextRange) { 150 fn update_close_delim(&mut self, idx: usize, close_relative_range: TextRange) {
145 let (_, token_text_range) = &mut self.entries[idx]; 151 let (_, token_text_range) = &mut self.entries[idx];
146 if let TokenTextRange::Delimiter(dim, _) = token_text_range { 152 if let TokenTextRange::Delimiter(dim) = token_text_range {
147 *token_text_range = TokenTextRange::Delimiter(*dim, close_relative_range); 153 let cover = dim.cover(close_relative_range);
154 *token_text_range = TokenTextRange::Delimiter(cover);
148 } 155 }
149 } 156 }
150 157
@@ -500,7 +507,7 @@ impl SrcToken for SynToken {
500 } 507 }
501 } 508 }
502 fn to_text(&self) -> SmolStr { 509 fn to_text(&self) -> SmolStr {
503 self.token().text().clone() 510 self.token().text().into()
504 } 511 }
505} 512}
506 513
@@ -593,7 +600,8 @@ impl<'a> TtTreeSink<'a> {
593 } 600 }
594 } 601 }
595 602
596 fn finish(self) -> (Parse<SyntaxNode>, TokenMap) { 603 fn finish(mut self) -> (Parse<SyntaxNode>, TokenMap) {
604 self.token_map.entries.shrink_to_fit();
597 (self.inner.finish(), self.token_map) 605 (self.inner.finish(), self.token_map)
598 } 606 }
599} 607}
@@ -674,10 +682,8 @@ impl<'a> TreeSink for TtTreeSink<'a> {
674 self.text_pos += TextSize::of(text); 682 self.text_pos += TextSize::of(text);
675 } 683 }
676 684
677 let text = SmolStr::new(self.buf.as_str()); 685 self.inner.token(kind, self.buf.as_str());
678 self.buf.clear(); 686 self.buf.clear();
679 self.inner.token(kind, text);
680
681 // Add whitespace between adjoint puncts 687 // Add whitespace between adjoint puncts
682 let next = last.bump(); 688 let next = last.bump();
683 if let ( 689 if let (
diff --git a/crates/mbe/src/tests.rs b/crates/mbe/src/tests.rs
index 9ff901e97..bd2977ebd 100644
--- a/crates/mbe/src/tests.rs
+++ b/crates/mbe/src/tests.rs
@@ -261,7 +261,6 @@ fn test_expr_order() {
261 261
262 let dump = format!("{:#?}", expanded); 262 let dump = format!("{:#?}", expanded);
263 assert_eq_text!( 263 assert_eq_text!(
264 dump.trim(),
265 r#"[email protected] 264 r#"[email protected]
266 [email protected] 265 [email protected]
267 [email protected] "fn" 266 [email protected] "fn"
@@ -285,6 +284,7 @@ fn test_expr_order() {
285 [email protected] "2" 284 [email protected] "2"
286 [email protected] ";" 285 [email protected] ";"
287 [email protected] "}""#, 286 [email protected] "}""#,
287 dump.trim()
288 ); 288 );
289} 289}
290 290
@@ -989,7 +989,6 @@ fn test_tt_composite2() {
989 989
990 let res = format!("{:#?}", &node); 990 let res = format!("{:#?}", &node);
991 assert_eq_text!( 991 assert_eq_text!(
992 res.trim(),
993 r###"[email protected] 992 r###"[email protected]
994 [email protected] 993 [email protected]
995 [email protected] 994 [email protected]
@@ -1003,7 +1002,8 @@ fn test_tt_composite2() {
1003 [email protected] ">" 1002 [email protected] ">"
1004 [email protected] " " 1003 [email protected] " "
1005 [email protected] "#" 1004 [email protected] "#"
1006 [email protected] ")""### 1005 [email protected] ")""###,
1006 res.trim()
1007 ); 1007 );
1008} 1008}
1009 1009
@@ -1742,7 +1742,7 @@ impl MacroFixture {
1742 fn assert_expand(&self, invocation: &str, expected: &str) { 1742 fn assert_expand(&self, invocation: &str, expected: &str) {
1743 let expansion = self.expand_tt(invocation); 1743 let expansion = self.expand_tt(invocation);
1744 let actual = format!("{:?}", expansion); 1744 let actual = format!("{:?}", expansion);
1745 test_utils::assert_eq_text!(&actual.trim(), &expected.trim()); 1745 test_utils::assert_eq_text!(&expected.trim(), &actual.trim());
1746 } 1746 }
1747 1747
1748 fn assert_expand_items(&self, invocation: &str, expected: &str) -> &MacroFixture { 1748 fn assert_expand_items(&self, invocation: &str, expected: &str) -> &MacroFixture {
@@ -1941,7 +1941,6 @@ fn test_no_space_after_semi_colon() {
1941 1941
1942 let dump = format!("{:#?}", expanded); 1942 let dump = format!("{:#?}", expanded);
1943 assert_eq_text!( 1943 assert_eq_text!(
1944 dump.trim(),
1945 r###"[email protected] 1944 r###"[email protected]
1946 [email protected] 1945 [email protected]
1947 [email protected] 1946 [email protected]
@@ -1981,6 +1980,7 @@ fn test_no_space_after_semi_colon() {
1981 [email protected] 1980 [email protected]
1982 [email protected] "f" 1981 [email protected] "f"
1983 [email protected] ";""###, 1982 [email protected] ";""###,
1983 dump.trim()
1984 ); 1984 );
1985} 1985}
1986 1986