-
Notifications
You must be signed in to change notification settings - Fork 14
/
custom_cmd.rs
102 lines (80 loc) · 2.25 KB
/
custom_cmd.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
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
//! Example of using a custom command for z3.
#[macro_use]
extern crate clap;
use rsmt2::prelude::*;
fn main() {
let matches = clap_app!(myapp =>
(version: "1.0")
(about: "Example of using a custom command for z3")
(@arg CMD: --z3_cmd +takes_value "Specifies a custom command to run z3")
(@arg INPUT: "An optional smt2 file")
)
.get_matches();
let file = matches.value_of("INPUT");
let cmd = matches.value_of("CMD");
if let Err(e) = run(file, cmd) {
eprintln!("|===| Error");
for line in e.to_string().lines() {
eprintln!("| {}", line)
}
eprintln!("|===|")
}
}
fn run(file: Option<&str>, cmd: Option<&str>) -> SmtRes<()> {
if let Some(file) = file {
let output = run_file(file, cmd)?;
print!("{}", output);
Ok(())
} else {
run_test(cmd)
}
}
fn solver(cmd: Option<&str>) -> SmtRes<Solver<()>> {
let cmd = cmd.unwrap_or_else(|| rsmt2::SmtStyle::Z3.cmd());
SmtConf::z3(cmd).spawn(())
}
fn run_file(file: &str, cmd: Option<&str>) -> SmtRes<String> {
use std::io::{BufRead, BufReader, Read, Write};
let mut file_read = std::fs::OpenOptions::new().read(true).open(file)?;
let mut content = String::with_capacity(103);
file_read.read_to_string(&mut content)?;
let mut solver = solver(cmd)?;
solver.write(content.as_bytes())?;
solver.flush()?;
content.clear();
let mut solver = BufReader::new(solver);
assert!(content.is_empty());
loop {
if solver.read_line(&mut content)? == 0 {
break;
}
}
Ok(content)
}
fn run_test(cmd: Option<&str>) -> SmtRes<()> {
let mut solver = solver(cmd)?;
solver.declare_const("a", "Bool")?;
solver.assert("(and a (not a))")?;
if solver.check_sat()? {
panic!("expected unsat, got sat")
} else {
println!("success")
}
Ok(())
}
#[test]
fn test_unknown_cmd() {
assert_eq!(
run_test(Some("z3_unknown_command"))
.unwrap_err()
.to_string(),
"While spawning child process with z3_unknown_command"
)
}
#[test]
fn test_rsc_test_smt2() {
assert_eq!(
run_file("rsc/test.smt2", Some("z3")).unwrap().trim(),
"unsat"
)
}