pub struct GlobalState {
multi_threaded: Cell<bool>,
ongoing_action_data_race_free: Cell<bool>,
vector_clocks: RefCell<IndexVec<VectorIdx, ThreadClockSet>>,
vector_info: RefCell<IndexVec<VectorIdx, ThreadId>>,
thread_info: RefCell<IndexVec<ThreadId, ThreadExtraState>>,
reuse_candidates: RefCell<FxHashSet<VectorIdx>>,
last_sc_fence: RefCell<VClock>,
last_sc_write_per_thread: RefCell<VClock>,
pub track_outdated_loads: bool,
}
Expand description
Global data-race detection state, contains the currently executing thread as well as the vector-clocks associated with each of the threads.
Fields§
§multi_threaded: Cell<bool>
Set to true once the first additional thread has launched, due to the dependency between before and after a thread launch. Any data-races must be recorded after this so concurrent execution can ignore recording any data-races.
ongoing_action_data_race_free: Cell<bool>
A flag to mark we are currently performing a data race free action (such as atomic access) to suppress the race detector
vector_clocks: RefCell<IndexVec<VectorIdx, ThreadClockSet>>
Mapping of a vector index to a known set of thread clocks, this is not directly mapping from a thread id since it may refer to multiple threads.
vector_info: RefCell<IndexVec<VectorIdx, ThreadId>>
Mapping of a given vector index to the current thread that the execution is representing, this may change if a vector index is re-assigned to a new thread.
thread_info: RefCell<IndexVec<ThreadId, ThreadExtraState>>
The mapping of a given thread to associated thread metadata.
reuse_candidates: RefCell<FxHashSet<VectorIdx>>
Potential vector indices that could be re-used on thread creation values are inserted here on after the thread has terminated and been joined with, and hence may potentially become free for use as the index for a new thread. Elements in this set may still require the vector index to report data-races, and can only be re-used after all active vector-clocks catch up with the threads timestamp.
last_sc_fence: RefCell<VClock>
We make SC fences act like RMWs on a global location. To implement that, they all release and acquire into this clock.
last_sc_write_per_thread: RefCell<VClock>
The timestamp of last SC write performed by each thread. Threads only update their own index here!
track_outdated_loads: bool
Track when an outdated (weak memory) load happens.
Implementations§
Source§impl GlobalState
impl GlobalState
Sourcepub fn new(config: &MiriConfig) -> Self
pub fn new(config: &MiriConfig) -> Self
Create a new global state, setup with just thread-id=0 advanced to timestamp = 1.
fn race_detecting(&self) -> bool
pub fn ongoing_action_data_race_free(&self) -> bool
fn find_vector_index_reuse_candidate(&self) -> Option<VectorIdx>
pub fn thread_created( &mut self, thread_mgr: &ThreadManager<'_>, thread: ThreadId, current_span: Span, )
Sourcepub fn thread_joined(&mut self, threads: &ThreadManager<'_>, joinee: ThreadId)
pub fn thread_joined(&mut self, threads: &ThreadManager<'_>, joinee: ThreadId)
Hook on a thread join to update the implicit happens-before relation between the joined thread (the joinee, the thread that someone waited on) and the current thread (the joiner, the thread who was waiting).
Sourcepub fn thread_terminated(&mut self, thread_mgr: &ThreadManager<'_>)
pub fn thread_terminated(&mut self, thread_mgr: &ThreadManager<'_>)
On thread termination, the vector-clock may re-used
in the future once all remaining thread-clocks catch
up with the time index of the terminated thread.
This assigns thread termination with a unique index
which will be used to join the thread
This should be called strictly before any calls to
thread_joined
.
Sourcefn maybe_perform_sync_operation<'tcx>(
&self,
thread_mgr: &ThreadManager<'_>,
current_span: Span,
op: impl FnOnce(VectorIdx, RefMut<'_, ThreadClockSet>) -> InterpResult<'tcx, bool>,
) -> InterpResult<'tcx>
fn maybe_perform_sync_operation<'tcx>( &self, thread_mgr: &ThreadManager<'_>, current_span: Span, op: impl FnOnce(VectorIdx, RefMut<'_, ThreadClockSet>) -> InterpResult<'tcx, bool>, ) -> InterpResult<'tcx>
Attempt to perform a synchronized operation, this will perform no operation if multi-threading is not currently enabled. Otherwise it will increment the clock for the current vector before and after the operation for data-race detection between any happens-before edges the operation may create.
Sourcefn print_thread_metadata(
&self,
thread_mgr: &ThreadManager<'_>,
vector: VectorIdx,
) -> String
fn print_thread_metadata( &self, thread_mgr: &ThreadManager<'_>, vector: VectorIdx, ) -> String
Internal utility to identify a thread stored internally returns the id and the name for better diagnostics.
Sourcepub fn acquire_clock<'tcx>(&self, clock: &VClock, threads: &ThreadManager<'tcx>)
pub fn acquire_clock<'tcx>(&self, clock: &VClock, threads: &ThreadManager<'tcx>)
Acquire the given clock into the current thread, establishing synchronization with
the moment when that clock snapshot was taken via release_clock
.
As this is an acquire operation, the thread timestamp is not
incremented.
Sourcepub fn release_clock<'tcx, R>(
&self,
threads: &ThreadManager<'tcx>,
callback: impl FnOnce(&VClock) -> R,
) -> R
pub fn release_clock<'tcx, R>( &self, threads: &ThreadManager<'tcx>, callback: impl FnOnce(&VClock) -> R, ) -> R
Calls the given closure with the “release” clock of the current thread. Other threads can acquire this clock in the future to establish synchronization with this program point.
fn thread_index(&self, thread: ThreadId) -> VectorIdx
Sourcefn thread_state_mut(
&self,
thread: ThreadId,
) -> (VectorIdx, RefMut<'_, ThreadClockSet>)
fn thread_state_mut( &self, thread: ThreadId, ) -> (VectorIdx, RefMut<'_, ThreadClockSet>)
Load the vector index used by the given thread as well as the set of vector clocks used by the thread.
Sourcefn thread_state(&self, thread: ThreadId) -> (VectorIdx, Ref<'_, ThreadClockSet>)
fn thread_state(&self, thread: ThreadId) -> (VectorIdx, Ref<'_, ThreadClockSet>)
Load the vector index used by the given thread as well as the set of vector clocks used by the thread.
Sourcepub(super) fn active_thread_state(
&self,
thread_mgr: &ThreadManager<'_>,
) -> (VectorIdx, Ref<'_, ThreadClockSet>)
pub(super) fn active_thread_state( &self, thread_mgr: &ThreadManager<'_>, ) -> (VectorIdx, Ref<'_, ThreadClockSet>)
Load the current vector clock in use and the current set of thread clocks in use for the vector.
Sourcepub(super) fn active_thread_state_mut(
&self,
thread_mgr: &ThreadManager<'_>,
) -> (VectorIdx, RefMut<'_, ThreadClockSet>)
pub(super) fn active_thread_state_mut( &self, thread_mgr: &ThreadManager<'_>, ) -> (VectorIdx, RefMut<'_, ThreadClockSet>)
Load the current vector clock in use and the current set of thread clocks in use for the vector mutably for modification.
Sourcefn active_thread_index(&self, thread_mgr: &ThreadManager<'_>) -> VectorIdx
fn active_thread_index(&self, thread_mgr: &ThreadManager<'_>) -> VectorIdx
Return the current thread, should be the same as the data-race active thread.
pub(super) fn sc_write(&self, thread_mgr: &ThreadManager<'_>)
pub(super) fn sc_read(&self, thread_mgr: &ThreadManager<'_>)
Trait Implementations§
Source§impl Clone for GlobalState
impl Clone for GlobalState
Source§fn clone(&self) -> GlobalState
fn clone(&self) -> GlobalState
1.0.0 · Source§fn clone_from(&mut self, source: &Self)
fn clone_from(&mut self, source: &Self)
source
. Read moreSource§impl Debug for GlobalState
impl Debug for GlobalState
Source§impl VisitProvenance for GlobalState
impl VisitProvenance for GlobalState
fn visit_provenance(&self, _visit: &mut VisitWith<'_>)
Auto Trait Implementations§
impl !Freeze for GlobalState
impl !RefUnwindSafe for GlobalState
impl Send for GlobalState
impl !Sync for GlobalState
impl Unpin for GlobalState
impl UnwindSafe for GlobalState
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Layout§
Note: Most layout information is completely unstable and may even differ between compilations. The only exception is types with certain repr(...)
attributes. Please see the Rust Reference's “Type Layout” chapter for details on type layout guarantees.
Size: 288 bytes