Skip to content

Commit 3b7cb23

Browse files
Centri3RalfJung
authored andcommitted
Add new intrinsic is_constant and optimize pow
Fix overflow check Make MIRI choose the path randomly and rename the intrinsic Add back test Add miri test and make it operate on `ptr` Define `llvm.is.constant` for primitives Update MIRI comment and fix test in stage2 Add const eval test Clarify that both branches must have the same side effects guaranteed non guarantee use immediate type instead Co-Authored-By: Ralf Jung <[email protected]>
1 parent c368b4c commit 3b7cb23

File tree

2 files changed

+27
-0
lines changed

2 files changed

+27
-0
lines changed

src/shims/intrinsics/mod.rs

+12
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ use std::iter;
55

66
use log::trace;
77

8+
use rand::Rng;
89
use rustc_apfloat::{Float, Round};
910
use rustc_middle::ty::layout::LayoutOf;
1011
use rustc_middle::{
@@ -141,6 +142,17 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> {
141142
this.write_pointer(Pointer::new(ptr.provenance, masked_addr), dest)?;
142143
}
143144

145+
// We want to return either `true` or `false` at random, or else something like
146+
// ```
147+
// if !is_val_statically_known(0) { unreachable_unchecked(); }
148+
// ```
149+
// Would not be considered UB, or the other way around (`is_val_statically_known(0)`).
150+
"is_val_statically_known" => {
151+
let [_] = check_arg_count(args)?;
152+
let branch: bool = this.machine.rng.get_mut().gen();
153+
this.write_scalar(Scalar::from_bool(branch), dest)?;
154+
}
155+
144156
// Floating-point operations
145157
"fabsf32" => {
146158
let [f] = check_arg_count(args)?;

tests/pass/intrinsics.rs

+15
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,21 @@ fn main() {
3333
assert_eq!(intrinsics::likely(false), false);
3434
assert_eq!(intrinsics::unlikely(true), true);
3535

36+
let mut saw_true = false;
37+
let mut saw_false = false;
38+
39+
for _ in 0..50 {
40+
if unsafe { intrinsics::is_val_statically_known(0) } {
41+
saw_true = true;
42+
} else {
43+
saw_false = true;
44+
}
45+
}
46+
assert!(
47+
saw_true && saw_false,
48+
"`is_val_statically_known` failed to return both true and false. Congrats, you won the lottery!"
49+
);
50+
3651
intrinsics::forget(Bomb);
3752

3853
let _v = intrinsics::discriminant_value(&Some(()));

0 commit comments

Comments
 (0)