def __init__(self, stream, annotations=None): TreeWalker.__init__(self) self.stream = stream self.write = self.stream.write self.mgr = get_env().formula_manager if not annotations: self.annotations = Annotations() else: self.annotations = annotations
def test_annotations(self): x = Symbol('x') x_next = Symbol('x.next') f = Iff(x, Not(x_next)) ann = Annotations() ann.add(x, 'next', x_next.symbol_name()) ann.add(f, 'trans', 'true') ann.add(x, 'init', 'true') tree_buf = StringIO() dag_buf = StringIO() tree_printer = SmtPrinter(tree_buf, annotations=ann) dag_printer = SmtDagPrinter(dag_buf, annotations=ann) dag_printer.printer(f) tree_printer.printer(f) self.assertEqual( tree_buf.getvalue(), "(! (= (! x :next x.next :init true) (not x.next)) :trans true)") self.assertEqual( dag_buf.getvalue(), "(let ((.def_0 (not x.next))) (let ((.def_1 (= (! x :next x.next :init true) .def_0))) (! .def_1 :trans true)))" )
def test_basic(self): ann = Annotations() a = Symbol("a") next_a = Symbol("next(a)") init_a = Symbol("init(a)") ann.add(a, "next", next_a) ann.add(a, "init", init_a) ann.add(a, "related", next_a) ann.add(a, "related", init_a) self.assertIn(a, ann) self.assertEqual(set([next_a]), ann.annotations(a)["next"]) self.assertEqual(set([init_a]), ann.annotations(a)["init"]) self.assertEqual(set([init_a, next_a]), ann.annotations(a)["related"]) self.assertEqual(set([a]), ann.all_annotated_formulae("next")) self.assertEqual(set([a]), ann.all_annotated_formulae("init")) self.assertEqual(set([a]), ann.all_annotated_formulae("related")) self.assertEqual(set(), ann.all_annotated_formulae("non-existent"))
def __init__(self): self.keys = {} self.definitions = {} self.annotations = Annotations()
def test_remove_value(self): ann = Annotations() a = Symbol("a") next_a = Symbol("next(a)") init_a = Symbol("init(a)") ann.add(a, "next", next_a) ann.add(a, "init", init_a) ann.add(a, "related", next_a) ann.add(a, "related", init_a) self.assertNotEqual( ann.annotations(a)["init"], ann.annotations(a)["related"]) ann.remove_value(a, "related", next_a) self.assertEqual( ann.annotations(a)["related"], ann.annotations(a)["init"])
def test_remove_annotation(self): ann = Annotations() a = Symbol("a") next_a = Symbol("next(a)") init_a = Symbol("init(a)") ann.add(a, "next", next_a) ann.add(a, "init", init_a) ann.add(a, "related", next_a) ann.add(a, "related", init_a) ann.remove_annotation(a, "next") self.assertNotIn("next", ann.annotations(a)) self.assertEqual(set([init_a]), ann.annotations(a)["init"]) self.assertEqual(set([init_a, next_a]), ann.annotations(a)["related"]) self.assertEqual(set([]), ann.all_annotated_formulae("next")) self.assertEqual(set([a]), ann.all_annotated_formulae("init")) self.assertEqual(set([a]), ann.all_annotated_formulae("related")) self.assertEqual(set(), ann.all_annotated_formulae("non-existent"))
def test_remove_value(self): ann = Annotations() a = Symbol("a") next_a = Symbol("next(a)") init_a = Symbol("init(a)") ann.add(a, "next", next_a) ann.add(a, "init", init_a) ann.add(a, "related", next_a) ann.add(a, "related", init_a) self.assertNotEqual(ann.annotations(a)["init"], ann.annotations(a)["related"]) ann.remove_value(a, "related", next_a) self.assertEqual(ann.annotations(a)["related"], ann.annotations(a)["init"])
def test_remove(self): ann = Annotations() a = Symbol("a") next_a = Symbol("next(a)") init_a = Symbol("init(a)") ann.add(a, "next", next_a) ann.add(a, "init", init_a) ann.add(a, "related", next_a) ann.add(a, "related", init_a) self.assertIn(a, ann) ann.remove(a) self.assertNotIn(a, ann) self.assertEqual(None, ann.annotations(a)) self.assertEqual(set([]), ann.all_annotated_formulae("next")) self.assertEqual(set([]), ann.all_annotated_formulae("init")) self.assertEqual(set([]), ann.all_annotated_formulae("related")) self.assertEqual(set(), ann.all_annotated_formulae("non-existent"))
class SmtPrinter(TreeWalker): def __init__(self, stream, annotations=None): TreeWalker.__init__(self) self.stream = stream self.write = self.stream.write self.mgr = get_env().formula_manager if not annotations: self.annotations = Annotations() else: self.annotations = annotations def printer(self, f): self.walk(f) def walk_threshold(self, formula): """This is a complete printer""" raise NotImplementedError def walk_nary(self, formula, operator): self.write("(%s" % operator) for s in formula.args(): self.write(" ") yield s self.write(")") def walk_and(self, formula): return self.walk_nary(formula, "and") def walk_or(self, formula): return self.walk_nary(formula, "or") def walk_not(self, formula): return self.walk_nary(formula, "not") def walk_implies(self, formula): return self.walk_nary(formula, "=>") def walk_iff(self, formula): return self.walk_nary(formula, "=") def walk_plus(self, formula): return self.walk_nary(formula, "+") def walk_minus(self, formula): return self.walk_nary(formula, "-") def walk_times(self, formula): return self.walk_nary(formula, "*") def walk_equals(self, formula): return self.walk_nary(formula, "=") def walk_le(self, formula): return self.walk_nary(formula, "<=") def walk_lt(self, formula): return self.walk_nary(formula, "<") def walk_ite(self, formula): return self.walk_nary(formula, "ite") def walk_toreal(self, formula): return self.walk_nary(formula, "to_real") def walk_realtoint(self, formula): return self.walk_nary(formula, "to_int") def walk_div(self, formula): return self.walk_nary(formula, "/") def walk_int_div(self, formula): return self.walk_nary(formula, "div") def walk_mod(self, formula): return self.walk_nary(formula, "mod") def walk_pow(self, formula): return self.walk_nary(formula, "pow") def walk_bv_and(self, formula): return self.walk_nary(formula, "bvand") def walk_bv_or(self, formula): return self.walk_nary(formula, "bvor") def walk_bv_not(self, formula): return self.walk_nary(formula, "bvnot") def walk_bv_xor(self, formula): return self.walk_nary(formula, "bvxor") def walk_bv_add(self, formula): return self.walk_nary(formula, "bvadd") def walk_bv_sub(self, formula): return self.walk_nary(formula, "bvsub") def walk_bv_neg(self, formula): return self.walk_nary(formula, "bvneg") def walk_bv_mul(self, formula): return self.walk_nary(formula, "bvmul") def walk_bv_udiv(self, formula): return self.walk_nary(formula, "bvudiv") def walk_bv_urem(self, formula): return self.walk_nary(formula, "bvurem") def walk_bv_lshl(self, formula): return self.walk_nary(formula, "bvshl") def walk_bv_lshr(self, formula): return self.walk_nary(formula, "bvlshr") def walk_bv_ult(self, formula): return self.walk_nary(formula, "bvult") def walk_bv_ule(self, formula): return self.walk_nary(formula, "bvule") def walk_bv_slt(self, formula): return self.walk_nary(formula, "bvslt") def walk_bv_sle(self, formula): return self.walk_nary(formula, "bvsle") def walk_bv_concat(self, formula): return self.walk_nary(formula, "concat") def walk_bv_comp(self, formula): return self.walk_nary(formula, "bvcomp") def walk_bv_ashr(self, formula): return self.walk_nary(formula, "bvashr") def walk_bv_sdiv(self, formula): return self.walk_nary(formula, "bvsdiv") def walk_bv_srem(self, formula): return self.walk_nary(formula, "bvsrem") def walk_bv_tonatural(self, formula): return self.walk_nary(formula, "bv2nat") #def walk_int_to_bv(self, formula): return self.walk_nary(formula, "int2bv") def walk_array_select(self, formula): return self.walk_nary(formula, "select") def walk_array_store(self, formula): return self.walk_nary(formula, "store") def walk_symbol(self, formula): self.write(quote(formula.symbol_name())) def walk_function(self, formula): return self.walk_nary(formula, quote(formula.function_name().symbol_name())) def walk_int_constant(self, formula): if formula.constant_value() < 0: self.write("(- " + str(-formula.constant_value()) + ")") else: self.write(str(formula.constant_value())) def walk_real_constant(self, formula): if formula.constant_value() < 0: template = "(- %s)" else: template = "%s" (n,d) = abs(formula.constant_value().numerator), \ formula.constant_value().denominator if d != 1: res = template % ("(/ " + str(n) + " " + str(d) + ")") else: res = template % (str(n) + ".0") self.write(res) def walk_bool_constant(self, formula): if formula.constant_value(): self.write("true") else: self.write("false") def walk_bv_constant(self, formula): self.write("#b" + formula.bv_bin_str()) def walk_str_constant(self, formula): self.write('"' + formula.constant_value().replace('"', '""') + '"') def walk_forall(self, formula): return self._walk_quantifier("forall", formula) def walk_exists(self, formula): return self._walk_quantifier("exists", formula) def _walk_quantifier(self, operator, formula): assert len(formula.quantifier_vars()) > 0 self.write("(%s (" % operator) for s in formula.quantifier_vars(): self.write("(") yield s self.write(" %s)" % s.symbol_type().as_smtlib(False)) self.write(") ") body = formula.arg(0) pats = formula.quantifier_patterns() nopats = formula.quantifier_nopatterns() if self.annotations.has_annotation(body, "qid"): qids = self.annotations[body]["qid"] else: qids = set() some_annotation = len(pats) + len(nopats) + len(qids) > 0 if len(qids) == 0: qid = None else: qid = next(iter(qids)) if some_annotation: self.write("(! ") yield body def gen_pat(pat): for term_num, term in enumerate(pat): yield term if term_num < len(pat) - 1: self.write(" ") def gen_pats(lbl, ps): for pat_num, pat in enumerate(ps): self.write(" :%s (" % lbl) yield from gen_pat(pat) self.write(")") def gen_nopats(lbl, ns): for nopat in ns: self.write(" :%s " % lbl) yield nopat if len(pats) > 0: yield from gen_pats("pattern", pats) if len(nopats) > 0: yield from gen_nopats("no-pattern", nopats) if qid: self.write(" :qid %s" % qid) # Closing the (! ... :pattern (...) ) # ^ if some_annotation: self.write(" )") self.write(")") def walk_bv_extract(self, formula): self.write("((_ extract %d %d) " % (formula.bv_extract_end(), formula.bv_extract_start())) yield formula.arg(0) self.write(")") @handles(op.INT_TO_BV) def walk_int_to_bv(self, formula): self.write("((_ int2bv %d) " % formula._content.payload) yield formula.arg(0) self.write(")") @handles(op.BV_ROR, op.BV_ROL) def walk_bv_rotate(self, formula): if formula.is_bv_ror(): rotate_type = "rotate_right" else: assert formula.is_bv_rol() rotate_type = "rotate_left" rot_step = formula.bv_rotation_step() if is_python_integer(rot_step): self.write("((_ %s %d) " % (rotate_type, rot_step)) yield formula.arg(0) else: self.write("(ext_%s " % rotate_type) yield formula.arg(0) self.write(" ") yield rot_step self.write(")") @handles(op.BV_ZEXT, op.BV_SEXT) def walk_bv_extend(self, formula): if formula.is_bv_zext(): extend_type = "zero_extend" else: assert formula.is_bv_sext() extend_type = "sign_extend" self.write("((_ %s %d) " % (extend_type, formula.bv_extend_step())) yield formula.arg(0) self.write(")") def walk_str_length(self, formula): self.write("(str.len ") self.walk(formula.arg(0)) self.write(")") def walk_str_charat(self, formula, **kwargs): self.write("( str.at ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(")") def walk_str_concat(self, formula, **kwargs): self.write("( str.++ ") for arg in formula.args(): self.walk(arg) self.write(" ") self.write(")") def walk_str_contains(self, formula, **kwargs): self.write("( str.contains ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(")") def walk_str_indexof(self, formula, **kwargs): self.write("( str.indexof ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(" ") self.walk(formula.arg(2)) self.write(")") def walk_str_replace(self, formula, **kwargs): self.write("( str.replace ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(" ") self.walk(formula.arg(2)) self.write(")") def walk_str_substr(self, formula, **kwargs): self.write("( str.substr ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(" ") self.walk(formula.arg(2)) self.write(")") def walk_str_prefixof(self, formula, **kwargs): self.write("( str.prefixof ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(")") def walk_str_suffixof(self, formula, **kwargs): self.write("( str.suffixof ") self.walk(formula.arg(0)) self.write(" ") self.walk(formula.arg(1)) self.write(")") def walk_str_to_int(self, formula, **kwargs): self.write("( str.to.int ") self.walk(formula.arg(0)) self.write(")") def walk_int_to_str(self, formula, **kwargs): self.write("( int.to.str ") self.walk(formula.arg(0)) self.write(")") def walk_array_value(self, formula): assign = formula.array_value_assigned_values_map() for _ in xrange(len(assign)): self.write("(store ") self.write("((as const %s) " % formula.get_type().as_smtlib(False)) yield formula.array_value_default() self.write(")") for k in sorted(assign, key=str): self.write(" ") yield k self.write(" ") yield assign[k] self.write(")")