Skip to content

Commit 109c5db

Browse files
Move some files around
1 parent 8199be0 commit 109c5db

12 files changed

+1548
-1520
lines changed
+258
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,258 @@
1+
use rustc_data_structures::stable_hasher::HashStable;
2+
use rustc_serialize::{Decodable, Decoder, Encodable};
3+
use std::cmp::Ordering;
4+
use std::fmt;
5+
use std::hash;
6+
7+
use crate::{
8+
DebruijnIndex, DebugWithInfcx, HashStableContext, InferCtxtLike, Interner, OptWithInfcx,
9+
TyDecoder, TyEncoder,
10+
};
11+
12+
use self::ConstKind::*;
13+
14+
/// Represents a constant in Rust.
15+
// #[derive(derive_more::From)]
16+
pub enum ConstKind<I: Interner> {
17+
/// A const generic parameter.
18+
Param(I::ParamConst),
19+
20+
/// Infer the value of the const.
21+
Infer(I::InferConst),
22+
23+
/// Bound const variable, used only when preparing a trait query.
24+
Bound(DebruijnIndex, I::BoundConst),
25+
26+
/// A placeholder const - universally quantified higher-ranked const.
27+
Placeholder(I::PlaceholderConst),
28+
29+
/// An unnormalized const item such as an anon const or assoc const or free const item.
30+
/// Right now anything other than anon consts does not actually work properly but this
31+
/// should
32+
Unevaluated(I::AliasConst),
33+
34+
/// Used to hold computed value.
35+
Value(I::ValueConst),
36+
37+
/// A placeholder for a const which could not be computed; this is
38+
/// propagated to avoid useless error messages.
39+
Error(I::ErrorGuaranteed),
40+
41+
/// Unevaluated non-const-item, used by `feature(generic_const_exprs)` to represent
42+
/// const arguments such as `N + 1` or `foo(N)`
43+
Expr(I::ExprConst),
44+
}
45+
46+
const fn const_kind_discriminant<I: Interner>(value: &ConstKind<I>) -> usize {
47+
match value {
48+
Param(_) => 0,
49+
Infer(_) => 1,
50+
Bound(_, _) => 2,
51+
Placeholder(_) => 3,
52+
Unevaluated(_) => 4,
53+
Value(_) => 5,
54+
Error(_) => 6,
55+
Expr(_) => 7,
56+
}
57+
}
58+
59+
impl<I: Interner> hash::Hash for ConstKind<I> {
60+
fn hash<H: hash::Hasher>(&self, state: &mut H) {
61+
const_kind_discriminant(self).hash(state);
62+
match self {
63+
Param(p) => p.hash(state),
64+
Infer(i) => i.hash(state),
65+
Bound(d, b) => {
66+
d.hash(state);
67+
b.hash(state);
68+
}
69+
Placeholder(p) => p.hash(state),
70+
Unevaluated(u) => u.hash(state),
71+
Value(v) => v.hash(state),
72+
Error(e) => e.hash(state),
73+
Expr(e) => e.hash(state),
74+
}
75+
}
76+
}
77+
78+
impl<CTX: HashStableContext, I: Interner> HashStable<CTX> for ConstKind<I>
79+
where
80+
I::ParamConst: HashStable<CTX>,
81+
I::InferConst: HashStable<CTX>,
82+
I::BoundConst: HashStable<CTX>,
83+
I::PlaceholderConst: HashStable<CTX>,
84+
I::AliasConst: HashStable<CTX>,
85+
I::ValueConst: HashStable<CTX>,
86+
I::ErrorGuaranteed: HashStable<CTX>,
87+
I::ExprConst: HashStable<CTX>,
88+
{
89+
fn hash_stable(
90+
&self,
91+
hcx: &mut CTX,
92+
hasher: &mut rustc_data_structures::stable_hasher::StableHasher,
93+
) {
94+
const_kind_discriminant(self).hash_stable(hcx, hasher);
95+
match self {
96+
Param(p) => p.hash_stable(hcx, hasher),
97+
Infer(i) => i.hash_stable(hcx, hasher),
98+
Bound(d, b) => {
99+
d.hash_stable(hcx, hasher);
100+
b.hash_stable(hcx, hasher);
101+
}
102+
Placeholder(p) => p.hash_stable(hcx, hasher),
103+
Unevaluated(u) => u.hash_stable(hcx, hasher),
104+
Value(v) => v.hash_stable(hcx, hasher),
105+
Error(e) => e.hash_stable(hcx, hasher),
106+
Expr(e) => e.hash_stable(hcx, hasher),
107+
}
108+
}
109+
}
110+
111+
impl<I: Interner, D: TyDecoder<I = I>> Decodable<D> for ConstKind<I>
112+
where
113+
I::ParamConst: Decodable<D>,
114+
I::InferConst: Decodable<D>,
115+
I::BoundConst: Decodable<D>,
116+
I::PlaceholderConst: Decodable<D>,
117+
I::AliasConst: Decodable<D>,
118+
I::ValueConst: Decodable<D>,
119+
I::ErrorGuaranteed: Decodable<D>,
120+
I::ExprConst: Decodable<D>,
121+
{
122+
fn decode(d: &mut D) -> Self {
123+
match Decoder::read_usize(d) {
124+
0 => Param(Decodable::decode(d)),
125+
1 => Infer(Decodable::decode(d)),
126+
2 => Bound(Decodable::decode(d), Decodable::decode(d)),
127+
3 => Placeholder(Decodable::decode(d)),
128+
4 => Unevaluated(Decodable::decode(d)),
129+
5 => Value(Decodable::decode(d)),
130+
6 => Error(Decodable::decode(d)),
131+
7 => Expr(Decodable::decode(d)),
132+
_ => panic!(
133+
"{}",
134+
format!(
135+
"invalid enum variant tag while decoding `{}`, expected 0..{}",
136+
"ConstKind", 8,
137+
)
138+
),
139+
}
140+
}
141+
}
142+
143+
impl<I: Interner, E: TyEncoder<I = I>> Encodable<E> for ConstKind<I>
144+
where
145+
I::ParamConst: Encodable<E>,
146+
I::InferConst: Encodable<E>,
147+
I::BoundConst: Encodable<E>,
148+
I::PlaceholderConst: Encodable<E>,
149+
I::AliasConst: Encodable<E>,
150+
I::ValueConst: Encodable<E>,
151+
I::ErrorGuaranteed: Encodable<E>,
152+
I::ExprConst: Encodable<E>,
153+
{
154+
fn encode(&self, e: &mut E) {
155+
let disc = const_kind_discriminant(self);
156+
match self {
157+
Param(p) => e.emit_enum_variant(disc, |e| p.encode(e)),
158+
Infer(i) => e.emit_enum_variant(disc, |e| i.encode(e)),
159+
Bound(d, b) => e.emit_enum_variant(disc, |e| {
160+
d.encode(e);
161+
b.encode(e);
162+
}),
163+
Placeholder(p) => e.emit_enum_variant(disc, |e| p.encode(e)),
164+
Unevaluated(u) => e.emit_enum_variant(disc, |e| u.encode(e)),
165+
Value(v) => e.emit_enum_variant(disc, |e| v.encode(e)),
166+
Error(er) => e.emit_enum_variant(disc, |e| er.encode(e)),
167+
Expr(ex) => e.emit_enum_variant(disc, |e| ex.encode(e)),
168+
}
169+
}
170+
}
171+
172+
impl<I: Interner> PartialOrd for ConstKind<I> {
173+
fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
174+
Some(self.cmp(other))
175+
}
176+
}
177+
178+
impl<I: Interner> Ord for ConstKind<I> {
179+
fn cmp(&self, other: &Self) -> Ordering {
180+
const_kind_discriminant(self)
181+
.cmp(&const_kind_discriminant(other))
182+
.then_with(|| match (self, other) {
183+
(Param(p1), Param(p2)) => p1.cmp(p2),
184+
(Infer(i1), Infer(i2)) => i1.cmp(i2),
185+
(Bound(d1, b1), Bound(d2, b2)) => d1.cmp(d2).then_with(|| b1.cmp(b2)),
186+
(Placeholder(p1), Placeholder(p2)) => p1.cmp(p2),
187+
(Unevaluated(u1), Unevaluated(u2)) => u1.cmp(u2),
188+
(Value(v1), Value(v2)) => v1.cmp(v2),
189+
(Error(e1), Error(e2)) => e1.cmp(e2),
190+
(Expr(e1), Expr(e2)) => e1.cmp(e2),
191+
_ => {
192+
debug_assert!(false, "This branch must be unreachable, maybe the match is missing an arm? self = {self:?}, other = {other:?}");
193+
Ordering::Equal
194+
}
195+
})
196+
}
197+
}
198+
199+
impl<I: Interner> PartialEq for ConstKind<I> {
200+
fn eq(&self, other: &Self) -> bool {
201+
match (self, other) {
202+
(Param(l0), Param(r0)) => l0 == r0,
203+
(Infer(l0), Infer(r0)) => l0 == r0,
204+
(Bound(l0, l1), Bound(r0, r1)) => l0 == r0 && l1 == r1,
205+
(Placeholder(l0), Placeholder(r0)) => l0 == r0,
206+
(Unevaluated(l0), Unevaluated(r0)) => l0 == r0,
207+
(Value(l0), Value(r0)) => l0 == r0,
208+
(Error(l0), Error(r0)) => l0 == r0,
209+
(Expr(l0), Expr(r0)) => l0 == r0,
210+
_ => false,
211+
}
212+
}
213+
}
214+
215+
impl<I: Interner> Eq for ConstKind<I> {}
216+
217+
impl<I: Interner> Clone for ConstKind<I> {
218+
fn clone(&self) -> Self {
219+
match self {
220+
Param(arg0) => Param(arg0.clone()),
221+
Infer(arg0) => Infer(arg0.clone()),
222+
Bound(arg0, arg1) => Bound(arg0.clone(), arg1.clone()),
223+
Placeholder(arg0) => Placeholder(arg0.clone()),
224+
Unevaluated(arg0) => Unevaluated(arg0.clone()),
225+
Value(arg0) => Value(arg0.clone()),
226+
Error(arg0) => Error(arg0.clone()),
227+
Expr(arg0) => Expr(arg0.clone()),
228+
}
229+
}
230+
}
231+
232+
impl<I: Interner> fmt::Debug for ConstKind<I> {
233+
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
234+
OptWithInfcx::new_no_ctx(self).fmt(f)
235+
}
236+
}
237+
238+
impl<I: Interner> DebugWithInfcx<I> for ConstKind<I> {
239+
fn fmt<InfCtx: InferCtxtLike<I>>(
240+
this: OptWithInfcx<'_, I, InfCtx, &Self>,
241+
f: &mut core::fmt::Formatter<'_>,
242+
) -> core::fmt::Result {
243+
use ConstKind::*;
244+
245+
match this.data {
246+
Param(param) => write!(f, "{param:?}"),
247+
Infer(var) => write!(f, "{:?}", &this.wrap(var)),
248+
Bound(debruijn, var) => crate::debug_bound_var(f, *debruijn, var.clone()),
249+
Placeholder(placeholder) => write!(f, "{placeholder:?}"),
250+
Unevaluated(uv) => {
251+
write!(f, "{:?}", &this.wrap(uv))
252+
}
253+
Value(valtree) => write!(f, "{valtree:?}"),
254+
Error(_) => write!(f, "{{const error}}"),
255+
Expr(expr) => write!(f, "{:?}", &this.wrap(expr)),
256+
}
257+
}
258+
}

compiler/rustc_type_ir/src/debug.rs

+117
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
use crate::{Interner, UniverseIndex};
2+
3+
use core::fmt;
4+
use std::marker::PhantomData;
5+
6+
pub trait InferCtxtLike<I: Interner> {
7+
fn universe_of_ty(&self, ty: I::InferTy) -> Option<UniverseIndex>;
8+
9+
fn universe_of_lt(&self, lt: I::InferRegion) -> Option<UniverseIndex>;
10+
11+
fn universe_of_ct(&self, ct: I::InferConst) -> Option<UniverseIndex>;
12+
}
13+
14+
impl<I: Interner> InferCtxtLike<I> for core::convert::Infallible {
15+
fn universe_of_ty(&self, _ty: <I as Interner>::InferTy) -> Option<UniverseIndex> {
16+
match *self {}
17+
}
18+
19+
fn universe_of_ct(&self, _ct: <I as Interner>::InferConst) -> Option<UniverseIndex> {
20+
match *self {}
21+
}
22+
23+
fn universe_of_lt(&self, _lt: <I as Interner>::InferRegion) -> Option<UniverseIndex> {
24+
match *self {}
25+
}
26+
}
27+
28+
pub trait DebugWithInfcx<I: Interner>: fmt::Debug {
29+
fn fmt<InfCtx: InferCtxtLike<I>>(
30+
this: OptWithInfcx<'_, I, InfCtx, &Self>,
31+
f: &mut fmt::Formatter<'_>,
32+
) -> fmt::Result;
33+
}
34+
35+
impl<I: Interner, T: DebugWithInfcx<I> + ?Sized> DebugWithInfcx<I> for &'_ T {
36+
fn fmt<InfCtx: InferCtxtLike<I>>(
37+
this: OptWithInfcx<'_, I, InfCtx, &Self>,
38+
f: &mut fmt::Formatter<'_>,
39+
) -> fmt::Result {
40+
<T as DebugWithInfcx<I>>::fmt(this.map(|&data| data), f)
41+
}
42+
}
43+
44+
impl<I: Interner, T: DebugWithInfcx<I>> DebugWithInfcx<I> for [T] {
45+
fn fmt<InfCtx: InferCtxtLike<I>>(
46+
this: OptWithInfcx<'_, I, InfCtx, &Self>,
47+
f: &mut fmt::Formatter<'_>,
48+
) -> fmt::Result {
49+
match f.alternate() {
50+
true => {
51+
write!(f, "[\n")?;
52+
for element in this.data.iter() {
53+
write!(f, "{:?},\n", &this.wrap(element))?;
54+
}
55+
write!(f, "]")
56+
}
57+
false => {
58+
write!(f, "[")?;
59+
if this.data.len() > 0 {
60+
for element in &this.data[..(this.data.len() - 1)] {
61+
write!(f, "{:?}, ", &this.wrap(element))?;
62+
}
63+
if let Some(element) = this.data.last() {
64+
write!(f, "{:?}", &this.wrap(element))?;
65+
}
66+
}
67+
write!(f, "]")
68+
}
69+
}
70+
}
71+
}
72+
73+
pub struct OptWithInfcx<'a, I: Interner, InfCtx: InferCtxtLike<I>, T> {
74+
pub data: T,
75+
pub infcx: Option<&'a InfCtx>,
76+
_interner: PhantomData<I>,
77+
}
78+
79+
impl<I: Interner, InfCtx: InferCtxtLike<I>, T: Copy> Copy for OptWithInfcx<'_, I, InfCtx, T> {}
80+
81+
impl<I: Interner, InfCtx: InferCtxtLike<I>, T: Clone> Clone for OptWithInfcx<'_, I, InfCtx, T> {
82+
fn clone(&self) -> Self {
83+
Self { data: self.data.clone(), infcx: self.infcx, _interner: self._interner }
84+
}
85+
}
86+
87+
impl<'a, I: Interner, T> OptWithInfcx<'a, I, core::convert::Infallible, T> {
88+
pub fn new_no_ctx(data: T) -> Self {
89+
Self { data, infcx: None, _interner: PhantomData }
90+
}
91+
}
92+
93+
impl<'a, I: Interner, InfCtx: InferCtxtLike<I>, T> OptWithInfcx<'a, I, InfCtx, T> {
94+
pub fn new(data: T, infcx: &'a InfCtx) -> Self {
95+
Self { data, infcx: Some(infcx), _interner: PhantomData }
96+
}
97+
98+
pub fn wrap<U>(self, u: U) -> OptWithInfcx<'a, I, InfCtx, U> {
99+
OptWithInfcx { data: u, infcx: self.infcx, _interner: PhantomData }
100+
}
101+
102+
pub fn map<U>(self, f: impl FnOnce(T) -> U) -> OptWithInfcx<'a, I, InfCtx, U> {
103+
OptWithInfcx { data: f(self.data), infcx: self.infcx, _interner: PhantomData }
104+
}
105+
106+
pub fn as_ref(&self) -> OptWithInfcx<'a, I, InfCtx, &T> {
107+
OptWithInfcx { data: &self.data, infcx: self.infcx, _interner: PhantomData }
108+
}
109+
}
110+
111+
impl<I: Interner, InfCtx: InferCtxtLike<I>, T: DebugWithInfcx<I>> fmt::Debug
112+
for OptWithInfcx<'_, I, InfCtx, T>
113+
{
114+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
115+
DebugWithInfcx::fmt(self.as_ref(), f)
116+
}
117+
}

0 commit comments

Comments
 (0)