diff --git a/src/librustc_mir/interpret/eval_context.rs b/src/librustc_mir/interpret/eval_context.rs index 6497e211de3..b44152a5188 100644 --- a/src/librustc_mir/interpret/eval_context.rs +++ b/src/librustc_mir/interpret/eval_context.rs @@ -171,15 +171,8 @@ impl<'mir, 'tcx, Tag> Frame<'mir, 'tcx, Tag> { impl<'mir, 'tcx, Tag, Extra> Frame<'mir, 'tcx, Tag, Extra> { /// Return the `SourceInfo` of the current instruction. - pub fn current_source_info(&self) -> Option { - self.loc.map(|loc| { - let block = &self.body.basic_blocks()[loc.block]; - if loc.statement_index < block.statements.len() { - block.statements[loc.statement_index].source_info - } else { - block.terminator().source_info - } - }) + pub fn current_source_info(&self) -> Option<&mir::SourceInfo> { + self.loc.map(|loc| self.body.source_info(loc)) } } diff --git a/src/librustc_mir/interpret/intrinsics/caller_location.rs b/src/librustc_mir/interpret/intrinsics/caller_location.rs index ddeed92f851..9adef8c43c7 100644 --- a/src/librustc_mir/interpret/intrinsics/caller_location.rs +++ b/src/librustc_mir/interpret/intrinsics/caller_location.rs @@ -29,18 +29,25 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> { }) // Assert that there is always such a frame. .unwrap(); + // Assert that the frame we look at is actually executing code currently + // (`current_source_info` is None when we are unwinding and the frame does + // not require cleanup). let loc = frame.loc.unwrap(); + // If this is a `Call` terminator, use the `fn_span` instead. let block = &frame.body.basic_blocks()[loc.block]; - assert_eq!(block.statements.len(), loc.statement_index); - debug!( - "find_closest_untracked_caller_location:: got terminator {:?} ({:?})", - block.terminator(), - block.terminator().kind - ); - if let TerminatorKind::Call { fn_span, .. } = block.terminator().kind { - return fn_span; + if loc.statement_index == block.statements.len() { + debug!( + "find_closest_untracked_caller_location:: got terminator {:?} ({:?})", + block.terminator(), + block.terminator().kind + ); + if let TerminatorKind::Call { fn_span, .. } = block.terminator().kind { + return fn_span; + } } - unreachable!(); + // This is a different terminator (such as `Drop`) or not a terminator at all + // (such as `box`). Use the normal span. + frame.body.source_info(loc).span } /// Allocate a `const core::panic::Location` with the provided filename and line/column numbers.