[−][src]Function rustc_typeck::check::upvar::determine_capture_info
pub(in check::upvar) fn determine_capture_info<'tcx>(
capture_info_a: CaptureInfo<'tcx>,
capture_info_b: CaptureInfo<'tcx>
) -> CaptureInfo<'tcx>
Helper function to determine if we need to escalate CaptureKind from CaptureInfo A to B and returns the escalated CaptureInfo. (Note: CaptureInfo contains CaptureKind and an expression that led to capture it in that way)
If both CaptureKinds are considered equivalent, then the CaptureInfo is selected based
on the CaptureInfo containing an associated expression id.
If both the CaptureKind and Expression are considered to be equivalent,
then CaptureInfo A is preferred. This can be useful in cases where we want to priortize
expressions reported back to the user as part of diagnostics based on which appears earlier
in the closure. This can be acheived simply by calling
determine_capture_info(existing_info, current_info). This works out because the
expressions that occur earlier in the closure body than the current expression are processed before.
Consider the following example
struct Point { x: i32, y: i32 } let mut p: Point { x: 10, y: 10 }; let c = || { p.x += 10; // ^ E1 ^ // ... // More code // ... p.x += 10; // E2 // ^ E2 ^ };
CaptureKind associated with both E1 and E2 will be ByRef(MutBorrow),
and both have an expression associated, however for diagnostics we prefer reporting
E1 since it appears earlier in the closure body. When E2 is being processed we
would've already handled E1, and have an existing capture_information for it.
Calling determine_capture_info(existing_info_e1, current_info_e2) will return
existing_info_e1 in this case, allowing us to point to E1 in case of diagnostics.