-
Notifications
You must be signed in to change notification settings - Fork 82
/
Copy pathrecommends.rs
63 lines (55 loc) · 1.25 KB
/
recommends.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
#[allow(unused_imports)]
use builtin::*;
use builtin_macros::*;
#[allow(unused_imports)]
use vstd::{pervasive::*, seq::*, seq_lib::*};
verus! {
spec fn max_int(x: int, y: int) -> int {
if x > y {
x
} else {
y
}
}
// To enable recommends checking, use: spec(checked) instead of spec
spec fn seq_max_int(s: Seq<int>) -> int
recommends
s.len()
> 0, // without this, spec(checked) generates a recommends warning below
decreases s.len(),
{
let m = s[s.len() - 1];
if s.len() <= 1 {
m
} else {
max_int(m, seq_max_int(s.drop_last()))
}
}
proof fn test(s: Seq<int>)
requires
seq_max_int(s)
>= 0, // without this, the assertion fails and there's a recommends note
{
assert(seq_max_int(s) >= 0);
}
fn main() {
proof {
let s = seq![10, 20, 30, 25];
reveal_with_fuel(seq_max_int, 4);
assert(seq_max_int(s) == 30);
}
}
// Usage of `spec_affirm`
spec fn some_predicate(a: nat) -> bool
recommends
a < 100,
{
if (a >= 50) {
let _ = spec_affirm(50 <= a && a < 100);
a >= 75
} else {
let _ = spec_affirm(a < 40); // spec(checked) would raise a recommends note here
a < 25
}
}
} // verus!