From cb3767f28a2f9e443b816b17d5d07b6a1cff90ab Mon Sep 17 00:00:00 2001 From: Martin Asquino Date: Mon, 4 Nov 2019 10:33:10 -0300 Subject: HirDatabase stored attributes --- crates/ra_hir/src/code_model/attrs.rs | 92 +++++++++++++++++++++++++++++++++++ 1 file changed, 92 insertions(+) create mode 100644 crates/ra_hir/src/code_model/attrs.rs (limited to 'crates/ra_hir/src/code_model/attrs.rs') diff --git a/crates/ra_hir/src/code_model/attrs.rs b/crates/ra_hir/src/code_model/attrs.rs new file mode 100644 index 000000000..f7db36b66 --- /dev/null +++ b/crates/ra_hir/src/code_model/attrs.rs @@ -0,0 +1,92 @@ +//! FIXME: write short doc here + +use crate::{ + db::{AstDatabase, DefDatabase, HirDatabase}, + Adt, Const, Enum, EnumVariant, FieldSource, Function, HasSource, MacroDef, Module, Static, + Struct, StructField, Trait, TypeAlias, Union, +}; +use hir_def::attr::Attr; +use hir_expand::hygiene::Hygiene; +use ra_syntax::ast; +use std::sync::Arc; + +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] +pub enum AttrDef { + Module(Module), + StructField(StructField), + Adt(Adt), + Function(Function), + EnumVariant(EnumVariant), + Static(Static), + Const(Const), + Trait(Trait), + TypeAlias(TypeAlias), + MacroDef(MacroDef), +} + +impl_froms!( + AttrDef: Module, + StructField, + Adt(Struct, Enum, Union), + EnumVariant, + Static, + Const, + Function, + Trait, + TypeAlias, + MacroDef +); + +pub trait Attrs { + fn attrs(&self, db: &impl HirDatabase) -> Option>; +} + +pub(crate) fn attributes_query( + db: &(impl DefDatabase + AstDatabase), + def: AttrDef, +) -> Option> { + match def { + AttrDef::Module(it) => { + let src = it.declaration_source(db)?; + let hygiene = Hygiene::new(db, src.file_id); + Attr::from_attrs_owner(&src.ast, &hygiene) + } + AttrDef::StructField(it) => match it.source(db).ast { + FieldSource::Named(named) => { + let src = it.source(db); + let hygiene = Hygiene::new(db, src.file_id); + Attr::from_attrs_owner(&named, &hygiene) + } + FieldSource::Pos(..) => None, + }, + AttrDef::Adt(it) => match it { + Adt::Struct(it) => attrs_from_ast(it, db), + Adt::Enum(it) => attrs_from_ast(it, db), + Adt::Union(it) => attrs_from_ast(it, db), + }, + AttrDef::EnumVariant(it) => attrs_from_ast(it, db), + AttrDef::Static(it) => attrs_from_ast(it, db), + AttrDef::Const(it) => attrs_from_ast(it, db), + AttrDef::Function(it) => attrs_from_ast(it, db), + AttrDef::Trait(it) => attrs_from_ast(it, db), + AttrDef::TypeAlias(it) => attrs_from_ast(it, db), + AttrDef::MacroDef(it) => attrs_from_ast(it, db), + } +} + +fn attrs_from_ast(node: T, db: &D) -> Option> +where + T: HasSource, + T::Ast: ast::AttrsOwner, + D: DefDatabase + AstDatabase, +{ + let src = node.source(db); + let hygiene = Hygiene::new(db, src.file_id); + Attr::from_attrs_owner(&src.ast, &hygiene) +} + +impl + Copy> Attrs for T { + fn attrs(&self, db: &impl HirDatabase) -> Option> { + db.attrs((*self).into()) + } +} -- cgit v1.2.3