@@ -93,6 +93,11 @@ pub enum ImplExprAtom {
93
93
/// `dyn Trait` implements `Trait` using a built-in implementation; this refers to that
94
94
/// built-in implementation.
95
95
Dyn ,
96
+ /// A virtual `Drop` implementation.
97
+ /// `Drop` doesn't work like a real trait but we want to pretend it does. If a type has a
98
+ /// user-defined `impl Drop for X` we just use the `Concrete` variant, but if it doesn't we use
99
+ /// this variant to supply the data needed to know what code will run on drop.
100
+ Drop ( DropData ) ,
96
101
/// A built-in trait whose implementation is computed by the compiler, such as `FnMut`. This
97
102
/// morally points to an invisible `impl` block; as such it contains the information we may
98
103
/// need from one.
@@ -109,6 +114,30 @@ pub enum ImplExprAtom {
109
114
Error ( String ) ,
110
115
}
111
116
117
+ #[ derive( AdtInto ) ]
118
+ #[ args( <' tcx, S : UnderOwnerState <' tcx> >, from: resolution:: DropData <' tcx>, state: S as s) ]
119
+ #[ derive_group( Serializers ) ]
120
+ #[ derive( Clone , Debug , Hash , PartialEq , Eq , PartialOrd , Ord , JsonSchema ) ]
121
+ pub enum DropData {
122
+ /// A drop that does nothing, e.g. for scalars and pointers.
123
+ Noop ,
124
+ /// An implicit `Drop` local clause, if the `resolve_drop_bounds` option is `false`. If that
125
+ /// option is `true`, we'll add `Drop` bounds to every type param, and use that to resolve
126
+ /// `Drop` impls of generics. If it's `false`, we use this variant to indicate that the drop
127
+ /// clause comes from a generic or associated type.
128
+ Implicit ,
129
+ /// The implicit `Drop` impl that exists for every type without an explicit `Drop` impl. The
130
+ /// virtual impl is considered to have one `T: Drop` bound for each generic argument of the
131
+ /// target type; it then simply drops each field in order.
132
+ Glue {
133
+ /// The type we're generating glue for.
134
+ ty : Ty ,
135
+ /// The `ImplExpr`s for the `T: Drop` bounds of the virtual impl. There is one for each
136
+ /// generic argument, in order.
137
+ impl_exprs : Vec < ImplExpr > ,
138
+ } ,
139
+ }
140
+
112
141
/// An `ImplExpr` describes the full data of a trait implementation. Because of generics, this may
113
142
/// need to combine several concrete trait implementation items. For example, `((1u8, 2u8),
114
143
/// "hello").clone()` combines the generic implementation of `Clone` for `(A, B)` with the
@@ -173,7 +202,13 @@ pub fn solve_trait<'tcx, S: BaseState<'tcx> + HasOwnerId>(
173
202
let resolved = s. with_cache ( |cache| {
174
203
cache
175
204
. predicate_searcher
176
- . get_or_insert_with ( || PredicateSearcher :: new_for_owner ( s. base ( ) . tcx , s. owner_id ( ) ) )
205
+ . get_or_insert_with ( || {
206
+ PredicateSearcher :: new_for_owner (
207
+ s. base ( ) . tcx ,
208
+ s. owner_id ( ) ,
209
+ s. base ( ) . options . resolve_drop_bounds ,
210
+ )
211
+ } )
177
212
. resolve ( & trait_ref, & warn)
178
213
} ) ;
179
214
let impl_expr = match resolved {
@@ -209,7 +244,7 @@ pub fn solve_item_required_traits<'tcx, S: UnderOwnerState<'tcx>>(
209
244
}
210
245
_ => { }
211
246
}
212
- let predicates = required_predicates ( tcx, def_id) ;
247
+ let predicates = required_predicates ( tcx, def_id, s . base ( ) . options . resolve_drop_bounds ) ;
213
248
impl_exprs. extend ( solve_item_traits_inner ( s, generics, predicates) ) ;
214
249
}
215
250
let mut impl_exprs = vec ! [ ] ;
@@ -226,7 +261,7 @@ pub fn solve_item_implied_traits<'tcx, S: UnderOwnerState<'tcx>>(
226
261
def_id : RDefId ,
227
262
generics : ty:: GenericArgsRef < ' tcx > ,
228
263
) -> Vec < ImplExpr > {
229
- let predicates = implied_predicates ( s. base ( ) . tcx , def_id) ;
264
+ let predicates = implied_predicates ( s. base ( ) . tcx , def_id, s . base ( ) . options . resolve_drop_bounds ) ;
230
265
solve_item_traits_inner ( s, generics, predicates)
231
266
}
232
267
0 commit comments