11//! Type inhabitedness logic.
2- use std:: {
3- collections:: HashMap ,
4- ops:: ControlFlow :: { self , Break , Continue } ,
5- } ;
2+ use std:: ops:: ControlFlow :: { self , Break , Continue } ;
63
74use chalk_ir:: {
85 visit:: { TypeSuperVisitable , TypeVisitable , TypeVisitor } ,
@@ -12,7 +9,7 @@ use hir_def::{
129 adt:: VariantData , attr:: Attrs , visibility:: Visibility , AdtId , EnumVariantId , HasModule , Lookup ,
1310 ModuleId , VariantId ,
1411} ;
15- use rustc_hash:: FxHashMap ;
12+ use rustc_hash:: FxHashSet ;
1613
1714use crate :: {
1815 consteval:: try_const_usize, db:: HirDatabase , Binders , Interner , Substitution , Ty , TyKind ,
@@ -21,7 +18,7 @@ use crate::{
2118/// Checks whether a type is visibly uninhabited from a particular module.
2219pub ( crate ) fn is_ty_uninhabited_from ( ty : & Ty , target_mod : ModuleId , db : & dyn HirDatabase ) -> bool {
2320 let mut uninhabited_from =
24- UninhabitedFrom { target_mod, db, max_depth : 500 , recursive_ty : HashMap :: default ( ) } ;
21+ UninhabitedFrom { target_mod, db, max_depth : 500 , recursive_ty : FxHashSet :: default ( ) } ;
2522 let inhabitedness = ty. visit_with ( & mut uninhabited_from, DebruijnIndex :: INNERMOST ) ;
2623 inhabitedness == BREAK_VISIBLY_UNINHABITED
2724}
@@ -38,7 +35,7 @@ pub(crate) fn is_enum_variant_uninhabited_from(
3835 let is_local = variant. parent . lookup ( db. upcast ( ) ) . container . krate ( ) == target_mod. krate ( ) ;
3936
4037 let mut uninhabited_from =
41- UninhabitedFrom { target_mod, db, max_depth : 500 , recursive_ty : HashMap :: default ( ) } ;
38+ UninhabitedFrom { target_mod, db, max_depth : 500 , recursive_ty : FxHashSet :: default ( ) } ;
4239 let inhabitedness = uninhabited_from. visit_variant (
4340 variant. into ( ) ,
4441 & enum_data. variants [ variant. local_id ] . variant_data ,
@@ -51,7 +48,7 @@ pub(crate) fn is_enum_variant_uninhabited_from(
5148
5249struct UninhabitedFrom < ' a > {
5350 target_mod : ModuleId ,
54- recursive_ty : FxHashMap < Ty , ( ) > ,
51+ recursive_ty : FxHashSet < Ty > ,
5552 // guard for preventing stack overflow in non trivial non terminating types
5653 max_depth : usize ,
5754 db : & ' a dyn HirDatabase ,
@@ -74,12 +71,12 @@ impl TypeVisitor<Interner> for UninhabitedFrom<'_> {
7471 ty : & Ty ,
7572 outer_binder : DebruijnIndex ,
7673 ) -> ControlFlow < VisiblyUninhabited > {
77- if self . recursive_ty . contains_key ( ty) || self . max_depth == 0 {
74+ if self . recursive_ty . contains ( ty) || self . max_depth == 0 {
7875 // rustc considers recursive types always inhabited. I think it is valid to consider
7976 // recursive types as always uninhabited, but we should do what rustc is doing.
8077 return CONTINUE_OPAQUELY_INHABITED ;
8178 }
82- self . recursive_ty . insert ( ty. clone ( ) , ( ) ) ;
79+ self . recursive_ty . insert ( ty. clone ( ) ) ;
8380 self . max_depth -= 1 ;
8481 let r = match ty. kind ( Interner ) {
8582 TyKind :: Adt ( adt, subst) => self . visit_adt ( adt. 0 , subst) ,
0 commit comments