@@ -74,10 +74,10 @@ impl BoundRegionKind {
74
74
}
75
75
}
76
76
77
- /// Defines the kinds of types.
77
+ /// Defines the kinds of types used by the type system .
78
78
///
79
- /// N.B., if you change this, you'll probably want to change the corresponding
80
- /// AST structure in `rustc_ast/src/ast.rs` as well .
79
+ /// Types written by the user start out as [hir::TyKind](rustc_hir::TyKind) and get
80
+ /// converted to this representation using `AstConv::ast_ty_to_ty` .
81
81
#[ derive( Clone , PartialEq , Eq , PartialOrd , Ord , Hash , TyEncodable , TyDecodable , Debug ) ]
82
82
#[ derive( HashStable ) ]
83
83
#[ rustc_diagnostic_item = "TyKind" ]
@@ -100,10 +100,11 @@ pub enum TyKind<'tcx> {
100
100
101
101
/// Algebraic data types (ADT). For example: structures, enumerations and unions.
102
102
///
103
- /// InternalSubsts here, possibly against intuition, *may* contain `Param`s.
104
- /// That is, even after substitution it is possible that there are type
105
- /// variables. This happens when the `Adt` corresponds to an ADT
106
- /// definition and not a concrete use of it.
103
+ /// For example, the type `List<i32>` would be represented using the `AdtDef`
104
+ /// for `struct List<T>` and the substs `[i32]`.
105
+ ///
106
+ /// Note that generic parameters in fields only get lazily substituted
107
+ /// by using something like `adt_def.all_fields().map(|field| field.ty(tcx, substs))`.
107
108
Adt ( & ' tcx AdtDef , SubstsRef < ' tcx > ) ,
108
109
109
110
/// An unsized FFI type that is opaque to Rust. Written as `extern type T`.
@@ -112,7 +113,7 @@ pub enum TyKind<'tcx> {
112
113
/// The pointee of a string slice. Written as `str`.
113
114
Str ,
114
115
115
- /// An array with the given length. Written as `[T; n ]`.
116
+ /// An array with the given length. Written as `[T; N ]`.
116
117
Array ( Ty < ' tcx > , & ' tcx ty:: Const < ' tcx > ) ,
117
118
118
119
/// The pointee of an array slice. Written as `[T]`.
@@ -126,11 +127,12 @@ pub enum TyKind<'tcx> {
126
127
Ref ( Region < ' tcx > , Ty < ' tcx > , hir:: Mutability ) ,
127
128
128
129
/// The anonymous type of a function declaration/definition. Each
129
- /// function has a unique type, which is output (for a function
130
- /// named `foo` returning an `i32`) as `fn() -> i32 {foo}`.
130
+ /// function has a unique type.
131
131
///
132
- /// For example the type of `bar` here:
132
+ /// For the function `fn foo() -> i32 { 3 }` this type would be
133
+ /// shown to the user as `fn() -> i32 {foo}`.
133
134
///
135
+ /// For example the type of `bar` here:
134
136
/// ```rust
135
137
/// fn foo() -> i32 { 1 }
136
138
/// let bar = foo; // bar: fn() -> i32 {foo}
@@ -139,6 +141,9 @@ pub enum TyKind<'tcx> {
139
141
140
142
/// A pointer to a function. Written as `fn() -> i32`.
141
143
///
144
+ /// Note that both functions and closures start out as either
145
+ /// [FnDef] or [Closure] which can be then be coerced to this variant.
146
+ ///
142
147
/// For example the type of `bar` here:
143
148
///
144
149
/// ```rust
@@ -150,17 +155,41 @@ pub enum TyKind<'tcx> {
150
155
/// A trait object. Written as `dyn for<'b> Trait<'b, Assoc = u32> + Send + 'a`.
151
156
Dynamic ( & ' tcx List < Binder < ' tcx , ExistentialPredicate < ' tcx > > > , ty:: Region < ' tcx > ) ,
152
157
153
- /// The anonymous type of a closure. Used to represent the type of
154
- /// `|a| a`.
155
- /// For the order of the substs see the `ClosureSubsts` type's documentation.
158
+ /// The anonymous type of a closure. Used to represent the type of `|a| a`.
159
+ ///
160
+ /// Closure substs contain both the - potentially substituted - generic parameters
161
+ /// of its parent and some synthetic parameters. See the documentation for
162
+ /// [ClosureSubsts] for more details.
156
163
Closure ( DefId , SubstsRef < ' tcx > ) ,
157
164
158
165
/// The anonymous type of a generator. Used to represent the type of
159
166
/// `|a| yield a`.
167
+ ///
168
+ /// For more info about generator substs, visit the documentation for
169
+ /// [GeneratorSubsts].
160
170
Generator ( DefId , SubstsRef < ' tcx > , hir:: Movability ) ,
161
171
162
172
/// A type representing the types stored inside a generator.
163
- /// This should only appear in GeneratorInteriors.
173
+ /// This should only appear as part of the [GeneratorSubsts].
174
+ ///
175
+ /// Note that the captured variables for generators are stored separately
176
+ /// using a tuple in the same way as for closures.
177
+ ///
178
+ /// Unlike upvars, the witness can reference lifetimes from
179
+ /// inside of the generator itself. To deal with them in
180
+ /// the type of the generator, we convert them to higher ranked
181
+ /// lifetimes bound by the witness itself.
182
+ ///
183
+ /// Looking at the following example, the witness for this generator
184
+ /// may end up as something like `for<'a> [Vec<i32>, &'a Vec<i32>]`:
185
+ ///
186
+ /// ```rust
187
+ /// |a| {
188
+ /// let x = &vec![3];
189
+ /// yield a;
190
+ /// yield x[0];
191
+ /// }
192
+ /// ```
164
193
GeneratorWitness ( Binder < ' tcx , & ' tcx List < Ty < ' tcx > > > ) ,
165
194
166
195
/// The never type `!`.
@@ -175,23 +204,44 @@ pub enum TyKind<'tcx> {
175
204
Projection ( ProjectionTy < ' tcx > ) ,
176
205
177
206
/// Opaque (`impl Trait`) type found in a return type.
207
+ ///
178
208
/// The `DefId` comes either from
179
209
/// * the `impl Trait` ast::Ty node,
180
210
/// * or the `type Foo = impl Trait` declaration
181
- /// The substitutions are for the generics of the function in question.
182
- /// After typeck, the concrete type can be found in the `types` map.
211
+ ///
212
+ /// For RPIT the substitutions are for the generics of the function,
213
+ /// while for TAIT it is used for the generic parameters of the alias.
214
+ ///
215
+ /// During codegen, `tcx.type_of(def_id)` can be used to get the underlying type.
183
216
Opaque ( DefId , SubstsRef < ' tcx > ) ,
184
217
185
218
/// A type parameter; for example, `T` in `fn f<T>(x: T) {}`.
186
219
Param ( ParamTy ) ,
187
220
188
- /// Bound type variable, used only when preparing a trait query.
221
+ /// Bound type variable, used to represent the `'a` in `for<'a> fn(&'a ())`.
222
+ ///
223
+ /// For canonical queries, we replace inference variables with bound variables,
224
+ /// so e.g. when checking whether `&'_ (): Trait<_>` holds, we canonicalize that to
225
+ /// `for<'a, T> &'a (): Trait<T>` and then convert the introduced bound variables
226
+ /// back to inference variables in a new inference context when inside of the query.
227
+ ///
228
+ /// See the `rustc-dev-guide` for more details about
229
+ /// [higher-ranked trait bounds][1] and [canonical queries][2].
230
+ ///
231
+ /// [1]: https://rustc-dev-guide.rust-lang.org/traits/hrtb.html
232
+ /// [2]: https://rustc-dev-guide.rust-lang.org/traits/canonical-queries.html
189
233
Bound ( ty:: DebruijnIndex , BoundTy ) ,
190
234
191
- /// A placeholder type - universally quantified higher-ranked type.
235
+ /// A placeholder type, used during higher ranked subtyping to instantiate
236
+ /// bound variables.
192
237
Placeholder ( ty:: PlaceholderType ) ,
193
238
194
239
/// A type variable used during type checking.
240
+ ///
241
+ /// Similar to placeholders, inference variables also live in a universe to
242
+ /// correctly deal with higher ranked types. Though unlike placeholders,
243
+ /// that universe is stored in the `InferCtxt` instead of directly
244
+ /// inside of the type.
195
245
Infer ( InferTy ) ,
196
246
197
247
/// A placeholder for a type which could not be computed; this is
0 commit comments