@@ -39,9 +39,38 @@ pub enum TypingMode<I: Interner> {
3939 ///
4040 /// We only normalize opaque types which may get defined by the current body,
4141 /// which are stored in `defining_opaque_types`.
42+ ///
43+ /// We also refuse to project any associated type that is marked `default`.
44+ /// Non-`default` ("final") types are always projected. This is necessary in
45+ /// general for soundness of specialization. However, we *could* allow projections
46+ /// in fully-monomorphic cases. We choose not to, because we prefer for `default type`
47+ /// to force the type definition to be treated abstractly by any consumers of the
48+ /// impl. Concretely, that means that the following example will
49+ /// fail to compile:
50+ ///
51+ /// ```compile_fail,E0308
52+ /// #![feature(specialization)]
53+ /// trait Assoc {
54+ /// type Output;
55+ /// }
56+ ///
57+ /// impl<T> Assoc for T {
58+ /// default type Output = bool;
59+ /// }
60+ ///
61+ /// fn main() {
62+ /// let x: <() as Assoc>::Output = true;
63+ /// }
64+ /// ```
4265 Analysis { defining_opaque_types : I :: DefiningOpaqueTypes } ,
4366 /// After analysis, mostly during codegen and MIR optimizations, we're able to
44- /// reveal all opaque types.
67+ /// reveal all opaque types. As the concrete type should *never* be observable
68+ /// directly by the user, this should not be used by checks which may expose
69+ /// such details to the user.
70+ ///
71+ /// There are some exceptions to this as for example `layout_of` and const-evaluation
72+ /// always run in `PostAnalysis` mode, even when used during analysis. This exposes
73+ /// some information about the underlying type to users, but not the type itself.
4574 PostAnalysis ,
4675}
4776
0 commit comments