Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Enable powf*, exp*, log* intrinsics #2996

Merged
merged 16 commits into from
Feb 7, 2024
16 changes: 8 additions & 8 deletions docs/src/rust-feature-support/intrinsics.md
Original file line number Diff line number Diff line change
Expand Up @@ -148,10 +148,10 @@ cttz_nonzero | Yes | |
discriminant_value | Yes | |
drop_in_place | No | |
exact_div | Yes | |
exp2f32 | No | |
exp2f64 | No | |
expf32 | No | |
expf64 | No | |
exp2f32 | Partial | Results are overapproximated |
exp2f64 | Partial | Results are overapproximated |
expf32 | Partial | Results are overapproximated |
expf64 | Partial | Results are overapproximated |
fabsf32 | Yes | |
fabsf64 | Yes | |
fadd_fast | Yes | |
Expand All @@ -170,8 +170,8 @@ log10f32 | No | |
log10f64 | No | |
log2f32 | No | |
log2f64 | No | |
logf32 | No | |
logf64 | No | |
logf32 | Partial | Results are overapproximated |
logf64 | Partial | Results are overapproximated |
maxnumf32 | Yes | |
maxnumf64 | Yes | |
min_align_of | Yes | |
Expand All @@ -185,8 +185,8 @@ nearbyintf64 | Yes | |
needs_drop | Yes | |
nontemporal_store | No | |
offset | Partial | Doesn't check [all UB conditions](https://doc.rust-lang.org/std/primitive.pointer.html#safety-2) |
powf32 | No | |
powf64 | No | |
powf32 | Partial | Results are overapproximated |
powf64 | Partial | Results are overapproximated |
powif32 | No | |
powif64 | No | |
pref_align_of | Yes | |
Expand Down
16 changes: 8 additions & 8 deletions kani-compiler/src/codegen_cprover_gotoc/codegen/intrinsic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -420,10 +420,10 @@ impl<'tcx> GotocCtx<'tcx> {
self.codegen_expr_to_place_stable(place, e)
}
"exact_div" => self.codegen_exact_div(fargs, place, loc),
"exp2f32" => unstable_codegen!(codegen_simple_intrinsic!(Exp2f)),
"exp2f64" => unstable_codegen!(codegen_simple_intrinsic!(Exp2)),
"expf32" => unstable_codegen!(codegen_simple_intrinsic!(Expf)),
"expf64" => unstable_codegen!(codegen_simple_intrinsic!(Exp)),
"exp2f32" => codegen_simple_intrinsic!(Exp2f),
"exp2f64" => codegen_simple_intrinsic!(Exp2),
"expf32" => codegen_simple_intrinsic!(Expf),
"expf64" => codegen_simple_intrinsic!(Exp),
"fabsf32" => codegen_simple_intrinsic!(Fabsf),
"fabsf64" => codegen_simple_intrinsic!(Fabs),
"fadd_fast" => {
Expand Down Expand Up @@ -456,8 +456,8 @@ impl<'tcx> GotocCtx<'tcx> {
"log10f64" => unstable_codegen!(codegen_simple_intrinsic!(Log10)),
"log2f32" => unstable_codegen!(codegen_simple_intrinsic!(Log2f)),
"log2f64" => unstable_codegen!(codegen_simple_intrinsic!(Log2)),
"logf32" => unstable_codegen!(codegen_simple_intrinsic!(Logf)),
"logf64" => unstable_codegen!(codegen_simple_intrinsic!(Log)),
"logf32" => codegen_simple_intrinsic!(Logf),
"logf64" => codegen_simple_intrinsic!(Log),
tautschnig marked this conversation as resolved.
Show resolved Hide resolved
"maxnumf32" => codegen_simple_intrinsic!(Fmaxf),
"maxnumf64" => codegen_simple_intrinsic!(Fmax),
"min_align_of" => codegen_intrinsic_const!(),
Expand All @@ -474,8 +474,8 @@ impl<'tcx> GotocCtx<'tcx> {
"offset" => unreachable!(
"Expected `core::intrinsics::unreachable` to be handled by `BinOp::OffSet`"
),
"powf32" => unstable_codegen!(codegen_simple_intrinsic!(Powf)),
"powf64" => unstable_codegen!(codegen_simple_intrinsic!(Pow)),
"powf32" => codegen_simple_intrinsic!(Powf),
"powf64" => codegen_simple_intrinsic!(Pow),
"powif32" => unstable_codegen!(codegen_simple_intrinsic!(Powif)),
"powif64" => unstable_codegen!(codegen_simple_intrinsic!(Powi)),
"pref_align_of" => codegen_intrinsic_const!(),
Expand Down
20 changes: 20 additions & 0 deletions tests/kani/Intrinsics/Math/Arith/exp.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
// Copyright Kani Contributors
// SPDX-License-Identifier: Apache-2.0 OR MIT

#[kani::proof]
fn verify_exp32() {
let two = 2.0_f32;
let two_sq = std::f32::consts::E * std::f32::consts::E;
let two_exp = two.exp();

assert!((two_sq - two_exp).abs() <= 1.0);
tautschnig marked this conversation as resolved.
Show resolved Hide resolved
}

#[kani::proof]
fn verify_exp64() {
let two = 2.0_f64;
let two_sq = std::f64::consts::E * std::f64::consts::E;
let two_exp = two.exp();

assert!((two_sq - two_exp).abs() <= 1.0);
}
18 changes: 18 additions & 0 deletions tests/kani/Intrinsics/Math/Arith/exp2.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
// Copyright Kani Contributors
// SPDX-License-Identifier: Apache-2.0 OR MIT

tautschnig marked this conversation as resolved.
Show resolved Hide resolved
#[kani::proof]
fn verify_exp2_32() {
let two = 2.0_f32;
let two_two = two.exp2();

assert!((two_two - 4.0).abs() <= 1.0);
}

#[kani::proof]
fn verify_exp2_64() {
let two = 2.0_f64;
let two_two = two.exp2();

assert!((two_two - 4.0).abs() <= 1.0);
}
18 changes: 18 additions & 0 deletions tests/kani/Intrinsics/Math/Arith/log.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
// Copyright Kani Contributors
// SPDX-License-Identifier: Apache-2.0 OR MIT

#[kani::proof]
fn verify_logf32() {
let e = std::f32::consts::E;
let e_log = e.ln();

assert!((e_log - 1.0).abs() <= 0.1);
}

#[kani::proof]
fn verify_logf64() {
let e = std::f64::consts::E;
let e_log = e.ln();

assert!((e_log - 1.0).abs() <= 0.1);
}
11 changes: 11 additions & 0 deletions tests/kani/Intrinsics/Math/Arith/powf32.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// Copyright Kani Contributors
// SPDX-License-Identifier: Apache-2.0 OR MIT

#[kani::proof]
fn verify_pow() {
let x: f32 = kani::any();
kani::assume(x.is_normal());
kani::assume(x > 1.0 && x < u16::MAX.into());
let x2 = x.powf(2.0);
assert!(x2 >= 0.0);
}
26 changes: 26 additions & 0 deletions tests/kani/Intrinsics/Math/Arith/powf64.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
// Copyright Kani Contributors
// SPDX-License-Identifier: Apache-2.0 OR MIT

pub fn f(a: u64) -> u64 {
const C: f64 = 0.618;
(a as f64).powf(C) as u64
}

#[cfg(kani)]
mod verification {
use super::*;

#[kani::proof]
fn verify_f() {
const LIMIT: u64 = 10;
let x: u64 = kani::any();
let y: u64 = kani::any();
// outside these limits our approximation may yield spurious results
kani::assume(x > LIMIT && x < LIMIT * 3);
kani::assume(y > LIMIT && y < LIMIT * 3);
kani::assume(x > y);
let x_ = f(x);
let y_ = f(y);
assert!(x_ >= y_);
}
}
Loading