Skip to content

Commit b596c32

Browse files
Resolve tuple variants in value namespace
1 parent 0bee7cb commit b596c32

File tree

4 files changed

+55
-7
lines changed

4 files changed

+55
-7
lines changed

crates/hir_ty/src/infer.rs

Lines changed: 25 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ use hir_def::{
2323
expr::{ArithOp, BinaryOp, BindingAnnotation, ExprId, PatId},
2424
lang_item::LangItemTarget,
2525
path::{path, Path},
26-
resolver::{HasResolver, Resolver, TypeNs},
26+
resolver::{HasResolver, ResolveValueResult, Resolver, TypeNs, ValueNs},
2727
type_ref::TypeRef,
2828
AdtId, AssocItemId, DefWithBodyId, EnumVariantId, FieldId, FunctionId, HasModule, Lookup,
2929
TraitId, TypeAliasId, VariantId,
@@ -548,7 +548,7 @@ impl<'a> InferenceContext<'a> {
548548
self.table.normalize_associated_types_in(ty)
549549
}
550550

551-
fn resolve_variant(&mut self, path: Option<&Path>) -> (Ty, Option<VariantId>) {
551+
fn resolve_variant(&mut self, path: Option<&Path>, value_ns: bool) -> (Ty, Option<VariantId>) {
552552
let path = match path {
553553
Some(path) => path,
554554
None => return (self.err_ty(), None),
@@ -557,11 +557,32 @@ impl<'a> InferenceContext<'a> {
557557
let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver);
558558
// FIXME: this should resolve assoc items as well, see this example:
559559
// https://play.rust-lang.org/?gist=087992e9e22495446c01c0d4e2d69521
560-
let (resolution, unresolved) =
560+
let (resolution, unresolved) = if value_ns {
561+
match resolver.resolve_path_in_value_ns(self.db.upcast(), path.mod_path()) {
562+
Some(ResolveValueResult::ValueNs(value)) => match value {
563+
ValueNs::EnumVariantId(var) => {
564+
let substs = ctx.substs_from_path(path, var.into(), true);
565+
let ty = self.db.ty(var.parent.into());
566+
let ty = self.insert_type_vars(ty.substitute(&Interner, &substs));
567+
return (ty, Some(var.into()));
568+
}
569+
ValueNs::StructId(strukt) => {
570+
let substs = ctx.substs_from_path(path, strukt.into(), true);
571+
let ty = self.db.ty(strukt.into());
572+
let ty = self.insert_type_vars(ty.substitute(&Interner, &substs));
573+
return (ty, Some(strukt.into()));
574+
}
575+
_ => return (self.err_ty(), None),
576+
},
577+
Some(ResolveValueResult::Partial(typens, unresolved)) => (typens, Some(unresolved)),
578+
None => return (self.err_ty(), None),
579+
}
580+
} else {
561581
match resolver.resolve_path_in_type_ns(self.db.upcast(), path.mod_path()) {
562582
Some(it) => it,
563583
None => return (self.err_ty(), None),
564-
};
584+
}
585+
};
565586
return match resolution {
566587
TypeNs::AdtId(AdtId::StructId(strukt)) => {
567588
let substs = ctx.substs_from_path(path, strukt.into(), true);

crates/hir_ty/src/infer/expr.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -437,7 +437,7 @@ impl<'a> InferenceContext<'a> {
437437
TyKind::Never.intern(&Interner)
438438
}
439439
Expr::RecordLit { path, fields, spread } => {
440-
let (ty, def_id) = self.resolve_variant(path.as_deref());
440+
let (ty, def_id) = self.resolve_variant(path.as_deref(), false);
441441
if let Some(variant) = def_id {
442442
self.write_variant_resolution(tgt_expr.into(), variant);
443443
}

crates/hir_ty/src/infer/pat.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ impl<'a> InferenceContext<'a> {
2727
id: PatId,
2828
ellipsis: Option<usize>,
2929
) -> Ty {
30-
let (ty, def) = self.resolve_variant(path);
30+
let (ty, def) = self.resolve_variant(path, true);
3131
let var_data = def.map(|it| it.variant_data(self.db.upcast()));
3232
if let Some(variant) = def {
3333
self.write_variant_resolution(id.into(), variant);
@@ -68,7 +68,7 @@ impl<'a> InferenceContext<'a> {
6868
default_bm: BindingMode,
6969
id: PatId,
7070
) -> Ty {
71-
let (ty, def) = self.resolve_variant(path);
71+
let (ty, def) = self.resolve_variant(path, false);
7272
let var_data = def.map(|it| it.variant_data(self.db.upcast()));
7373
if let Some(variant) = def {
7474
self.write_variant_resolution(id.into(), variant);

crates/hir_ty/src/tests/patterns.rs

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -889,3 +889,30 @@ fn main() {
889889
"#]],
890890
);
891891
}
892+
893+
#[test]
894+
fn pattern_lookup_in_value_ns() {
895+
check_types(
896+
r#"
897+
use self::Constructor::*;
898+
struct IntRange {
899+
range: (),
900+
}
901+
enum Constructor {
902+
IntRange(IntRange),
903+
}
904+
fn main() {
905+
match Constructor::IntRange(IntRange { range: () }) {
906+
IntRange(x) => {
907+
x;
908+
//^ IntRange
909+
}
910+
Constructor::IntRange(x) => {
911+
x;
912+
//^ IntRange
913+
}
914+
}
915+
}
916+
"#,
917+
);
918+
}

0 commit comments

Comments
 (0)