@@ -189,7 +189,10 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
189
189
return Ok ( val) ;
190
190
}
191
191
let lvalue = self . eval_lvalue ( lvalue) ?;
192
+ self . read_lvalue ( lvalue, ty)
193
+ }
192
194
195
+ fn read_lvalue ( & self , lvalue : Lvalue < ' tcx > , ty : Ty < ' tcx > ) -> EvalResult < ' tcx , Value > {
193
196
if ty. is_never ( ) {
194
197
return Err ( EvalError :: Unreachable ) ;
195
198
}
@@ -219,7 +222,11 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
219
222
Lvalue :: Global ( GlobalId { instance, promoted : None } )
220
223
}
221
224
222
- Projection ( ref proj) => return self . eval_lvalue_projection ( proj) ,
225
+ Projection ( ref proj) => {
226
+ let ty = self . lvalue_ty ( & proj. base ) ;
227
+ let lvalue = self . eval_lvalue ( & proj. base ) ?;
228
+ return self . eval_lvalue_projection ( lvalue, ty, & proj. elem ) ;
229
+ }
223
230
} ;
224
231
225
232
if log_enabled ! ( :: log:: LogLevel :: Trace ) {
@@ -348,19 +355,17 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
348
355
349
356
fn eval_lvalue_projection (
350
357
& mut self ,
351
- proj : & mir:: LvalueProjection < ' tcx > ,
358
+ base : Lvalue < ' tcx > ,
359
+ base_ty : Ty < ' tcx > ,
360
+ proj_elem : & mir:: ProjectionElem < ' tcx , mir:: Operand < ' tcx > > ,
352
361
) -> EvalResult < ' tcx , Lvalue < ' tcx > > {
353
362
use rustc:: mir:: ProjectionElem :: * ;
354
- let ( ptr, extra, aligned) = match proj . elem {
363
+ let ( ptr, extra, aligned) = match * proj_elem {
355
364
Field ( field, field_ty) => {
356
- let base = self . eval_lvalue ( & proj. base ) ?;
357
- let base_ty = self . lvalue_ty ( & proj. base ) ;
358
365
return self . lvalue_field ( base, field. index ( ) , base_ty, field_ty) ;
359
366
}
360
367
361
368
Downcast ( _, variant) => {
362
- let base = self . eval_lvalue ( & proj. base ) ?;
363
- let base_ty = self . lvalue_ty ( & proj. base ) ;
364
369
let base_layout = self . type_layout ( base_ty) ?;
365
370
// FIXME(solson)
366
371
let base = self . force_allocation ( base) ?;
@@ -376,8 +381,7 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
376
381
}
377
382
378
383
Deref => {
379
- let base_ty = self . lvalue_ty ( & proj. base ) ;
380
- let val = self . eval_and_read_lvalue ( & proj. base ) ?;
384
+ let val = self . read_lvalue ( base, base_ty) ?;
381
385
382
386
let pointee_type = match base_ty. sty {
383
387
ty:: TyRawPtr ( ref tam) |
@@ -402,8 +406,6 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
402
406
}
403
407
404
408
Index ( ref operand) => {
405
- let base = self . eval_lvalue ( & proj. base ) ?;
406
- let base_ty = self . lvalue_ty ( & proj. base ) ;
407
409
// FIXME(solson)
408
410
let base = self . force_allocation ( base) ?;
409
411
let ( base_ptr, _, aligned) = base. to_ptr_extra_aligned ( ) ;
@@ -419,8 +421,6 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
419
421
}
420
422
421
423
ConstantIndex { offset, min_length, from_end } => {
422
- let base = self . eval_lvalue ( & proj. base ) ?;
423
- let base_ty = self . lvalue_ty ( & proj. base ) ;
424
424
// FIXME(solson)
425
425
let base = self . force_allocation ( base) ?;
426
426
let ( base_ptr, _, aligned) = base. to_ptr_extra_aligned ( ) ;
@@ -440,8 +440,6 @@ impl<'a, 'tcx> EvalContext<'a, 'tcx> {
440
440
}
441
441
442
442
Subslice { from, to } => {
443
- let base = self . eval_lvalue ( & proj. base ) ?;
444
- let base_ty = self . lvalue_ty ( & proj. base ) ;
445
443
// FIXME(solson)
446
444
let base = self . force_allocation ( base) ?;
447
445
let ( base_ptr, _, aligned) = base. to_ptr_extra_aligned ( ) ;
0 commit comments