Unnamed repository; edit this file 'description' to name the repository.
fix: introduce new type var when expectation for ref pat is not ref
Ryo Yoshida 2023-05-22
parent a04d845 · commit 01f42d2
-rw-r--r--crates/hir-ty/src/infer/pat.rs13
-rw-r--r--crates/hir-ty/src/tests/patterns.rs17
2 files changed, 26 insertions, 4 deletions
diff --git a/crates/hir-ty/src/infer/pat.rs b/crates/hir-ty/src/infer/pat.rs
index 05f6fcaead..0c2b179a10 100644
--- a/crates/hir-ty/src/infer/pat.rs
+++ b/crates/hir-ty/src/infer/pat.rs
@@ -313,16 +313,23 @@ impl<'a> InferenceContext<'a> {
fn infer_ref_pat(
&mut self,
- pat: PatId,
+ inner_pat: PatId,
mutability: Mutability,
expected: &Ty,
default_bm: BindingMode,
) -> Ty {
let expectation = match expected.as_reference() {
Some((inner_ty, _lifetime, _exp_mut)) => inner_ty.clone(),
- _ => self.result.standard_types.unknown.clone(),
+ None => {
+ let inner_ty = self.table.new_type_var();
+ let ref_ty =
+ TyKind::Ref(mutability, static_lifetime(), inner_ty.clone()).intern(Interner);
+ // Unification failure will be reported by the caller.
+ self.unify(&ref_ty, expected);
+ inner_ty
+ }
};
- let subty = self.infer_pat(pat, &expectation, default_bm);
+ let subty = self.infer_pat(inner_pat, &expectation, default_bm);
TyKind::Ref(mutability, static_lifetime(), subty).intern(Interner)
}
diff --git a/crates/hir-ty/src/tests/patterns.rs b/crates/hir-ty/src/tests/patterns.rs
index c8c31bdea5..b73f0d72a3 100644
--- a/crates/hir-ty/src/tests/patterns.rs
+++ b/crates/hir-ty/src/tests/patterns.rs
@@ -1,6 +1,6 @@
use expect_test::expect;
-use super::{check, check_infer, check_infer_with_mismatches, check_types};
+use super::{check, check_infer, check_infer_with_mismatches, check_no_mismatches, check_types};
#[test]
fn infer_pattern() {
@@ -241,6 +241,21 @@ fn infer_pattern_match_ergonomics_ref() {
}
#[test]
+fn ref_pat_with_inference_variable() {
+ check_no_mismatches(
+ r#"
+enum E { A }
+fn test() {
+ let f = |e| match e {
+ &E::A => {}
+ };
+ f(&E::A);
+}
+"#,
+ );
+}
+
+#[test]
fn infer_pattern_match_slice() {
check_infer(
r#"