Unnamed repository; edit this file 'description' to name the repository.
Merge #11878
11878: fix: Paper over GAT panic r=flodiebold a=flodiebold TIL that Chalk expects the arguments to a generic associated type to come *before* the ones for the parent trait, not *after* as we have been doing with all other nested generics. Fixing this requires a larger refactoring, so for now this just papers over the problem by completely ignoring parameters of associated types. Fixes #11769. Co-authored-by: Florian Diebold <[email protected]>
bors[bot] 2022-04-02
parent 0fe7417 · parent 019f486 · commit 5fe366c
-rw-r--r--crates/hir_ty/src/tests/regression.rs19
-rw-r--r--crates/hir_ty/src/utils.rs9
2 files changed, 28 insertions, 0 deletions
diff --git a/crates/hir_ty/src/tests/regression.rs b/crates/hir_ty/src/tests/regression.rs
index 2809b1e912..65eb2da5af 100644
--- a/crates/hir_ty/src/tests/regression.rs
+++ b/crates/hir_ty/src/tests/regression.rs
@@ -1497,3 +1497,22 @@ fn regression_11688_3() {
"#,
);
}
+
+#[test]
+fn gat_crash() {
+ cov_mark::check!(ignore_gats);
+ check_no_mismatches(
+ r#"
+trait ATrait {}
+
+trait Crash {
+ type Member<const N: usize>: ATrait;
+ fn new<const N: usize>() -> Self::Member<N>;
+}
+
+fn test<T: Crash>() {
+ T::new();
+}
+"#,
+ );
+}
diff --git a/crates/hir_ty/src/utils.rs b/crates/hir_ty/src/utils.rs
index 343e89eb9b..c4a11c86d4 100644
--- a/crates/hir_ty/src/utils.rs
+++ b/crates/hir_ty/src/utils.rs
@@ -175,6 +175,15 @@ pub(super) fn associated_type_by_name_including_super_traits(
pub(crate) fn generics(db: &dyn DefDatabase, def: GenericDefId) -> Generics {
let parent_generics = parent_generic_def(db, def).map(|def| Box::new(generics(db, def)));
+ if parent_generics.is_some() && matches!(def, GenericDefId::TypeAliasId(_)) {
+ // XXX: treat generic associated types as not existing to avoid crashes (#)
+ //
+ // Chalk expects the inner associated type's parameters to come
+ // *before*, not after the trait's generics as we've always done it.
+ // Adapting to this requires a larger refactoring
+ cov_mark::hit!(ignore_gats);
+ return Generics { def, params: Interned::new(Default::default()), parent_generics };
+ }
Generics { def, params: db.generic_params(def), parent_generics }
}