Skip to content

Commit d310620

Browse files
committed
Allow configuring the failure rate with -Zmiri-compare-exchange-weak-failure-rate
1 parent d4b592e commit d310620

File tree

4 files changed

+20
-3
lines changed

4 files changed

+20
-3
lines changed

src/bin/miri.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -282,6 +282,14 @@ fn main() {
282282
};
283283
miri_config.tracked_alloc_id = Some(miri::AllocId(id));
284284
}
285+
arg if arg.starts_with("-Zmiri-compare-exchange-weak-failure-rate=") => {
286+
let rate = match arg.strip_prefix("-Zmiri-compare-exchange-weak-failure-rate=").unwrap().parse::<f64>() {
287+
Ok(rate) if rate >= 0.0 && rate <= 1.0 => rate,
288+
Ok(_) => panic!("-Zmiri-compare-exchange-weak-failure-rate must be between `0.0` and `1.0`"),
289+
Err(err) => panic!("-Zmiri-compare-exchange-weak-failure-rate requires a `f64` between `0.0` and `1.0`: {}", err),
290+
};
291+
miri_config.cmpxchg_weak_failure_rate = rate;
292+
}
285293
_ => {
286294
// Forward to rustc.
287295
rustc_args.push(arg);

src/data_race.rs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -567,10 +567,11 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: MiriEvalContextExt<'mir, 'tcx> {
567567
let old = this.allow_data_races_mut(|this| this.read_immediate(place.into()))?;
568568
// `binary_op` will bail if either of them is not a scalar.
569569
let eq = this.overflowing_binary_op(mir::BinOp::Eq, old, expect_old)?.0;
570-
// If the operation would succeed, but is "weak", fail 80% of the time.
571-
// FIXME: this is quite arbitrary.
570+
// If the operation would succeed, but is "weak", fail some portion
571+
// of the time, based on `rate`.
572+
let rate = this.memory.extra.cmpxchg_weak_failure_rate;
572573
let cmpxchg_success = eq.to_bool()?
573-
&& (!can_fail_spuriously || this.memory.extra.rng.borrow_mut().gen_range(0, 10) < 8);
574+
&& (!can_fail_spuriously || this.memory.extra.rng.borrow_mut().gen::<f64>() < rate);
574575
let res = Immediate::ScalarPair(
575576
old.to_scalar_or_uninit(),
576577
Scalar::from_bool(cmpxchg_success).into(),

src/eval.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,9 @@ pub struct MiriConfig {
5050
pub track_raw: bool,
5151
/// Determine if data race detection should be enabled
5252
pub data_race_detector: bool,
53+
/// Rate of spurious failures for compare_exchange_weak atomic operations,
54+
/// between 0.0 and 1.0, defaulting to 0.8 (80% chance of failure).
55+
pub cmpxchg_weak_failure_rate: f64,
5356
}
5457

5558
impl Default for MiriConfig {
@@ -68,6 +71,7 @@ impl Default for MiriConfig {
6871
tracked_alloc_id: None,
6972
track_raw: false,
7073
data_race_detector: true,
74+
cmpxchg_weak_failure_rate: 0.8,
7175
}
7276
}
7377
}

src/machine.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -135,6 +135,9 @@ pub struct MemoryExtra {
135135

136136
/// Controls whether alignment of memory accesses is being checked.
137137
pub(crate) check_alignment: AlignmentCheck,
138+
139+
/// Failure rate of compare_exchange_weak, between 0.0 and 1.0
140+
pub(crate) cmpxchg_weak_failure_rate: f64,
138141
}
139142

140143
impl MemoryExtra {
@@ -162,6 +165,7 @@ impl MemoryExtra {
162165
rng: RefCell::new(rng),
163166
tracked_alloc_id: config.tracked_alloc_id,
164167
check_alignment: config.check_alignment,
168+
cmpxchg_weak_failure_rate: config.cmpxchg_weak_failure_rate,
165169
}
166170
}
167171

0 commit comments

Comments
 (0)