|
3 | 3 | //! This module uses a bit of static metadata to provide completions |
4 | 4 | //! for built-in attributes. |
5 | 5 |
|
6 | | -use std::mem; |
7 | | - |
8 | 6 | use once_cell::sync::Lazy; |
9 | 7 | use rustc_hash::{FxHashMap, FxHashSet}; |
10 | 8 | use syntax::{ast, AstNode, NodeOrToken, SyntaxKind, T}; |
@@ -272,27 +270,27 @@ const ATTRIBUTES: &[AttrCompletion] = &[ |
272 | 270 | fn parse_comma_sep_input(derive_input: ast::TokenTree) -> Option<FxHashSet<String>> { |
273 | 271 | let (l_paren, r_paren) = derive_input.l_paren_token().zip(derive_input.r_paren_token())?; |
274 | 272 | let mut input_derives = FxHashSet::default(); |
275 | | - let mut current_derive = String::new(); |
276 | | - for token in derive_input |
| 273 | + let mut tokens = derive_input |
277 | 274 | .syntax() |
278 | 275 | .children_with_tokens() |
279 | 276 | .filter_map(NodeOrToken::into_token) |
280 | 277 | .skip_while(|token| token != &l_paren) |
281 | 278 | .skip(1) |
282 | 279 | .take_while(|token| token != &r_paren) |
283 | | - { |
284 | | - if token.kind() == T![,] { |
285 | | - if !current_derive.is_empty() { |
286 | | - input_derives.insert(mem::take(&mut current_derive)); |
287 | | - } |
288 | | - } else { |
289 | | - current_derive.push_str(token.text().trim()); |
| 280 | + .peekable(); |
| 281 | + let mut input = String::new(); |
| 282 | + while tokens.peek().is_some() { |
| 283 | + for token in tokens.by_ref().take_while(|t| t.kind() != T![,]) { |
| 284 | + input.push_str(token.text()); |
290 | 285 | } |
291 | | - } |
292 | 286 |
|
293 | | - if !current_derive.is_empty() { |
294 | | - input_derives.insert(current_derive); |
| 287 | + if !input.is_empty() { |
| 288 | + input_derives.insert(input.trim().to_owned()); |
| 289 | + } |
| 290 | + |
| 291 | + input.clear(); |
295 | 292 | } |
| 293 | + |
296 | 294 | Some(input_derives) |
297 | 295 | } |
298 | 296 |
|
|
0 commit comments