1use std::fmt;
2
3use derive_where::derive_where;
4#[cfg(feature = "nightly")]
5use rustc_macros::{Decodable_NoContext, Encodable_NoContext, HashStable_NoContext};
6use rustc_type_ir_macros::{TypeFoldable_Generic, TypeVisitable_Generic};
7
8use crate::{self as ty, Interner};
9
10#[derive_where(Clone, Copy, Hash, PartialEq, Eq; I: Interner)]
13#[derive(TypeVisitable_Generic, TypeFoldable_Generic)]
14#[cfg_attr(
15 feature = "nightly",
16 derive(Encodable_NoContext, Decodable_NoContext, HashStable_NoContext)
17)]
18pub enum ClauseKind<I: Interner> {
19 Trait(ty::TraitPredicate<I>),
23
24 RegionOutlives(ty::OutlivesPredicate<I, I::Region>),
26
27 TypeOutlives(ty::OutlivesPredicate<I, I::Ty>),
29
30 Projection(ty::ProjectionPredicate<I>),
33
34 ConstArgHasType(I::Const, I::Ty),
37
38 WellFormed(I::Term),
40
41 ConstEvaluatable(I::Const),
43
44 HostEffect(ty::HostEffectPredicate<I>),
49
50 UnstableFeature(
52 #[type_foldable(identity)]
53 #[type_visitable(ignore)]
54 I::Symbol,
55 ),
56}
57
58#[derive_where(Clone, Copy, Hash, PartialEq, Eq; I: Interner)]
59#[derive(TypeVisitable_Generic, TypeFoldable_Generic)]
60#[cfg_attr(
61 feature = "nightly",
62 derive(Encodable_NoContext, Decodable_NoContext, HashStable_NoContext)
63)]
64pub enum PredicateKind<I: Interner> {
65 Clause(ClauseKind<I>),
67
68 DynCompatible(I::DefId),
70
71 Subtype(ty::SubtypePredicate<I>),
77
78 Coerce(ty::CoercePredicate<I>),
87
88 ConstEquate(I::Const, I::Const),
90
91 Ambiguous,
94
95 NormalizesTo(ty::NormalizesTo<I>),
104
105 AliasRelate(I::Term, I::Term, AliasRelationDirection),
110}
111
112#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Debug, Copy)]
113#[cfg_attr(
114 feature = "nightly",
115 derive(HashStable_NoContext, Encodable_NoContext, Decodable_NoContext)
116)]
117pub enum AliasRelationDirection {
118 Equate,
119 Subtype,
120}
121
122impl std::fmt::Display for AliasRelationDirection {
123 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
124 match self {
125 AliasRelationDirection::Equate => write!(f, "=="),
126 AliasRelationDirection::Subtype => write!(f, "<:"),
127 }
128 }
129}
130
131impl<I: Interner> fmt::Debug for ClauseKind<I> {
132 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
133 match self {
134 ClauseKind::ConstArgHasType(ct, ty) => write!(f, "ConstArgHasType({ct:?}, {ty:?})"),
135 ClauseKind::HostEffect(data) => data.fmt(f),
136 ClauseKind::Trait(a) => a.fmt(f),
137 ClauseKind::RegionOutlives(pair) => pair.fmt(f),
138 ClauseKind::TypeOutlives(pair) => pair.fmt(f),
139 ClauseKind::Projection(pair) => pair.fmt(f),
140 ClauseKind::WellFormed(data) => write!(f, "WellFormed({data:?})"),
141 ClauseKind::ConstEvaluatable(ct) => {
142 write!(f, "ConstEvaluatable({ct:?})")
143 }
144 ClauseKind::UnstableFeature(feature_name) => {
145 write!(f, "UnstableFeature({feature_name:?})")
146 }
147 }
148 }
149}
150
151impl<I: Interner> fmt::Debug for PredicateKind<I> {
152 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
153 match self {
154 PredicateKind::Clause(a) => a.fmt(f),
155 PredicateKind::Subtype(pair) => pair.fmt(f),
156 PredicateKind::Coerce(pair) => pair.fmt(f),
157 PredicateKind::DynCompatible(trait_def_id) => {
158 write!(f, "DynCompatible({trait_def_id:?})")
159 }
160 PredicateKind::ConstEquate(c1, c2) => write!(f, "ConstEquate({c1:?}, {c2:?})"),
161 PredicateKind::Ambiguous => write!(f, "Ambiguous"),
162 PredicateKind::NormalizesTo(p) => p.fmt(f),
163 PredicateKind::AliasRelate(t1, t2, dir) => {
164 write!(f, "AliasRelate({t1:?}, {dir:?}, {t2:?})")
165 }
166 }
167 }
168}