From ece18fecfabdc3583a3f38436682296e652161a2 Mon Sep 17 00:00:00 2001 From: roife Date: Tue, 5 Mar 2024 19:29:49 +0800 Subject: [PATCH 1/4] fix: resolve sub-patterns inside range pattern --- crates/hir-def/src/body/lower.rs | 12 +++--------- crates/hir-def/src/body/pretty.rs | 2 +- crates/hir-def/src/hir.rs | 2 +- 3 files changed, 5 insertions(+), 11 deletions(-) diff --git a/crates/hir-def/src/body/lower.rs b/crates/hir-def/src/body/lower.rs index c9300898b386..18a6c5c2cdc2 100644 --- a/crates/hir-def/src/body/lower.rs +++ b/crates/hir-def/src/body/lower.rs @@ -1413,16 +1413,10 @@ impl ExprCollector<'_> { ast::Pat::LiteralPat(it) => { Some(Box::new(LiteralOrConst::Literal(pat_literal_to_hir(it)?.0))) } - ast::Pat::IdentPat(p) => { - let name = - p.name().map(|nr| nr.as_name()).unwrap_or_else(Name::missing); - Some(Box::new(LiteralOrConst::Const(name.into()))) + pat @ (ast::Pat::IdentPat(_) | ast::Pat::PathPat(_)) => { + let subpat = self.collect_pat(pat.clone(), binding_list); + Some(Box::new(LiteralOrConst::Const(subpat))) } - ast::Pat::PathPat(p) => p - .path() - .and_then(|path| self.expander.parse_path(self.db, path)) - .map(LiteralOrConst::Const) - .map(Box::new), _ => None, }) }; diff --git a/crates/hir-def/src/body/pretty.rs b/crates/hir-def/src/body/pretty.rs index cd14f7b855a8..b2aab55a6a89 100644 --- a/crates/hir-def/src/body/pretty.rs +++ b/crates/hir-def/src/body/pretty.rs @@ -635,7 +635,7 @@ impl Printer<'_> { fn print_literal_or_const(&mut self, literal_or_const: &LiteralOrConst) { match literal_or_const { LiteralOrConst::Literal(l) => self.print_literal(l), - LiteralOrConst::Const(c) => self.print_path(c), + LiteralOrConst::Const(c) => self.print_pat(*c), } } diff --git a/crates/hir-def/src/hir.rs b/crates/hir-def/src/hir.rs index 34b2910b4f5e..ac0caaf0dc89 100644 --- a/crates/hir-def/src/hir.rs +++ b/crates/hir-def/src/hir.rs @@ -101,7 +101,7 @@ pub enum Literal { /// Used in range patterns. pub enum LiteralOrConst { Literal(Literal), - Const(Path), + Const(PatId), } impl Literal { From 96a7c6ae3cc69ace6c2e77cc4a4c7f453c07998c Mon Sep 17 00:00:00 2001 From: roife Date: Tue, 5 Mar 2024 19:30:41 +0800 Subject: [PATCH 2/4] fix: mir for range pattern --- crates/hir-ty/src/mir/lower.rs | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/crates/hir-ty/src/mir/lower.rs b/crates/hir-ty/src/mir/lower.rs index ed316f972689..577a01aee782 100644 --- a/crates/hir-ty/src/mir/lower.rs +++ b/crates/hir-ty/src/mir/lower.rs @@ -1364,10 +1364,14 @@ impl<'ctx> MirLowerCtx<'ctx> { match loc { LiteralOrConst::Literal(l) => self.lower_literal_to_operand(ty, l), LiteralOrConst::Const(c) => { - let unresolved_name = || MirLowerError::unresolved_path(self.db, c); + let c = match &self.body.pats[*c] { + Pat::Path(p) => p, + _ => not_supported!("only `char` and numeric types are allowed in range patterns"), + }; + let unresolved_name = || MirLowerError::unresolved_path(self.db, c.as_ref()); let resolver = self.owner.resolver(self.db.upcast()); let pr = resolver - .resolve_path_in_value_ns(self.db.upcast(), c) + .resolve_path_in_value_ns(self.db.upcast(), c.as_ref()) .ok_or_else(unresolved_name)?; match pr { ResolveValueResult::ValueNs(v, _) => { From 16995ceda94b68f2bf667e1f7eff022ea795de50 Mon Sep 17 00:00:00 2001 From: roife Date: Tue, 5 Mar 2024 19:31:01 +0800 Subject: [PATCH 3/4] test: add tests for constants inside range pattern --- crates/ide/src/goto_definition.rs | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/crates/ide/src/goto_definition.rs b/crates/ide/src/goto_definition.rs index 41148db61460..aac01384cbdb 100644 --- a/crates/ide/src/goto_definition.rs +++ b/crates/ide/src/goto_definition.rs @@ -532,6 +532,24 @@ fn bar() { $0foo!() => {} } } +"#, + ); + } + + #[test] + fn goto_definition_works_for_consts_inside_range_pattern() { + check( + r#" +//- /lib.rs +const A: u32 = 0; + //^ + +fn bar(v: u32) { + match v { + 0..=$0A => {} + _ => {} + } +} "#, ); } From 9cc3a9cfc25ea36ceb0474011d51de4fc7d42f7a Mon Sep 17 00:00:00 2001 From: roife Date: Tue, 5 Mar 2024 19:55:31 +0800 Subject: [PATCH 4/4] fix: formatting --- crates/hir-ty/src/mir/lower.rs | 4 +++- crates/ide/src/goto_definition.rs | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/crates/hir-ty/src/mir/lower.rs b/crates/hir-ty/src/mir/lower.rs index 577a01aee782..d0f739e6ac66 100644 --- a/crates/hir-ty/src/mir/lower.rs +++ b/crates/hir-ty/src/mir/lower.rs @@ -1366,7 +1366,9 @@ impl<'ctx> MirLowerCtx<'ctx> { LiteralOrConst::Const(c) => { let c = match &self.body.pats[*c] { Pat::Path(p) => p, - _ => not_supported!("only `char` and numeric types are allowed in range patterns"), + _ => not_supported!( + "only `char` and numeric types are allowed in range patterns" + ), }; let unresolved_name = || MirLowerError::unresolved_path(self.db, c.as_ref()); let resolver = self.owner.resolver(self.db.upcast()); diff --git a/crates/ide/src/goto_definition.rs b/crates/ide/src/goto_definition.rs index aac01384cbdb..1bda15255dcd 100644 --- a/crates/ide/src/goto_definition.rs +++ b/crates/ide/src/goto_definition.rs @@ -536,7 +536,7 @@ fn bar() { ); } - #[test] + #[test] fn goto_definition_works_for_consts_inside_range_pattern() { check( r#"