in z3tracer/src/model.rs [501:586]
fn log_instance(&self, key: QiKey) -> RawResult<()> {
let inst = self
.instantiations
.get(&key)
.ok_or(RawError::InvalidInstanceKey)?;
match &inst.frame {
QiFrame::Discovered { .. } => (),
QiFrame::NewMatch {
quantifier,
terms,
trigger,
used,
} => {
let quantifier = self.term(quantifier)?;
if let Term::Quant {
name,
var_names: Some(var_names),
..
} = quantifier
{
// Bind variable names.
let mut venv = BTreeMap::new();
for (i, vn) in var_names.iter().enumerate() {
venv.insert(i as u64, vn.name.clone());
}
if self.config.with_qi_triggers {
// Trim the outer "pattern" application.
let trigger = match self.term(trigger)? {
Term::App { name, args, .. }
if name == "pattern" && args.len() == 1 =>
{
&args[0]
}
_ => trigger,
};
println!("{} :: {{ {} }}", name, self.id_to_sexp(&venv, trigger)?);
} else {
println!("{}", name);
}
// Print instantiation terms.
let global_venv = BTreeMap::new();
if self.config.with_qi_variables {
for (i, vn) in var_names.iter().enumerate() {
println!(
" {} <-- {}",
vn.name.clone(),
self.id_to_sexp(&global_venv, &terms[i])?
);
}
}
if self.config.with_qi_used_terms {
// Print 'used' terms.
for u in used {
use MatchedTerm::*;
match u {
Trigger(id) => {
println!(" ! {}", self.id_to_sexp(&global_venv, id)?);
}
Equality(id1, id2) => {
println!(
" !! {} == {}",
self.id_to_sexp(&global_venv, id1)?,
self.id_to_sexp(&global_venv, id2)?
);
}
}
}
}
if self.config.with_qi_produced_terms {
for instance in &inst.instances {
// Print maximal produced terms (aka attached enodes).
let mut subterms = BTreeSet::new();
for e in instance.enodes.iter().rev() {
if !subterms.contains(e) {
let t = self.term(e)?;
self.append_term_subterms(&mut subterms, t)?;
println!(" --> {}", self.term_to_sexp(&global_venv, t)?);
}
}
}
}
}
}
}
Ok(())
}