]> git.lizzy.rs Git - rust.git/blob - crates/ra_hir/src/code_model.rs
d20e9de632c45898480a0184db24b936aae21283
[rust.git] / crates / ra_hir / src / code_model.rs
1 //! FIXME: write short doc here
2 use std::sync::Arc;
3
4 use either::Either;
5 use hir_def::{
6     adt::VariantData,
7     builtin_type::BuiltinType,
8     docs::Documentation,
9     expr::{BindingAnnotation, Pat, PatId},
10     nameres::ModuleSource,
11     per_ns::PerNs,
12     resolver::HasResolver,
13     type_ref::{Mutability, TypeRef},
14     AdtId, ConstId, DefWithBodyId, EnumId, FunctionId, HasModule, ImplId, LocalEnumVariantId,
15     LocalImportId, LocalModuleId, LocalStructFieldId, Lookup, ModuleId, StaticId, StructId,
16     TraitId, TypeAliasId, TypeParamId, UnionId,
17 };
18 use hir_expand::{
19     diagnostics::DiagnosticSink,
20     name::{name, AsName},
21     MacroDefId,
22 };
23 use hir_ty::{
24     autoderef, display::HirFormatter, expr::ExprValidator, ApplicationTy, Canonical, InEnvironment,
25     TraitEnvironment, Ty, TyDefId, TypeCtor, TypeWalk,
26 };
27 use ra_db::{CrateId, Edition, FileId};
28 use ra_syntax::ast;
29
30 use crate::{
31     db::{DefDatabase, HirDatabase},
32     CallableDef, HirDisplay, InFile, Name,
33 };
34
35 /// hir::Crate describes a single crate. It's the main interface with which
36 /// a crate's dependencies interact. Mostly, it should be just a proxy for the
37 /// root module.
38 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
39 pub struct Crate {
40     pub(crate) id: CrateId,
41 }
42
43 #[derive(Debug)]
44 pub struct CrateDependency {
45     pub krate: Crate,
46     pub name: Name,
47 }
48
49 impl Crate {
50     pub fn dependencies(self, db: &impl DefDatabase) -> Vec<CrateDependency> {
51         db.crate_graph()
52             .dependencies(self.id)
53             .map(|dep| {
54                 let krate = Crate { id: dep.crate_id() };
55                 let name = dep.as_name();
56                 CrateDependency { krate, name }
57             })
58             .collect()
59     }
60
61     // FIXME: add `transitive_reverse_dependencies`.
62     pub fn reverse_dependencies(self, db: &impl DefDatabase) -> Vec<Crate> {
63         let crate_graph = db.crate_graph();
64         crate_graph
65             .iter()
66             .filter(|&krate| crate_graph.dependencies(krate).any(|it| it.crate_id == self.id))
67             .map(|id| Crate { id })
68             .collect()
69     }
70
71     pub fn root_module(self, db: &impl DefDatabase) -> Option<Module> {
72         let module_id = db.crate_def_map(self.id).root;
73         Some(Module::new(self, module_id))
74     }
75
76     pub fn root_file(self, db: &impl DefDatabase) -> FileId {
77         db.crate_graph().crate_root(self.id)
78     }
79
80     pub fn edition(self, db: &impl DefDatabase) -> Edition {
81         let crate_graph = db.crate_graph();
82         crate_graph.edition(self.id)
83     }
84
85     pub fn all(db: &impl DefDatabase) -> Vec<Crate> {
86         db.crate_graph().iter().map(|id| Crate { id }).collect()
87     }
88 }
89
90 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
91 pub struct Module {
92     pub(crate) id: ModuleId,
93 }
94
95 /// The defs which can be visible in the module.
96 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
97 pub enum ModuleDef {
98     Module(Module),
99     Function(Function),
100     Adt(Adt),
101     // Can't be directly declared, but can be imported.
102     EnumVariant(EnumVariant),
103     Const(Const),
104     Static(Static),
105     Trait(Trait),
106     TypeAlias(TypeAlias),
107     BuiltinType(BuiltinType),
108 }
109 impl_froms!(
110     ModuleDef: Module,
111     Function,
112     Adt(Struct, Enum, Union),
113     EnumVariant,
114     Const,
115     Static,
116     Trait,
117     TypeAlias,
118     BuiltinType
119 );
120
121 pub use hir_def::attr::Attrs;
122
123 impl Module {
124     pub(crate) fn new(krate: Crate, crate_module_id: LocalModuleId) -> Module {
125         Module { id: ModuleId { krate: krate.id, local_id: crate_module_id } }
126     }
127
128     /// Name of this module.
129     pub fn name(self, db: &impl DefDatabase) -> Option<Name> {
130         let def_map = db.crate_def_map(self.id.krate);
131         let parent = def_map[self.id.local_id].parent?;
132         def_map[parent].children.iter().find_map(|(name, module_id)| {
133             if *module_id == self.id.local_id {
134                 Some(name.clone())
135             } else {
136                 None
137             }
138         })
139     }
140
141     /// Returns the crate this module is part of.
142     pub fn krate(self) -> Crate {
143         Crate { id: self.id.krate }
144     }
145
146     /// Topmost parent of this module. Every module has a `crate_root`, but some
147     /// might be missing `krate`. This can happen if a module's file is not included
148     /// in the module tree of any target in `Cargo.toml`.
149     pub fn crate_root(self, db: &impl DefDatabase) -> Module {
150         let def_map = db.crate_def_map(self.id.krate);
151         self.with_module_id(def_map.root)
152     }
153
154     /// Iterates over all child modules.
155     pub fn children(self, db: &impl DefDatabase) -> impl Iterator<Item = Module> {
156         let def_map = db.crate_def_map(self.id.krate);
157         let children = def_map[self.id.local_id]
158             .children
159             .iter()
160             .map(|(_, module_id)| self.with_module_id(*module_id))
161             .collect::<Vec<_>>();
162         children.into_iter()
163     }
164
165     /// Finds a parent module.
166     pub fn parent(self, db: &impl DefDatabase) -> Option<Module> {
167         let def_map = db.crate_def_map(self.id.krate);
168         let parent_id = def_map[self.id.local_id].parent?;
169         Some(self.with_module_id(parent_id))
170     }
171
172     pub fn path_to_root(self, db: &impl HirDatabase) -> Vec<Module> {
173         let mut res = vec![self];
174         let mut curr = self;
175         while let Some(next) = curr.parent(db) {
176             res.push(next);
177             curr = next
178         }
179         res
180     }
181
182     /// Returns a `ModuleScope`: a set of items, visible in this module.
183     pub fn scope(self, db: &impl HirDatabase) -> Vec<(Name, ScopeDef, Option<Import>)> {
184         db.crate_def_map(self.id.krate)[self.id.local_id]
185             .scope
186             .entries()
187             .map(|(name, res)| {
188                 (name.clone(), res.def.into(), res.import.map(|id| Import { parent: self, id }))
189             })
190             .collect()
191     }
192
193     pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) {
194         db.crate_def_map(self.id.krate).add_diagnostics(db, self.id.local_id, sink);
195         for decl in self.declarations(db) {
196             match decl {
197                 crate::ModuleDef::Function(f) => f.diagnostics(db, sink),
198                 crate::ModuleDef::Module(m) => {
199                     // Only add diagnostics from inline modules
200                     if let ModuleSource::Module(_) = m.definition_source(db).value {
201                         m.diagnostics(db, sink)
202                     }
203                 }
204                 _ => (),
205             }
206         }
207
208         for impl_block in self.impl_blocks(db) {
209             for item in impl_block.items(db) {
210                 if let AssocItem::Function(f) = item {
211                     f.diagnostics(db, sink);
212                 }
213             }
214         }
215     }
216
217     pub fn declarations(self, db: &impl DefDatabase) -> Vec<ModuleDef> {
218         let def_map = db.crate_def_map(self.id.krate);
219         def_map[self.id.local_id].scope.declarations().map(ModuleDef::from).collect()
220     }
221
222     pub fn impl_blocks(self, db: &impl DefDatabase) -> Vec<ImplBlock> {
223         let def_map = db.crate_def_map(self.id.krate);
224         def_map[self.id.local_id].impls.iter().copied().map(ImplBlock::from).collect()
225     }
226
227     pub(crate) fn with_module_id(self, module_id: LocalModuleId) -> Module {
228         Module::new(self.krate(), module_id)
229     }
230 }
231
232 pub struct Import {
233     pub(crate) parent: Module,
234     pub(crate) id: LocalImportId,
235 }
236
237 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
238 pub struct StructField {
239     pub(crate) parent: VariantDef,
240     pub(crate) id: LocalStructFieldId,
241 }
242
243 #[derive(Debug, PartialEq, Eq)]
244 pub enum FieldSource {
245     Named(ast::RecordFieldDef),
246     Pos(ast::TupleFieldDef),
247 }
248
249 impl StructField {
250     pub fn name(&self, db: &impl HirDatabase) -> Name {
251         self.parent.variant_data(db).fields()[self.id].name.clone()
252     }
253
254     pub fn ty(&self, db: &impl HirDatabase) -> Type {
255         let var_id = self.parent.into();
256         let ty = db.field_types(var_id)[self.id].clone();
257         Type::new(db, self.parent.module(db).id.krate.into(), var_id, ty)
258     }
259
260     pub fn parent_def(&self, _db: &impl HirDatabase) -> VariantDef {
261         self.parent
262     }
263 }
264
265 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
266 pub struct Struct {
267     pub(crate) id: StructId,
268 }
269
270 impl Struct {
271     pub fn module(self, db: &impl DefDatabase) -> Module {
272         Module { id: self.id.lookup(db).container.module(db) }
273     }
274
275     pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
276         Some(self.module(db).krate())
277     }
278
279     pub fn name(self, db: &impl DefDatabase) -> Name {
280         db.struct_data(self.id.into()).name.clone()
281     }
282
283     pub fn fields(self, db: &impl HirDatabase) -> Vec<StructField> {
284         db.struct_data(self.id.into())
285             .variant_data
286             .fields()
287             .iter()
288             .map(|(id, _)| StructField { parent: self.into(), id })
289             .collect()
290     }
291
292     pub fn ty(self, db: &impl HirDatabase) -> Type {
293         Type::from_def(db, self.id.lookup(db).container.module(db).krate, self.id)
294     }
295
296     fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> {
297         db.struct_data(self.id.into()).variant_data.clone()
298     }
299 }
300
301 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
302 pub struct Union {
303     pub(crate) id: UnionId,
304 }
305
306 impl Union {
307     pub fn name(self, db: &impl DefDatabase) -> Name {
308         db.union_data(self.id).name.clone()
309     }
310
311     pub fn module(self, db: &impl DefDatabase) -> Module {
312         Module { id: self.id.lookup(db).container.module(db) }
313     }
314
315     pub fn ty(self, db: &impl HirDatabase) -> Type {
316         Type::from_def(db, self.id.lookup(db).container.module(db).krate, self.id)
317     }
318
319     pub fn fields(self, db: &impl HirDatabase) -> Vec<StructField> {
320         db.union_data(self.id)
321             .variant_data
322             .fields()
323             .iter()
324             .map(|(id, _)| StructField { parent: self.into(), id })
325             .collect()
326     }
327
328     fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> {
329         db.union_data(self.id).variant_data.clone()
330     }
331 }
332
333 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
334 pub struct Enum {
335     pub(crate) id: EnumId,
336 }
337
338 impl Enum {
339     pub fn module(self, db: &impl DefDatabase) -> Module {
340         Module { id: self.id.lookup(db).container.module(db) }
341     }
342
343     pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
344         Some(self.module(db).krate())
345     }
346
347     pub fn name(self, db: &impl DefDatabase) -> Name {
348         db.enum_data(self.id).name.clone()
349     }
350
351     pub fn variants(self, db: &impl DefDatabase) -> Vec<EnumVariant> {
352         db.enum_data(self.id)
353             .variants
354             .iter()
355             .map(|(id, _)| EnumVariant { parent: self, id })
356             .collect()
357     }
358
359     pub fn ty(self, db: &impl HirDatabase) -> Type {
360         Type::from_def(db, self.id.lookup(db).container.module(db).krate, self.id)
361     }
362 }
363
364 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
365 pub struct EnumVariant {
366     pub(crate) parent: Enum,
367     pub(crate) id: LocalEnumVariantId,
368 }
369
370 impl EnumVariant {
371     pub fn module(self, db: &impl HirDatabase) -> Module {
372         self.parent.module(db)
373     }
374     pub fn parent_enum(self, _db: &impl DefDatabase) -> Enum {
375         self.parent
376     }
377
378     pub fn name(self, db: &impl DefDatabase) -> Name {
379         db.enum_data(self.parent.id).variants[self.id].name.clone()
380     }
381
382     pub fn fields(self, db: &impl HirDatabase) -> Vec<StructField> {
383         self.variant_data(db)
384             .fields()
385             .iter()
386             .map(|(id, _)| StructField { parent: self.into(), id })
387             .collect()
388     }
389
390     pub(crate) fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> {
391         db.enum_data(self.parent.id).variants[self.id].variant_data.clone()
392     }
393 }
394
395 /// A Data Type
396 #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
397 pub enum Adt {
398     Struct(Struct),
399     Union(Union),
400     Enum(Enum),
401 }
402 impl_froms!(Adt: Struct, Union, Enum);
403
404 impl Adt {
405     pub fn has_non_default_type_params(self, db: &impl HirDatabase) -> bool {
406         let subst = db.generic_defaults(self.into());
407         subst.iter().any(|ty| ty == &Ty::Unknown)
408     }
409     pub fn ty(self, db: &impl HirDatabase) -> Type {
410         let id = AdtId::from(self);
411         Type::from_def(db, id.module(db).krate, id)
412     }
413
414     pub fn module(self, db: &impl DefDatabase) -> Module {
415         match self {
416             Adt::Struct(s) => s.module(db),
417             Adt::Union(s) => s.module(db),
418             Adt::Enum(e) => e.module(db),
419         }
420     }
421
422     pub fn krate(self, db: &impl HirDatabase) -> Option<Crate> {
423         Some(self.module(db).krate())
424     }
425 }
426
427 #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
428 pub enum VariantDef {
429     Struct(Struct),
430     Union(Union),
431     EnumVariant(EnumVariant),
432 }
433 impl_froms!(VariantDef: Struct, Union, EnumVariant);
434
435 impl VariantDef {
436     pub fn fields(self, db: &impl HirDatabase) -> Vec<StructField> {
437         match self {
438             VariantDef::Struct(it) => it.fields(db),
439             VariantDef::Union(it) => it.fields(db),
440             VariantDef::EnumVariant(it) => it.fields(db),
441         }
442     }
443
444     pub fn module(self, db: &impl HirDatabase) -> Module {
445         match self {
446             VariantDef::Struct(it) => it.module(db),
447             VariantDef::Union(it) => it.module(db),
448             VariantDef::EnumVariant(it) => it.module(db),
449         }
450     }
451
452     pub(crate) fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> {
453         match self {
454             VariantDef::Struct(it) => it.variant_data(db),
455             VariantDef::Union(it) => it.variant_data(db),
456             VariantDef::EnumVariant(it) => it.variant_data(db),
457         }
458     }
459 }
460
461 /// The defs which have a body.
462 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
463 pub enum DefWithBody {
464     Function(Function),
465     Static(Static),
466     Const(Const),
467 }
468
469 impl_froms!(DefWithBody: Function, Const, Static);
470
471 impl DefWithBody {
472     pub fn module(self, db: &impl HirDatabase) -> Module {
473         match self {
474             DefWithBody::Const(c) => c.module(db),
475             DefWithBody::Function(f) => f.module(db),
476             DefWithBody::Static(s) => s.module(db),
477         }
478     }
479 }
480
481 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
482 pub struct Function {
483     pub(crate) id: FunctionId,
484 }
485
486 impl Function {
487     pub fn module(self, db: &impl DefDatabase) -> Module {
488         self.id.lookup(db).module(db).into()
489     }
490
491     pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
492         Some(self.module(db).krate())
493     }
494
495     pub fn name(self, db: &impl HirDatabase) -> Name {
496         db.function_data(self.id).name.clone()
497     }
498
499     pub fn has_self_param(self, db: &impl HirDatabase) -> bool {
500         db.function_data(self.id).has_self_param
501     }
502
503     pub fn params(self, db: &impl HirDatabase) -> Vec<TypeRef> {
504         db.function_data(self.id).params.clone()
505     }
506
507     pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) {
508         let infer = db.infer(self.id.into());
509         infer.add_diagnostics(db, self.id, sink);
510         let mut validator = ExprValidator::new(self.id, infer, sink);
511         validator.validate_body(db);
512     }
513 }
514
515 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
516 pub struct Const {
517     pub(crate) id: ConstId,
518 }
519
520 impl Const {
521     pub fn module(self, db: &impl DefDatabase) -> Module {
522         Module { id: self.id.lookup(db).module(db) }
523     }
524
525     pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
526         Some(self.module(db).krate())
527     }
528
529     pub fn name(self, db: &impl HirDatabase) -> Option<Name> {
530         db.const_data(self.id).name.clone()
531     }
532 }
533
534 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
535 pub struct Static {
536     pub(crate) id: StaticId,
537 }
538
539 impl Static {
540     pub fn module(self, db: &impl DefDatabase) -> Module {
541         Module { id: self.id.lookup(db).module(db) }
542     }
543
544     pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
545         Some(self.module(db).krate())
546     }
547 }
548
549 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
550 pub struct Trait {
551     pub(crate) id: TraitId,
552 }
553
554 impl Trait {
555     pub fn module(self, db: &impl DefDatabase) -> Module {
556         Module { id: self.id.lookup(db).container }
557     }
558
559     pub fn name(self, db: &impl DefDatabase) -> Name {
560         db.trait_data(self.id).name.clone()
561     }
562
563     pub fn items(self, db: &impl DefDatabase) -> Vec<AssocItem> {
564         db.trait_data(self.id).items.iter().map(|(_name, it)| (*it).into()).collect()
565     }
566
567     pub fn is_auto(self, db: &impl DefDatabase) -> bool {
568         db.trait_data(self.id).auto
569     }
570 }
571
572 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
573 pub struct TypeAlias {
574     pub(crate) id: TypeAliasId,
575 }
576
577 impl TypeAlias {
578     pub fn has_non_default_type_params(self, db: &impl HirDatabase) -> bool {
579         let subst = db.generic_defaults(self.id.into());
580         subst.iter().any(|ty| ty == &Ty::Unknown)
581     }
582
583     pub fn module(self, db: &impl DefDatabase) -> Module {
584         Module { id: self.id.lookup(db).module(db) }
585     }
586
587     pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
588         Some(self.module(db).krate())
589     }
590
591     pub fn type_ref(self, db: &impl DefDatabase) -> Option<TypeRef> {
592         db.type_alias_data(self.id).type_ref.clone()
593     }
594
595     pub fn ty(self, db: &impl HirDatabase) -> Type {
596         Type::from_def(db, self.id.lookup(db).module(db).krate, self.id)
597     }
598
599     pub fn name(self, db: &impl DefDatabase) -> Name {
600         db.type_alias_data(self.id).name.clone()
601     }
602 }
603
604 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
605 pub struct MacroDef {
606     pub(crate) id: MacroDefId,
607 }
608
609 #[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
610 pub enum AssocItem {
611     Function(Function),
612     Const(Const),
613     TypeAlias(TypeAlias),
614 }
615 // FIXME: not every function, ... is actually an assoc item. maybe we should make
616 // sure that you can only turn actual assoc items into AssocItems. This would
617 // require not implementing From, and instead having some checked way of
618 // casting them, and somehow making the constructors private, which would be annoying.
619 impl_froms!(AssocItem: Function, Const, TypeAlias);
620
621 impl AssocItem {
622     pub fn module(self, db: &impl DefDatabase) -> Module {
623         match self {
624             AssocItem::Function(f) => f.module(db),
625             AssocItem::Const(c) => c.module(db),
626             AssocItem::TypeAlias(t) => t.module(db),
627         }
628     }
629 }
630
631 #[derive(Clone, Copy, PartialEq, Eq, Debug, Hash)]
632 pub enum GenericDef {
633     Function(Function),
634     Adt(Adt),
635     Trait(Trait),
636     TypeAlias(TypeAlias),
637     ImplBlock(ImplBlock),
638     // enum variants cannot have generics themselves, but their parent enums
639     // can, and this makes some code easier to write
640     EnumVariant(EnumVariant),
641     // consts can have type parameters from their parents (i.e. associated consts of traits)
642     Const(Const),
643 }
644 impl_froms!(
645     GenericDef: Function,
646     Adt(Struct, Enum, Union),
647     Trait,
648     TypeAlias,
649     ImplBlock,
650     EnumVariant,
651     Const
652 );
653
654 #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
655 pub struct Local {
656     pub(crate) parent: DefWithBody,
657     pub(crate) pat_id: PatId,
658 }
659
660 impl Local {
661     pub fn name(self, db: &impl HirDatabase) -> Option<Name> {
662         let body = db.body(self.parent.into());
663         match &body[self.pat_id] {
664             Pat::Bind { name, .. } => Some(name.clone()),
665             _ => None,
666         }
667     }
668
669     pub fn is_self(self, db: &impl HirDatabase) -> bool {
670         self.name(db) == Some(name![self])
671     }
672
673     pub fn is_mut(self, db: &impl HirDatabase) -> bool {
674         let body = db.body(self.parent.into());
675         match &body[self.pat_id] {
676             Pat::Bind { mode, .. } => match mode {
677                 BindingAnnotation::Mutable | BindingAnnotation::RefMut => true,
678                 _ => false,
679             },
680             _ => false,
681         }
682     }
683
684     pub fn parent(self, _db: &impl HirDatabase) -> DefWithBody {
685         self.parent
686     }
687
688     pub fn module(self, db: &impl HirDatabase) -> Module {
689         self.parent.module(db)
690     }
691
692     pub fn ty(self, db: &impl HirDatabase) -> Type {
693         let def = DefWithBodyId::from(self.parent);
694         let infer = db.infer(def);
695         let ty = infer[self.pat_id].clone();
696         let resolver = def.resolver(db);
697         let krate = def.module(db).krate;
698         let environment = TraitEnvironment::lower(db, &resolver);
699         Type { krate, ty: InEnvironment { value: ty, environment } }
700     }
701
702     pub fn source(self, db: &impl HirDatabase) -> InFile<Either<ast::BindPat, ast::SelfParam>> {
703         let (_body, source_map) = db.body_with_source_map(self.parent.into());
704         let src = source_map.pat_syntax(self.pat_id).unwrap(); // Hmm...
705         let root = src.file_syntax(db);
706         src.map(|ast| {
707             ast.map_left(|it| it.cast().unwrap().to_node(&root)).map_right(|it| it.to_node(&root))
708         })
709     }
710 }
711
712 #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
713 pub struct TypeParam {
714     pub(crate) id: TypeParamId,
715 }
716
717 impl TypeParam {
718     pub fn name(self, db: &impl HirDatabase) -> Name {
719         let params = db.generic_params(self.id.parent);
720         params.types[self.id.local_id].name.clone()
721     }
722
723     pub fn module(self, db: &impl HirDatabase) -> Module {
724         self.id.parent.module(db).into()
725     }
726 }
727
728 #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
729 pub struct ImplBlock {
730     pub(crate) id: ImplId,
731 }
732
733 impl ImplBlock {
734     pub fn all_in_crate(db: &impl HirDatabase, krate: Crate) -> Vec<ImplBlock> {
735         let impls = db.impls_in_crate(krate.id);
736         impls.all_impls().map(Self::from).collect()
737     }
738     pub fn for_trait(db: &impl HirDatabase, krate: Crate, trait_: Trait) -> Vec<ImplBlock> {
739         let impls = db.impls_in_crate(krate.id);
740         impls.lookup_impl_blocks_for_trait(trait_.id).map(Self::from).collect()
741     }
742
743     pub fn target_trait(&self, db: &impl DefDatabase) -> Option<TypeRef> {
744         db.impl_data(self.id).target_trait.clone()
745     }
746
747     pub fn target_type(&self, db: &impl DefDatabase) -> TypeRef {
748         db.impl_data(self.id).target_type.clone()
749     }
750
751     pub fn target_ty(&self, db: &impl HirDatabase) -> Type {
752         let impl_data = db.impl_data(self.id);
753         let resolver = self.id.resolver(db);
754         let environment = TraitEnvironment::lower(db, &resolver);
755         let ty = Ty::from_hir(db, &resolver, &impl_data.target_type);
756         Type {
757             krate: self.id.lookup(db).container.krate,
758             ty: InEnvironment { value: ty, environment },
759         }
760     }
761
762     pub fn items(&self, db: &impl DefDatabase) -> Vec<AssocItem> {
763         db.impl_data(self.id).items.iter().map(|it| (*it).into()).collect()
764     }
765
766     pub fn is_negative(&self, db: &impl DefDatabase) -> bool {
767         db.impl_data(self.id).is_negative
768     }
769
770     pub fn module(&self, db: &impl DefDatabase) -> Module {
771         self.id.lookup(db).container.into()
772     }
773
774     pub fn krate(&self, db: &impl DefDatabase) -> Crate {
775         Crate { id: self.module(db).id.krate }
776     }
777 }
778
779 #[derive(Clone, PartialEq, Eq, Debug)]
780 pub struct Type {
781     pub(crate) krate: CrateId,
782     pub(crate) ty: InEnvironment<Ty>,
783 }
784
785 impl Type {
786     fn new(db: &impl HirDatabase, krate: CrateId, lexical_env: impl HasResolver, ty: Ty) -> Type {
787         let resolver = lexical_env.resolver(db);
788         let environment = TraitEnvironment::lower(db, &resolver);
789         Type { krate, ty: InEnvironment { value: ty, environment } }
790     }
791
792     fn from_def(
793         db: &impl HirDatabase,
794         krate: CrateId,
795         def: impl HasResolver + Into<TyDefId>,
796     ) -> Type {
797         let ty = db.ty(def.into());
798         Type::new(db, krate, def, ty)
799     }
800
801     pub fn is_bool(&self) -> bool {
802         match &self.ty.value {
803             Ty::Apply(a_ty) => match a_ty.ctor {
804                 TypeCtor::Bool => true,
805                 _ => false,
806             },
807             _ => false,
808         }
809     }
810
811     pub fn is_mutable_reference(&self) -> bool {
812         match &self.ty.value {
813             Ty::Apply(a_ty) => match a_ty.ctor {
814                 TypeCtor::Ref(Mutability::Mut) => true,
815                 _ => false,
816             },
817             _ => false,
818         }
819     }
820
821     pub fn is_unknown(&self) -> bool {
822         match &self.ty.value {
823             Ty::Unknown => true,
824             _ => false,
825         }
826     }
827
828     // FIXME: this method is broken, as it doesn't take closures into account.
829     pub fn as_callable(&self) -> Option<CallableDef> {
830         Some(self.ty.value.as_callable()?.0)
831     }
832
833     pub fn contains_unknown(&self) -> bool {
834         return go(&self.ty.value);
835
836         fn go(ty: &Ty) -> bool {
837             match ty {
838                 Ty::Unknown => true,
839                 Ty::Apply(a_ty) => a_ty.parameters.iter().any(go),
840                 _ => false,
841             }
842         }
843     }
844
845     pub fn fields(&self, db: &impl HirDatabase) -> Vec<(StructField, Type)> {
846         if let Ty::Apply(a_ty) = &self.ty.value {
847             match a_ty.ctor {
848                 TypeCtor::Adt(AdtId::StructId(s)) => {
849                     let var_def = s.into();
850                     return db
851                         .field_types(var_def)
852                         .iter()
853                         .map(|(local_id, ty)| {
854                             let def = StructField { parent: var_def.into(), id: local_id };
855                             let ty = ty.clone().subst(&a_ty.parameters);
856                             (def, self.derived(ty))
857                         })
858                         .collect();
859                 }
860                 _ => {}
861             }
862         };
863         Vec::new()
864     }
865
866     pub fn tuple_fields(&self, _db: &impl HirDatabase) -> Vec<Type> {
867         let mut res = Vec::new();
868         if let Ty::Apply(a_ty) = &self.ty.value {
869             match a_ty.ctor {
870                 TypeCtor::Tuple { .. } => {
871                     for ty in a_ty.parameters.iter() {
872                         let ty = ty.clone().subst(&a_ty.parameters);
873                         res.push(self.derived(ty));
874                     }
875                 }
876                 _ => {}
877             }
878         };
879         res
880     }
881
882     pub fn variant_fields(
883         &self,
884         db: &impl HirDatabase,
885         def: VariantDef,
886     ) -> Vec<(StructField, Type)> {
887         // FIXME: check that ty and def match
888         match &self.ty.value {
889             Ty::Apply(a_ty) => {
890                 let field_types = db.field_types(def.into());
891                 def.fields(db)
892                     .into_iter()
893                     .map(|it| {
894                         let ty = field_types[it.id].clone().subst(&a_ty.parameters);
895                         (it, self.derived(ty))
896                     })
897                     .collect()
898             }
899             _ => Vec::new(),
900         }
901     }
902
903     pub fn autoderef<'a>(&'a self, db: &'a impl HirDatabase) -> impl Iterator<Item = Type> + 'a {
904         // There should be no inference vars in types passed here
905         // FIXME check that?
906         let canonical = Canonical { value: self.ty.value.clone(), num_vars: 0 };
907         let environment = self.ty.environment.clone();
908         let ty = InEnvironment { value: canonical, environment: environment.clone() };
909         autoderef(db, Some(self.krate), ty)
910             .map(|canonical| canonical.value)
911             .map(move |ty| self.derived(ty))
912     }
913
914     // This would be nicer if it just returned an iterator, but that runs into
915     // lifetime problems, because we need to borrow temp `CrateImplBlocks`.
916     pub fn iterate_impl_items<T>(
917         self,
918         db: &impl HirDatabase,
919         krate: Crate,
920         mut callback: impl FnMut(AssocItem) -> Option<T>,
921     ) -> Option<T> {
922         for krate in self.ty.value.def_crates(db, krate.id)? {
923             let impls = db.impls_in_crate(krate);
924
925             for impl_block in impls.lookup_impl_blocks(&self.ty.value) {
926                 for &item in db.impl_data(impl_block).items.iter() {
927                     if let Some(result) = callback(item.into()) {
928                         return Some(result);
929                     }
930                 }
931             }
932         }
933         None
934     }
935
936     pub fn as_adt(&self) -> Option<Adt> {
937         let (adt, _subst) = self.ty.value.as_adt()?;
938         Some(adt.into())
939     }
940
941     // FIXME: provide required accessors such that it becomes implementable from outside.
942     pub fn is_equal_for_find_impls(&self, other: &Type) -> bool {
943         match (&self.ty.value, &other.ty.value) {
944             (Ty::Apply(a_original_ty), Ty::Apply(ApplicationTy { ctor, parameters })) => match ctor
945             {
946                 TypeCtor::Ref(..) => match parameters.as_single() {
947                     Ty::Apply(a_ty) => a_original_ty.ctor == a_ty.ctor,
948                     _ => false,
949                 },
950                 _ => a_original_ty.ctor == *ctor,
951             },
952             _ => false,
953         }
954     }
955
956     fn derived(&self, ty: Ty) -> Type {
957         Type {
958             krate: self.krate,
959             ty: InEnvironment { value: ty, environment: self.ty.environment.clone() },
960         }
961     }
962 }
963
964 impl HirDisplay for Type {
965     fn hir_fmt(&self, f: &mut HirFormatter<impl HirDatabase>) -> std::fmt::Result {
966         self.ty.value.hir_fmt(f)
967     }
968 }
969
970 /// For IDE only
971 pub enum ScopeDef {
972     ModuleDef(ModuleDef),
973     MacroDef(MacroDef),
974     GenericParam(TypeParam),
975     ImplSelfType(ImplBlock),
976     AdtSelfType(Adt),
977     Local(Local),
978     Unknown,
979 }
980
981 impl From<PerNs> for ScopeDef {
982     fn from(def: PerNs) -> Self {
983         def.take_types()
984             .or_else(|| def.take_values())
985             .map(|module_def_id| ScopeDef::ModuleDef(module_def_id.into()))
986             .or_else(|| {
987                 def.take_macros().map(|macro_def_id| ScopeDef::MacroDef(macro_def_id.into()))
988             })
989             .unwrap_or(ScopeDef::Unknown)
990     }
991 }
992
993 #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
994 pub enum AttrDef {
995     Module(Module),
996     StructField(StructField),
997     Adt(Adt),
998     Function(Function),
999     EnumVariant(EnumVariant),
1000     Static(Static),
1001     Const(Const),
1002     Trait(Trait),
1003     TypeAlias(TypeAlias),
1004     MacroDef(MacroDef),
1005 }
1006
1007 impl_froms!(
1008     AttrDef: Module,
1009     StructField,
1010     Adt(Struct, Enum, Union),
1011     EnumVariant,
1012     Static,
1013     Const,
1014     Function,
1015     Trait,
1016     TypeAlias,
1017     MacroDef
1018 );
1019
1020 pub trait HasAttrs {
1021     fn attrs(self, db: &impl DefDatabase) -> Attrs;
1022 }
1023
1024 impl<T: Into<AttrDef>> HasAttrs for T {
1025     fn attrs(self, db: &impl DefDatabase) -> Attrs {
1026         let def: AttrDef = self.into();
1027         db.attrs(def.into())
1028     }
1029 }
1030
1031 pub trait Docs {
1032     fn docs(&self, db: &impl HirDatabase) -> Option<Documentation>;
1033 }
1034 impl<T: Into<AttrDef> + Copy> Docs for T {
1035     fn docs(&self, db: &impl HirDatabase) -> Option<Documentation> {
1036         let def: AttrDef = (*self).into();
1037         db.documentation(def.into())
1038     }
1039 }