mirror of
				https://github.com/rust-lang/rust-analyzer.git
				synced 2025-10-31 12:04:43 +00:00 
			
		
		
		
	Improve SCIP symbols
In particular, the symbol generation before this change creates a lot
of symbols with the same name for different definitions. This change
makes progress on symbol uniqueness, but does not fix a couple cases
where it was unclear to me how to fix (see TODOs in `scip.rs`)
Behavior changes:
* `scip` command now reports symbol information omitted due to symbol
collisions. Iterating with this on a large codebase (Zed!) resulted in
the other improvements in this change.
* Generally fixes providing the path to nested definitions in
symbols. Instead of having special cases for a couple limited cases of
nesting, implements `Definition::enclosing_definition` and uses this
to walk definitions.
* Parameter variables are now treated like locals.
    - This fixes a bug where closure captures also received symbols
    scoped to the containing function.  To bring back parameter
    symbols I would want a way to filter these out, since they can
    cause symbol collisions.
    - Having symbols for them seems to be intentional in
    27e2eea54f, but no particular use is
    specified there. For the typical indexing purposes of SCIP I don't see
    why parameter symbols are useful or sensible, as function parameters
    are not referencable by anything but position. I can imagine they
    might be useful in representing diagnostics or something.
* Inherent impls are now represented as `impl#[SelfType]` - a type
named `impl` which takes a single type parameter.
* Trait impls are now represented as `impl#[SelfType][TraitType]` - a
type named `impl` which takes two type parameters.
* Associated types in traits and impls are now treated like types
instead of type parameters, and so are now suffixed with `#` instead
of wrapped with `[]`.  Treating them as type parameters seems to have
been intentional in 73d9c77f2a but it
doesn't make sense to me, so changing it.
* Static variables are now treated as terms instead of `Meta`, and so
receive `.` suffix instead of `:`.
* Attributes are now treated as `Meta` instead of `Macro`, and so
receive `:` suffix instead of `!`.
* `enclosing_symbol` is now provided for labels and generic params,
which are local symbols.
* Fixes a bug where presence of `'` causes a descriptor name to get
double wrapped in backticks, since both `fn new_descriptor` and
`scip::symbol::format_symbol` have logic for wrapping in
backticks. Solution is to simply delete the redundant logic.
* Deletes a couple tests in moniker.rs because the cases are
adequeately covered in scip.rs and the format for identifiers used in
moniker.rs is clunky with the new representation for trait impls
			
			
This commit is contained in:
		
							parent
							
								
									bfc223e857
								
							
						
					
					
						commit
						17c90f71bf
					
				
					 9 changed files with 520 additions and 268 deletions
				
			
		|  | @ -13,10 +13,10 @@ use either::Either; | |||
| use hir::{ | ||||
|     Adt, AsAssocItem, AsExternAssocItem, AssocItem, AttributeTemplate, BuiltinAttr, BuiltinType, | ||||
|     Const, Crate, DefWithBody, DeriveHelper, DocLinkDef, ExternAssocItem, ExternCrateDecl, Field, | ||||
|     Function, GenericParam, GenericSubstitution, HasVisibility, HirDisplay, Impl, InlineAsmOperand, | ||||
|     Label, Local, Macro, Module, ModuleDef, Name, PathResolution, Semantics, Static, | ||||
|     StaticLifetime, Struct, ToolModule, Trait, TraitAlias, TupleField, TypeAlias, Variant, | ||||
|     VariantDef, Visibility, | ||||
|     Function, GenericDef, GenericParam, GenericSubstitution, HasContainer, HasVisibility, | ||||
|     HirDisplay, Impl, InlineAsmOperand, ItemContainer, Label, Local, Macro, Module, ModuleDef, | ||||
|     Name, PathResolution, Semantics, Static, StaticLifetime, Struct, ToolModule, Trait, TraitAlias, | ||||
|     TupleField, TypeAlias, Variant, VariantDef, Visibility, | ||||
| }; | ||||
| use span::Edition; | ||||
| use stdx::{format_to, impl_from}; | ||||
|  | @ -98,8 +98,30 @@ impl Definition { | |||
| 
 | ||||
|     pub fn enclosing_definition(&self, db: &RootDatabase) -> Option<Definition> { | ||||
|         match self { | ||||
|             Definition::Macro(it) => Some(it.module(db).into()), | ||||
|             Definition::Module(it) => it.parent(db).map(Definition::Module), | ||||
|             Definition::Field(it) => Some(it.parent_def(db).into()), | ||||
|             Definition::Function(it) => it.container(db).try_into().ok(), | ||||
|             Definition::Adt(it) => Some(it.module(db).into()), | ||||
|             Definition::Const(it) => it.container(db).try_into().ok(), | ||||
|             Definition::Static(it) => it.container(db).try_into().ok(), | ||||
|             Definition::Trait(it) => it.container(db).try_into().ok(), | ||||
|             Definition::TraitAlias(it) => it.container(db).try_into().ok(), | ||||
|             Definition::TypeAlias(it) => it.container(db).try_into().ok(), | ||||
|             Definition::Variant(it) => Some(Adt::Enum(it.parent_enum(db)).into()), | ||||
|             Definition::SelfType(it) => Some(it.module(db).into()), | ||||
|             Definition::Local(it) => it.parent(db).try_into().ok(), | ||||
|             _ => None, | ||||
|             Definition::GenericParam(it) => Some(it.parent().into()), | ||||
|             Definition::Label(it) => it.parent(db).try_into().ok(), | ||||
|             Definition::ExternCrateDecl(it) => it.container(db).try_into().ok(), | ||||
|             Definition::DeriveHelper(it) => Some(it.derive().module(db).into()), | ||||
|             Definition::InlineAsmOperand(it) => it.parent(db).try_into().ok(), | ||||
|             Definition::BuiltinAttr(_) | ||||
|             | Definition::BuiltinType(_) | ||||
|             | Definition::BuiltinLifetime(_) | ||||
|             | Definition::TupleField(_) | ||||
|             | Definition::ToolModule(_) | ||||
|             | Definition::InlineAsmRegOrRegClass(_) => None, | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|  | @ -932,3 +954,29 @@ impl TryFrom<DefWithBody> for Definition { | |||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| impl TryFrom<ItemContainer> for Definition { | ||||
|     type Error = (); | ||||
|     fn try_from(container: ItemContainer) -> Result<Self, Self::Error> { | ||||
|         match container { | ||||
|             ItemContainer::Trait(it) => Ok(it.into()), | ||||
|             ItemContainer::Impl(it) => Ok(it.into()), | ||||
|             ItemContainer::Module(it) => Ok(it.into()), | ||||
|             ItemContainer::ExternBlock() | ItemContainer::Crate(_) => Err(()), | ||||
|         } | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| impl From<GenericDef> for Definition { | ||||
|     fn from(def: GenericDef) -> Self { | ||||
|         match def { | ||||
|             GenericDef::Function(it) => it.into(), | ||||
|             GenericDef::Adt(it) => it.into(), | ||||
|             GenericDef::Trait(it) => it.into(), | ||||
|             GenericDef::TraitAlias(it) => it.into(), | ||||
|             GenericDef::TypeAlias(it) => it.into(), | ||||
|             GenericDef::Impl(it) => it.into(), | ||||
|             GenericDef::Const(it) => it.into(), | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Michael Sloan
						Michael Sloan