Skip to content

Commit d518dcf

Browse files
committed
various minor cleanups
1 parent 614f446 commit d518dcf

File tree

3 files changed

+67
-60
lines changed

3 files changed

+67
-60
lines changed

src/borrow_tracker/tree_borrows/mod.rs

Lines changed: 35 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@ use rustc_middle::mir::{Mutability, RetagKind};
33
use rustc_middle::ty::layout::HasTypingEnv;
44
use rustc_middle::ty::{self, Ty};
55

6-
use self::tree::LocationState;
76
use crate::borrow_tracker::{GlobalState, GlobalStateInner, ProtectorKind};
87
use crate::concurrency::data_race::NaReadType;
98
use crate::*;
@@ -216,8 +215,6 @@ trait EvalContextPrivExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
216215
new_perm: NewPermission,
217216
new_tag: BorTag,
218217
) -> InterpResult<'tcx, Option<Provenance>> {
219-
// Make sure the new permissions make sense as the initial permissions of a fresh tag.
220-
assert!(new_perm.freeze_perm.is_initial() && new_perm.nonfreeze_perm.is_initial());
221218
let this = self.eval_context_mut();
222219
// Ensure we bail out if the pointer goes out-of-bounds (see miri#1050).
223220
this.check_ptr_access(place.ptr(), ptr_size, CheckInAllocMsg::Dereferenceable)?;
@@ -315,76 +312,81 @@ trait EvalContextPrivExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
315312
let span = this.machine.current_span();
316313
let alloc_extra = this.get_alloc_extra(alloc_id)?;
317314
let mut tree_borrows = alloc_extra.borrow_tracker_tb().borrow_mut();
318-
let prot = new_perm.protector.is_some();
319315

320316
// Store initial permissions and their corresponding range.
321-
let mut perms_map: RangeMap<LocationState> = RangeMap::new(
317+
let mut perms_map: RangeMap<Permission> = RangeMap::new(
322318
ptr_size,
323-
LocationState::new_uninit(
324-
Permission::new_disabled(),
325-
foreign_access_skipping::IdempotentForeignAccess::None,
326-
),
319+
Permission::new_disabled(), // this will be overwritten
327320
);
328321
// Keep track of whether the node has any part that allows for interior mutability.
322+
// FIXME: This misses `PhantomData<UnsafeCell<T>>` which could be considered a marker
323+
// for requesting interior mutability.
329324
let mut has_unsafe_cell = false;
330325

331326
this.visit_freeze_sensitive(place, ptr_size, |range, frozen| {
332327
has_unsafe_cell = has_unsafe_cell || !frozen;
333328

334-
// Adjust range.
335-
let mut range_with_offset = range;
336-
range_with_offset.start += base_offset;
337-
338329
// We are only ever `Frozen` inside the frozen bits.
339-
let (perm, access) = if frozen {
330+
let (perm_init, access) = if frozen {
340331
(new_perm.freeze_perm, new_perm.freeze_access)
341332
} else {
342333
(new_perm.nonfreeze_perm, new_perm.nonfreeze_access)
343334
};
344-
let strongest_idempotent = perm.strongest_idempotent_foreign_access(prot);
345335

346336
// Store initial permissions.
347-
let perm_init = LocationState::new_init(perm, strongest_idempotent);
348337
for (_perm_range, perm) in perms_map.iter_mut(range.start, range.size) {
349338
*perm = perm_init;
350339
}
351340

352341
// Some reborrows incur a read access to the parent.
353342
if access {
343+
// Adjust range to be relative to allocation start (rather than to `place`).
344+
let mut range_in_alloc = range;
345+
range_in_alloc.start += base_offset;
346+
354347
tree_borrows.perform_access(
355348
orig_tag,
356-
Some((range_with_offset, AccessKind::Read, diagnostics::AccessCause::Reborrow)),
349+
Some((range_in_alloc, AccessKind::Read, diagnostics::AccessCause::Reborrow)),
357350
this.machine.borrow_tracker.as_ref().unwrap(),
358351
alloc_id,
359352
this.machine.current_span(),
360-
)?
361-
}
362-
363-
// Also inform the data race model (but only if any bytes are actually affected).
364-
if range.size.bytes() > 0 && access {
365-
if let Some(data_race) = alloc_extra.data_race.as_vclocks_ref() {
366-
data_race.read(
367-
alloc_id,
368-
range_with_offset,
369-
NaReadType::Retag,
370-
Some(place.layout.ty),
371-
&this.machine,
372-
)?
353+
)?;
354+
355+
// Also inform the data race model (but only if any bytes are actually affected).
356+
if range.size.bytes() > 0 {
357+
if let Some(data_race) = alloc_extra.data_race.as_vclocks_ref() {
358+
data_race.read(
359+
alloc_id,
360+
range_in_alloc,
361+
NaReadType::Retag,
362+
Some(place.layout.ty),
363+
&this.machine,
364+
)?
365+
}
373366
}
374367
}
375368
interp_ok(())
376369
})?;
377370

371+
// SIFA of the frozen part must be weaker than SIFA of the non-frozen part, otherwise
372+
// `self.update_last_accessed_after_retag` will break the SIFA invariant (see `foreign_access_skipping.rs`).
373+
assert!(
374+
new_perm.freeze_perm.strongest_idempotent_foreign_access(new_perm.protector.is_some())
375+
<= new_perm
376+
.nonfreeze_perm
377+
.strongest_idempotent_foreign_access(new_perm.protector.is_some())
378+
);
379+
378380
// Record the parent-child pair in the tree.
379381
tree_borrows.new_child(
380-
ptr_size,
381382
base_offset,
382383
orig_tag,
383384
new_tag,
384-
new_perm,
385385
perms_map,
386+
// Allow lazily writing to surrounding data if we found an `UnsafeCell`.
387+
if has_unsafe_cell { new_perm.nonfreeze_perm } else { new_perm.freeze_perm },
388+
new_perm.protector.is_some(),
386389
span,
387-
has_unsafe_cell,
388390
)?;
389391
drop(tree_borrows);
390392

src/borrow_tracker/tree_borrows/tree.rs

Lines changed: 26 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@ use rustc_data_structures::fx::FxHashSet;
1818
use rustc_span::Span;
1919
use smallvec::SmallVec;
2020

21-
use super::NewPermission;
2221
use crate::borrow_tracker::tree_borrows::Permission;
2322
use crate::borrow_tracker::tree_borrows::diagnostics::{
2423
self, NodeDebugInfo, TbError, TransitionError,
@@ -614,61 +613,65 @@ impl Tree {
614613
}
615614

616615
impl<'tcx> Tree {
617-
/// Insert a new tag in the tree
616+
/// Insert a new tag in the tree.
617+
///
618+
/// `initial_perms` defines the initial permissions for the part of memory
619+
/// that is already considered "initialized" immediately. The ranges in this
620+
/// map are relative to `base_offset`.
621+
/// `default_perm` defines the initial permission for the rest of the allocation.
618622
pub(super) fn new_child(
619623
&mut self,
620-
size: Size,
621624
base_offset: Size,
622625
parent_tag: BorTag,
623626
new_tag: BorTag,
624-
perm: NewPermission,
625-
perms_map: RangeMap<LocationState>,
627+
init_perms: RangeMap<Permission>,
628+
default_uninit_perm: Permission,
629+
protected: bool,
626630
span: Span,
627-
has_unsafe_cell: bool,
628631
) -> InterpResult<'tcx> {
629632
let idx = self.tag_mapping.insert(new_tag);
630633
let parent_idx = self.tag_mapping.get(&parent_tag).unwrap();
631-
// Allow lazily writing to surrounding data if we have a reference to interior mutable data.
632-
let default_initial_perm =
633-
if has_unsafe_cell { perm.nonfreeze_perm } else { perm.freeze_perm };
634-
let prot = perm.protector.is_some();
634+
assert!(default_uninit_perm.is_initial());
635635

636-
// SIFA of the frozen part must be weaker than SIFA of the non-frozen part, otherwise
637-
// `self.update_last_accessed_after_retag` will break the SIFA invariant (see `foreign_access_skipping.rs`).
638-
assert!(
639-
perm.freeze_perm.strongest_idempotent_foreign_access(prot)
640-
<= perm.nonfreeze_perm.strongest_idempotent_foreign_access(prot)
641-
);
642-
let strongest_idempotent = default_initial_perm.strongest_idempotent_foreign_access(prot);
636+
let default_strongest_idempotent =
637+
default_uninit_perm.strongest_idempotent_foreign_access(protected);
643638
// Create the node
644639
self.nodes.insert(
645640
idx,
646641
Node {
647642
tag: new_tag,
648643
parent: Some(parent_idx),
649644
children: SmallVec::default(),
650-
default_initial_perm,
651-
default_initial_idempotent_foreign_access: strongest_idempotent,
652-
debug_info: NodeDebugInfo::new(new_tag, default_initial_perm, span),
645+
default_initial_perm: default_uninit_perm,
646+
default_initial_idempotent_foreign_access: default_strongest_idempotent,
647+
debug_info: NodeDebugInfo::new(new_tag, default_uninit_perm, span),
653648
},
654649
);
655650
// Register new_tag as a child of parent_tag
656651
self.nodes.get_mut(parent_idx).unwrap().children.push(idx);
657652

658-
for (Range { start, end }, &perm) in perms_map.iter(Size::from_bytes(0), size) {
653+
for (Range { start, end }, &perm) in init_perms.iter(Size::from_bytes(0), init_perms.size())
654+
{
655+
assert!(perm.is_initial());
659656
for (_perms_range, perms) in self
660657
.rperms
661658
.iter_mut(Size::from_bytes(start) + base_offset, Size::from_bytes(end - start))
662659
{
663-
perms.insert(idx, perm);
660+
perms.insert(
661+
idx,
662+
LocationState::new_init(
663+
perm,
664+
perm.strongest_idempotent_foreign_access(protected),
665+
),
666+
);
664667
}
665668
}
666669

667670
// Inserting the new perms might have broken the SIFA invariant (see `foreign_access_skipping.rs`).
668671
// We now weaken the recorded SIFA for our parents, until the invariant is restored.
669672
// We could weaken them all to `LocalAccess`, but it is more efficient to compute the SIFA
670673
// for the new permission statically, and use that.
671-
self.update_last_accessed_after_retag(parent_idx, strongest_idempotent);
674+
self.update_last_accessed_after_retag(parent_idx, default_strongest_idempotent);
672675

673676
interp_ok(())
674677
}

src/range_map.rs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,11 @@ impl<T> RangeMap<T> {
3131
RangeMap { v }
3232
}
3333

34+
pub fn size(&self) -> Size {
35+
let size = self.v.last().map(|x| x.range.end).unwrap_or(0);
36+
Size::from_bytes(size)
37+
}
38+
3439
/// Finds the index containing the given offset.
3540
fn find_offset(&self, offset: u64) -> usize {
3641
self.v
@@ -71,10 +76,7 @@ impl<T> RangeMap<T> {
7176
};
7277
// The first offset that is not included any more.
7378
let end = offset + len;
74-
assert!(
75-
end <= self.v.last().map(|x| x.range.end).unwrap_or(0),
76-
"iterating beyond the bounds of this RangeMap"
77-
);
79+
assert!(end <= self.size().bytes(), "iterating beyond the bounds of this RangeMap");
7880
slice
7981
.iter()
8082
.take_while(move |elem| elem.range.start < end)

0 commit comments

Comments
 (0)