@@ -189,12 +189,11 @@ fn reconstruct_place_meta<'tcx>(
189189}
190190
191191#[ instrument( skip( ecx) , level = "debug" , ret) ]
192- fn create_pointee_place < ' tcx > (
192+ fn create_valtree_place < ' tcx > (
193193 ecx : & mut CompileTimeEvalContext < ' tcx , ' tcx > ,
194- ty : Ty < ' tcx > ,
194+ layout : TyAndLayout < ' tcx > ,
195195 valtree : ty:: ValTree < ' tcx > ,
196196) -> MPlaceTy < ' tcx > {
197- let layout = ecx. layout_of ( ty) . unwrap ( ) ;
198197 let meta = reconstruct_place_meta ( layout, valtree, ecx. tcx . tcx ) ;
199198 ecx. allocate_dyn ( layout, MemoryKind :: Stack , meta) . unwrap ( )
200199}
@@ -216,11 +215,6 @@ pub fn valtree_to_const_value<'tcx>(
216215 // FIXME Does this need an example?
217216
218217 let ( param_env, ty) = param_env_ty. into_parts ( ) ;
219- let mut ecx: crate :: interpret:: InterpCx <
220- ' _ ,
221- ' _ ,
222- crate :: const_eval:: CompileTimeInterpreter < ' _ , ' _ > ,
223- > = mk_eval_cx ( tcx, DUMMY_SP , param_env, CanAccessStatics :: No ) ;
224218
225219 match ty. kind ( ) {
226220 ty:: FnDef ( ..) => {
@@ -233,33 +227,29 @@ pub fn valtree_to_const_value<'tcx>(
233227 "ValTrees for Bool, Int, Uint, Float or Char should have the form ValTree::Leaf"
234228 ) ,
235229 } ,
236- ty:: Ref ( _, _, _) | ty:: Tuple ( _) | ty:: Array ( _, _) | ty:: Adt ( ..) => {
237- let place = match ty. kind ( ) {
238- ty:: Ref ( _, inner_ty, _) => {
239- // Need to create a place for the pointee (the reference itself will be an immediate)
240- create_pointee_place ( & mut ecx, * inner_ty, valtree)
241- }
242- _ => {
243- // Need to create a place for this valtree.
244- create_pointee_place ( & mut ecx, ty, valtree)
245- }
246- } ;
247- debug ! ( ?place) ;
230+ ty:: Ref ( _, inner_ty, _) => {
231+ let mut ecx = mk_eval_cx ( tcx, DUMMY_SP , param_env, CanAccessStatics :: No ) ;
232+ let imm = valtree_to_ref ( & mut ecx, valtree, * inner_ty) ;
233+ let imm = ImmTy :: from_immediate ( imm, tcx. layout_of ( param_env_ty) . unwrap ( ) ) ;
234+ op_to_const ( & ecx, & imm. into ( ) )
235+ }
236+ ty:: Tuple ( _) | ty:: Array ( _, _) | ty:: Adt ( ..) => {
237+ let layout = tcx. layout_of ( param_env_ty) . unwrap ( ) ;
238+ if layout. is_zst ( ) {
239+ // Fast path to avoid some allocations.
240+ return ConstValue :: ZeroSized ;
241+ }
242+
243+ let mut ecx = mk_eval_cx ( tcx, DUMMY_SP , param_env, CanAccessStatics :: No ) ;
244+
245+ // Need to create a place for this valtree.
246+ let place = create_valtree_place ( & mut ecx, layout, valtree) ;
248247
249248 valtree_into_mplace ( & mut ecx, & place, valtree) ;
250249 dump_place ( & ecx, & place) ;
251250 intern_const_alloc_recursive ( & mut ecx, InternKind :: Constant , & place) . unwrap ( ) ;
252251
253- match ty. kind ( ) {
254- ty:: Ref ( _, _, _) => {
255- let ref_place = place. to_ref ( & tcx) ;
256- let imm =
257- ImmTy :: from_immediate ( ref_place, tcx. layout_of ( param_env_ty) . unwrap ( ) ) ;
258-
259- op_to_const ( & ecx, & imm. into ( ) )
260- }
261- _ => op_to_const ( & ecx, & place. into ( ) ) ,
262- }
252+ op_to_const ( & ecx, & place. into ( ) )
263253 }
264254 ty:: Never
265255 | ty:: Error ( _)
@@ -283,6 +273,22 @@ pub fn valtree_to_const_value<'tcx>(
283273 }
284274}
285275
276+ /// Put a valtree into memory and return a reference to that.
277+ fn valtree_to_ref < ' tcx > (
278+ ecx : & mut CompileTimeEvalContext < ' tcx , ' tcx > ,
279+ valtree : ty:: ValTree < ' tcx > ,
280+ pointee_ty : Ty < ' tcx > ,
281+ ) -> Immediate {
282+ let pointee_place = create_valtree_place ( ecx, ecx. layout_of ( pointee_ty) . unwrap ( ) , valtree) ;
283+ debug ! ( ?pointee_place) ;
284+
285+ valtree_into_mplace ( ecx, & pointee_place, valtree) ;
286+ dump_place ( ecx, & pointee_place) ;
287+ intern_const_alloc_recursive ( ecx, InternKind :: Constant , & pointee_place) . unwrap ( ) ;
288+
289+ pointee_place. to_ref ( & ecx. tcx )
290+ }
291+
286292#[ instrument( skip( ecx) , level = "debug" ) ]
287293fn valtree_into_mplace < ' tcx > (
288294 ecx : & mut CompileTimeEvalContext < ' tcx , ' tcx > ,
@@ -292,7 +298,6 @@ fn valtree_into_mplace<'tcx>(
292298 // This will match on valtree and write the value(s) corresponding to the ValTree
293299 // inside the place recursively.
294300
295- let tcx = ecx. tcx . tcx ;
296301 let ty = place. layout . ty ;
297302
298303 match ty. kind ( ) {
@@ -305,27 +310,8 @@ fn valtree_into_mplace<'tcx>(
305310 ecx. write_immediate ( Immediate :: Scalar ( scalar_int. into ( ) ) , place) . unwrap ( ) ;
306311 }
307312 ty:: Ref ( _, inner_ty, _) => {
308- let pointee_place = create_pointee_place ( ecx, * inner_ty, valtree) ;
309- debug ! ( ?pointee_place) ;
310-
311- valtree_into_mplace ( ecx, & pointee_place, valtree) ;
312- dump_place ( ecx, & pointee_place) ;
313- intern_const_alloc_recursive ( ecx, InternKind :: Constant , & pointee_place) . unwrap ( ) ;
314-
315- let imm = match inner_ty. kind ( ) {
316- ty:: Slice ( _) | ty:: Str => {
317- let len = valtree. unwrap_branch ( ) . len ( ) ;
318- let len_scalar = Scalar :: from_target_usize ( len as u64 , & tcx) ;
319-
320- Immediate :: ScalarPair (
321- Scalar :: from_maybe_pointer ( pointee_place. ptr ( ) , & tcx) ,
322- len_scalar,
323- )
324- }
325- _ => pointee_place. to_ref ( & tcx) ,
326- } ;
313+ let imm = valtree_to_ref ( ecx, valtree, * inner_ty) ;
327314 debug ! ( ?imm) ;
328-
329315 ecx. write_immediate ( imm, place) . unwrap ( ) ;
330316 }
331317 ty:: Adt ( _, _) | ty:: Tuple ( _) | ty:: Array ( _, _) | ty:: Str | ty:: Slice ( _) => {
0 commit comments