From a236bfa57a1a860e834498d6ca1e1fc1f857a3a4 Mon Sep 17 00:00:00 2001 From: Dawer <7803845+iDawer@users.noreply.github.com> Date: Fri, 7 May 2021 10:38:51 +0500 Subject: Lower binding pattern --- crates/hir_ty/src/diagnostics/pattern.rs | 30 +++++++++++++++++++--- .../src/diagnostics/pattern/deconstruct_pat.rs | 7 +---- 2 files changed, 28 insertions(+), 9 deletions(-) (limited to 'crates') diff --git a/crates/hir_ty/src/diagnostics/pattern.rs b/crates/hir_ty/src/diagnostics/pattern.rs index 14dd736a6..99f32097f 100644 --- a/crates/hir_ty/src/diagnostics/pattern.rs +++ b/crates/hir_ty/src/diagnostics/pattern.rs @@ -11,7 +11,7 @@ use la_arena::Idx; use crate::{db::HirDatabase, AdtId, InferenceResult, Interner, Substitution, Ty, TyKind}; -use self::{deconstruct_pat::ToDo, pat_util::EnumerateAndAdjustIterator}; +use self::pat_util::EnumerateAndAdjustIterator; pub type PatId = Idx; @@ -45,7 +45,6 @@ pub enum PatKind { /// `x`, `ref x`, `x @ P`, etc. Binding { subpattern: Option, - // todo: ToDo, }, /// `Foo(...)` or `Foo{...}` or `Foo`, where `Foo` is a variant name from an ADT with @@ -119,6 +118,10 @@ impl<'a> PatCtxt<'a> { PatKind::Leaf { subpatterns } } + hir_def::expr::Pat::Bind { subpat, .. } => { + PatKind::Binding { subpattern: self.lower_opt_pattern(subpat) } + } + hir_def::expr::Pat::TupleStruct { ref args, ellipsis, .. } => { let variant_data = match self.infer.variant_resolution_for_pat(pat) { Some(variant_id) => variant_id.variant_data(self.db.upcast()), @@ -175,6 +178,10 @@ impl<'a> PatCtxt<'a> { pats.iter().map(|&p| self.lower_pattern(p)).collect() } + fn lower_opt_pattern(&mut self, pat: Option) -> Option { + pat.map(|p| self.lower_pattern(p)) + } + fn lower_variant_or_leaf( &mut self, pat: hir_def::expr::PatId, @@ -383,13 +390,30 @@ fn main() { struct S { a: char} fn main(v: S) { match v { S{ a } => {} } - match v { S{ a: x } => {} } + match v { S{ a: _x } => {} } match v { S{ a: 'a' } => {} } match v { S{..} => {} } match v { _ => {} } match v { } //^ Missing match arm } +"#, + ); + } + + #[test] + fn binding() { + check_diagnostics( + r#" +fn main() { + match true { + _x @ true => {} + false => {} + } + //FIXME: false negative. + // Binding patterns should be expanded in `usefulness::expand_pattern()` + match true { _x @ true => {} } +} "#, ); } diff --git a/crates/hir_ty/src/diagnostics/pattern/deconstruct_pat.rs b/crates/hir_ty/src/diagnostics/pattern/deconstruct_pat.rs index 91b9c7184..1c86ed59b 100644 --- a/crates/hir_ty/src/diagnostics/pattern/deconstruct_pat.rs +++ b/crates/hir_ty/src/diagnostics/pattern/deconstruct_pat.rs @@ -801,12 +801,7 @@ impl Fields { cx: &MatchCheckCtx<'_>, pats: impl IntoIterator, ) -> Self { - let pats = { - let tys: SmallVec<[Ty; 2]> = match self { - Fields::Vec(pats) => pats.iter().copied().map(|pat| cx.type_of(pat)).collect(), - }; - pats.into_iter().zip(tys.into_iter()).map(move |(pat, ty)| cx.alloc_pat(pat)).collect() - }; + let pats = pats.into_iter().map(|pat| cx.alloc_pat(pat)).collect(); match self { Fields::Vec(_) => Fields::Vec(pats), -- cgit v1.2.3