@@ -30,7 +30,7 @@ use ty::subst::{Subst, Substs};
3030use ty:: walk:: TypeWalker ;
3131use util:: common:: MemoizationMap ;
3232use util:: nodemap:: NodeSet ;
33- use util:: nodemap:: FxHashMap ;
33+ use util:: nodemap:: { FxHashMap , FxHashSet } ;
3434
3535use serialize:: { self , Encodable , Encoder } ;
3636use std:: borrow:: Cow ;
@@ -1390,6 +1390,22 @@ impl<'tcx> serialize::UseSpecializedEncodable for AdtDef<'tcx> {
13901390
13911391impl < ' tcx > serialize:: UseSpecializedDecodable for AdtDef < ' tcx > { }
13921392
1393+ impl < ' a , ' gcx , ' tcx > AdtDefData < ' tcx , ' static > {
1394+ #[ inline]
1395+ pub fn is_uninhabited_recurse ( & ' tcx self ,
1396+ visited : & mut FxHashSet < ( DefId , & ' tcx Substs < ' tcx > ) > ,
1397+ block : Option < NodeId > ,
1398+ cx : TyCtxt < ' a , ' gcx , ' tcx > ,
1399+ substs : & ' tcx Substs < ' tcx > ) -> bool {
1400+ if !visited. insert ( ( self . did , substs) ) {
1401+ return false ;
1402+ } ;
1403+ self . variants . iter ( ) . all ( |v| {
1404+ v. is_uninhabited_recurse ( visited, block, cx, substs, self . is_union ( ) )
1405+ } )
1406+ }
1407+ }
1408+
13931409#[ derive( Copy , Clone , Debug , Eq , PartialEq ) ]
13941410pub enum AdtKind { Struct , Union , Enum }
13951411
@@ -1532,11 +1548,6 @@ impl<'a, 'gcx, 'tcx, 'container> AdtDefData<'gcx, 'container> {
15321548 self . variants . iter ( ) . flat_map ( VariantDefData :: fields_iter)
15331549 }
15341550
1535- #[ inline]
1536- pub fn is_empty ( & self ) -> bool {
1537- self . variants . is_empty ( )
1538- }
1539-
15401551 #[ inline]
15411552 pub fn is_univariant ( & self ) -> bool {
15421553 self . variants . len ( ) == 1
@@ -1796,6 +1807,22 @@ impl<'tcx, 'container> VariantDefData<'tcx, 'container> {
17961807 }
17971808}
17981809
1810+ impl < ' a , ' gcx , ' tcx > VariantDefData < ' tcx , ' static > {
1811+ #[ inline]
1812+ pub fn is_uninhabited_recurse ( & ' tcx self ,
1813+ visited : & mut FxHashSet < ( DefId , & ' tcx Substs < ' tcx > ) > ,
1814+ block : Option < NodeId > ,
1815+ cx : TyCtxt < ' a , ' gcx , ' tcx > ,
1816+ substs : & ' tcx Substs < ' tcx > ,
1817+ is_union : bool ) -> bool {
1818+ if is_union {
1819+ self . fields . iter ( ) . all ( |f| f. is_uninhabited_recurse ( visited, block, cx, substs) )
1820+ } else {
1821+ self . fields . iter ( ) . any ( |f| f. is_uninhabited_recurse ( visited, block, cx, substs) )
1822+ }
1823+ }
1824+ }
1825+
17991826impl < ' a , ' gcx , ' tcx , ' container > FieldDefData < ' tcx , ' container > {
18001827 pub fn new ( did : DefId ,
18011828 name : Name ,
@@ -1821,6 +1848,18 @@ impl<'a, 'gcx, 'tcx, 'container> FieldDefData<'tcx, 'container> {
18211848 }
18221849}
18231850
1851+ impl < ' a , ' gcx , ' tcx > FieldDefData < ' tcx , ' static > {
1852+ #[ inline]
1853+ pub fn is_uninhabited_recurse ( & ' tcx self ,
1854+ visited : & mut FxHashSet < ( DefId , & ' tcx Substs < ' tcx > ) > ,
1855+ block : Option < NodeId > ,
1856+ tcx : TyCtxt < ' a , ' gcx , ' tcx > ,
1857+ substs : & ' tcx Substs < ' tcx > ) -> bool {
1858+ block. map_or ( true , |b| self . vis . is_accessible_from ( b, & tcx. map ) ) &&
1859+ self . ty ( tcx, substs) . is_uninhabited_recurse ( visited, block, tcx)
1860+ }
1861+ }
1862+
18241863/// Records the substitutions used to translate the polytype for an
18251864/// item into the monotype of an item reference.
18261865#[ derive( Clone , RustcEncodable , RustcDecodable ) ]
0 commit comments