From fcce07d2d1b07cf4578af65b00a243e743a67f05 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Thu, 30 Jul 2020 20:16:04 +0200 Subject: Finalize attribute grammar --- crates/ra_assists/src/handlers/add_custom_impl.rs | 4 +-- crates/ra_hir_def/src/attr.rs | 19 +++++----- crates/ra_ide/src/completion/complete_attribute.rs | 10 +++--- crates/ra_syntax/src/ast/generated/nodes.rs | 41 ++-------------------- crates/ra_syntax/src/ast/node_ext.rs | 28 ++++++--------- xtask/src/codegen/rust.ungram | 5 +-- 6 files changed, 28 insertions(+), 79 deletions(-) diff --git a/crates/ra_assists/src/handlers/add_custom_impl.rs b/crates/ra_assists/src/handlers/add_custom_impl.rs index acb07e36a..b67438b6b 100644 --- a/crates/ra_assists/src/handlers/add_custom_impl.rs +++ b/crates/ra_assists/src/handlers/add_custom_impl.rs @@ -29,8 +29,8 @@ use crate::{ // } // ``` pub(crate) fn add_custom_impl(acc: &mut Assists, ctx: &AssistContext) -> Option<()> { - let input = ctx.find_node_at_offset::()?; - let attr = input.syntax().parent().and_then(ast::Attr::cast)?; + let attr = ctx.find_node_at_offset::()?; + let input = attr.token_tree()?; let attr_name = attr .syntax() diff --git a/crates/ra_hir_def/src/attr.rs b/crates/ra_hir_def/src/attr.rs index 70ccd4305..050832ce0 100644 --- a/crates/ra_hir_def/src/attr.rs +++ b/crates/ra_hir_def/src/attr.rs @@ -151,18 +151,15 @@ pub enum AttrInput { impl Attr { fn from_src(ast: ast::Attr, hygiene: &Hygiene) -> Option { let path = ModPath::from_src(ast.path()?, hygiene)?; - let input = match ast.input() { - None => None, - Some(ast::AttrInput::Literal(lit)) => { - // FIXME: escape? raw string? - let value = lit.syntax().first_token()?.text().trim_matches('"').into(); - Some(AttrInput::Literal(value)) - } - Some(ast::AttrInput::TokenTree(tt)) => { - Some(AttrInput::TokenTree(ast_to_token_tree(&tt)?.0)) - } + let input = if let Some(lit) = ast.literal() { + // FIXME: escape? raw string? + let value = lit.syntax().first_token()?.text().trim_matches('"').into(); + Some(AttrInput::Literal(value)) + } else if let Some(tt) = ast.token_tree() { + Some(AttrInput::TokenTree(ast_to_token_tree(&tt)?.0)) + } else { + None }; - Some(Attr { path, input }) } } diff --git a/crates/ra_ide/src/completion/complete_attribute.rs b/crates/ra_ide/src/completion/complete_attribute.rs index 109c5e9a8..2faaae974 100644 --- a/crates/ra_ide/src/completion/complete_attribute.rs +++ b/crates/ra_ide/src/completion/complete_attribute.rs @@ -13,20 +13,18 @@ use crate::completion::{ pub(super) fn complete_attribute(acc: &mut Completions, ctx: &CompletionContext) -> Option<()> { let attribute = ctx.attribute_under_caret.as_ref()?; - match (attribute.path(), attribute.input()) { - (Some(path), Some(ast::AttrInput::TokenTree(token_tree))) - if path.to_string() == "derive" => - { + match (attribute.path(), attribute.token_tree()) { + (Some(path), Some(token_tree)) if path.to_string() == "derive" => { complete_derive(acc, ctx, token_tree) } - (Some(path), Some(ast::AttrInput::TokenTree(token_tree))) + (Some(path), Some(token_tree)) if ["allow", "warn", "deny", "forbid"] .iter() .any(|lint_level| lint_level == &path.to_string()) => { complete_lint(acc, ctx, token_tree) } - (_, Some(ast::AttrInput::TokenTree(_token_tree))) => {} + (_, Some(_token_tree)) => {} _ => complete_attribute_start(acc, ctx, attribute), } Some(()) diff --git a/crates/ra_syntax/src/ast/generated/nodes.rs b/crates/ra_syntax/src/ast/generated/nodes.rs index e898c9181..05f75871d 100644 --- a/crates/ra_syntax/src/ast/generated/nodes.rs +++ b/crates/ra_syntax/src/ast/generated/nodes.rs @@ -24,7 +24,8 @@ impl Attr { pub fn l_brack_token(&self) -> Option { support::token(&self.syntax, T!['[']) } pub fn path(&self) -> Option { support::child(&self.syntax) } pub fn eq_token(&self) -> Option { support::token(&self.syntax, T![=]) } - pub fn input(&self) -> Option { support::child(&self.syntax) } + pub fn literal(&self) -> Option { support::child(&self.syntax) } + pub fn token_tree(&self) -> Option { support::child(&self.syntax) } pub fn r_brack_token(&self) -> Option { support::token(&self.syntax, T![']']) } } #[derive(Debug, Clone, PartialEq, Eq, Hash)] @@ -1378,11 +1379,6 @@ pub enum GenericParam { } impl ast::AttrsOwner for GenericParam {} #[derive(Debug, Clone, PartialEq, Eq, Hash)] -pub enum AttrInput { - Literal(Literal), - TokenTree(TokenTree), -} -#[derive(Debug, Clone, PartialEq, Eq, Hash)] pub enum Stmt { LetStmt(LetStmt), ExprStmt(ExprStmt), @@ -3342,34 +3338,6 @@ impl AstNode for GenericParam { } } } -impl From for AttrInput { - fn from(node: Literal) -> AttrInput { AttrInput::Literal(node) } -} -impl From for AttrInput { - fn from(node: TokenTree) -> AttrInput { AttrInput::TokenTree(node) } -} -impl AstNode for AttrInput { - fn can_cast(kind: SyntaxKind) -> bool { - match kind { - LITERAL | TOKEN_TREE => true, - _ => false, - } - } - fn cast(syntax: SyntaxNode) -> Option { - let res = match syntax.kind() { - LITERAL => AttrInput::Literal(Literal { syntax }), - TOKEN_TREE => AttrInput::TokenTree(TokenTree { syntax }), - _ => return None, - }; - Some(res) - } - fn syntax(&self) -> &SyntaxNode { - match self { - AttrInput::Literal(it) => &it.syntax, - AttrInput::TokenTree(it) => &it.syntax, - } - } -} impl From for Stmt { fn from(node: LetStmt) -> Stmt { Stmt::LetStmt(node) } } @@ -3471,11 +3439,6 @@ impl std::fmt::Display for GenericParam { std::fmt::Display::fmt(self.syntax(), f) } } -impl std::fmt::Display for AttrInput { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - std::fmt::Display::fmt(self.syntax(), f) - } -} impl std::fmt::Display for Stmt { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { std::fmt::Display::fmt(self.syntax(), f) diff --git a/crates/ra_syntax/src/ast/node_ext.rs b/crates/ra_syntax/src/ast/node_ext.rs index d2ee9586d..bba7310ad 100644 --- a/crates/ra_syntax/src/ast/node_ext.rs +++ b/crates/ra_syntax/src/ast/node_ext.rs @@ -7,7 +7,7 @@ use itertools::Itertools; use ra_parser::SyntaxKind; use crate::{ - ast::{self, support, AstNode, AttrInput, NameOwner, SyntaxNode}, + ast::{self, support, AstNode, NameOwner, SyntaxNode}, SmolStr, SyntaxElement, SyntaxToken, T, }; @@ -39,29 +39,23 @@ pub enum AttrKind { impl ast::Attr { pub fn as_simple_atom(&self) -> Option { - match self.input() { - None => self.simple_name(), - Some(_) => None, + if self.eq_token().is_some() || self.token_tree().is_some() { + return None; } + self.simple_name() } pub fn as_simple_call(&self) -> Option<(SmolStr, ast::TokenTree)> { - match self.input() { - Some(AttrInput::TokenTree(tt)) => Some((self.simple_name()?, tt)), - _ => None, - } + let tt = self.token_tree()?; + Some((self.simple_name()?, tt)) } pub fn as_simple_key_value(&self) -> Option<(SmolStr, SmolStr)> { - match self.input() { - Some(AttrInput::Literal(lit)) => { - let key = self.simple_name()?; - // FIXME: escape? raw string? - let value = lit.syntax().first_token()?.text().trim_matches('"').into(); - Some((key, value)) - } - _ => None, - } + let lit = self.literal()?; + let key = self.simple_name()?; + // FIXME: escape? raw string? + let value = lit.syntax().first_token()?.text().trim_matches('"').into(); + Some((key, value)) } pub fn simple_name(&self) -> Option { diff --git a/xtask/src/codegen/rust.ungram b/xtask/src/codegen/rust.ungram index a97cc80e9..42ef2fb82 100644 --- a/xtask/src/codegen/rust.ungram +++ b/xtask/src/codegen/rust.ungram @@ -182,10 +182,7 @@ Visibility = ')')? Attr = - '#' '!'? '[' Path ('=' input:AttrInput)? ']' - -AttrInput = - Literal | TokenTree + '#' '!'? '[' Path ('=' Literal | TokenTree)? ']' ParenType = '(' TypeRef ')' -- cgit v1.2.3 From fbe60a2e284035d16c2a1ee743ee88db418689aa Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Thu, 30 Jul 2020 20:27:39 +0200 Subject: simplify --- crates/ra_syntax/src/ast/generated/nodes.rs | 36 ++++++++++++++--------------- xtask/src/codegen/rust.ungram | 5 ++-- 2 files changed, 20 insertions(+), 21 deletions(-) diff --git a/crates/ra_syntax/src/ast/generated/nodes.rs b/crates/ra_syntax/src/ast/generated/nodes.rs index 05f75871d..c20ff53bf 100644 --- a/crates/ra_syntax/src/ast/generated/nodes.rs +++ b/crates/ra_syntax/src/ast/generated/nodes.rs @@ -322,9 +322,9 @@ pub struct ParamList { } impl ParamList { pub fn l_paren_token(&self) -> Option { support::token(&self.syntax, T!['(']) } - pub fn params(&self) -> AstChildren { support::children(&self.syntax) } pub fn self_param(&self) -> Option { support::child(&self.syntax) } pub fn comma_token(&self) -> Option { support::token(&self.syntax, T![,]) } + pub fn params(&self) -> AstChildren { support::children(&self.syntax) } pub fn r_paren_token(&self) -> Option { support::token(&self.syntax, T![')']) } } #[derive(Debug, Clone, PartialEq, Eq, Hash)] @@ -357,17 +357,6 @@ impl BlockExpr { pub fn r_curly_token(&self) -> Option { support::token(&self.syntax, T!['}']) } } #[derive(Debug, Clone, PartialEq, Eq, Hash)] -pub struct Param { - pub(crate) syntax: SyntaxNode, -} -impl ast::AttrsOwner for Param {} -impl ast::TypeAscriptionOwner for Param {} -impl Param { - pub fn pat(&self) -> Option { support::child(&self.syntax) } - pub fn colon_token(&self) -> Option { support::token(&self.syntax, T![:]) } - pub fn dotdotdot_token(&self) -> Option { support::token(&self.syntax, T![...]) } -} -#[derive(Debug, Clone, PartialEq, Eq, Hash)] pub struct SelfParam { pub(crate) syntax: SyntaxNode, } @@ -383,6 +372,17 @@ impl SelfParam { pub fn colon_token(&self) -> Option { support::token(&self.syntax, T![:]) } } #[derive(Debug, Clone, PartialEq, Eq, Hash)] +pub struct Param { + pub(crate) syntax: SyntaxNode, +} +impl ast::AttrsOwner for Param {} +impl ast::TypeAscriptionOwner for Param {} +impl Param { + pub fn pat(&self) -> Option { support::child(&self.syntax) } + pub fn colon_token(&self) -> Option { support::token(&self.syntax, T![:]) } + pub fn dotdotdot_token(&self) -> Option { support::token(&self.syntax, T![...]) } +} +#[derive(Debug, Clone, PartialEq, Eq, Hash)] pub struct TypeBoundList { pub(crate) syntax: SyntaxNode, } @@ -1724,8 +1724,8 @@ impl AstNode for BlockExpr { } fn syntax(&self) -> &SyntaxNode { &self.syntax } } -impl AstNode for Param { - fn can_cast(kind: SyntaxKind) -> bool { kind == PARAM } +impl AstNode for SelfParam { + fn can_cast(kind: SyntaxKind) -> bool { kind == SELF_PARAM } fn cast(syntax: SyntaxNode) -> Option { if Self::can_cast(syntax.kind()) { Some(Self { syntax }) @@ -1735,8 +1735,8 @@ impl AstNode for Param { } fn syntax(&self) -> &SyntaxNode { &self.syntax } } -impl AstNode for SelfParam { - fn can_cast(kind: SyntaxKind) -> bool { kind == SELF_PARAM } +impl AstNode for Param { + fn can_cast(kind: SyntaxKind) -> bool { kind == PARAM } fn cast(syntax: SyntaxNode) -> Option { if Self::can_cast(syntax.kind()) { Some(Self { syntax }) @@ -3599,12 +3599,12 @@ impl std::fmt::Display for BlockExpr { std::fmt::Display::fmt(self.syntax(), f) } } -impl std::fmt::Display for Param { +impl std::fmt::Display for SelfParam { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { std::fmt::Display::fmt(self.syntax(), f) } } -impl std::fmt::Display for SelfParam { +impl std::fmt::Display for Param { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { std::fmt::Display::fmt(self.syntax(), f) } diff --git a/xtask/src/codegen/rust.ungram b/xtask/src/codegen/rust.ungram index 42ef2fb82..8c4f953b0 100644 --- a/xtask/src/codegen/rust.ungram +++ b/xtask/src/codegen/rust.ungram @@ -54,9 +54,8 @@ Abi = ParamList = '('( - (Param (',' Param)* ','?)? - | SelfParam ','? - | SelfParam ',' (Param (',' Param)* ','?) + SelfParam + | (SelfParam ',')? (Param (',' Param)* ','?)? )')' SelfParam = -- cgit v1.2.3