Exemplo n.º 1
0
    def get_proof_term(self, goal, *, args=None, prevs=None):
        th_name = args
        C = goal.prop

        # Check whether rewriting using the theorem has an effect
        assert has_rewrite(th_name, C, sym=self.sym, conds=prevs), \
            "rewrite: unable to apply theorem."

        cv = then_conv(
            top_sweep_conv(rewr_conv(th_name, sym=self.sym, conds=prevs)),
            beta_norm_conv())
        eq_th = cv.eval(C)
        new_goal = eq_th.prop.rhs

        if self.sym:
            macro_name = 'rewrite_goal_sym'
        else:
            macro_name = 'rewrite_goal'
        if new_goal.is_equals() and new_goal.lhs == new_goal.rhs:
            return ProofTerm(macro_name, args=(th_name, C), prevs=prevs)
        else:
            new_goal = ProofTerm.sorry(Thm(goal.hyps, new_goal))
            assert new_goal.prop != goal.prop, "rewrite: unable to apply theorem"
            return ProofTerm(macro_name,
                             args=(th_name, C),
                             prevs=[new_goal] + prevs)
Exemplo n.º 2
0
def vcg_solve(goal):
    """Compute the verification conditions for a hoare triple, then
    solves the verification conditions using SMT.
    
    """
    assert goal.is_comb("Valid", 3), "vcg_solve"
    P, c, Q = goal.args

    T = Q.get_type().domain_type()
    pt = vcg_norm(T, goal)
    vc_pt = [ProofTerm("z3", vc, []) for vc in pt.assums]
    return ProofTerm("vcg", goal, vc_pt)
Exemplo n.º 3
0
    def get_proof_term(self, tm):
        if not tm.is_equals() or not int_eval(tm.lhs) != 0 or not int_eval(
                tm.rhs) == 0:
            raise ConvException(str(tm))

        lhs_value = int_eval(tm.lhs)
        if lhs_value > 0:
            premise_pt = ProofTerm("int_const_ineq",
                                   greater(IntType)(Int(lhs_value), Int(0)))
            return apply_theorem("int_pos_neq_zero", premise_pt)
        else:
            premise_pt = ProofTerm("int_const_ineq",
                                   less(IntType)(Int(lhs_value), Int(0)))
            return apply_theorem("int_neg_neq_zero", premise_pt)
Exemplo n.º 4
0
Arquivo: real.py Projeto: bzhan/holpy
 def get_proof_term(self, t):
     if t.get_type() != RealType:
         return refl(t)
     simp_t = Real(real_eval(t))
     if simp_t == t:
         return refl(t)
     return ProofTerm('real_eval', Eq(t, simp_t))
Exemplo n.º 5
0
Arquivo: real.py Projeto: bzhan/holpy
    def handle_leq_stage2(self, pt_upper_bound, pts, delta):
        # get ⊢ x_i ≤ -δ, for i = 1...n
        leq_pt = []
        pt_b = pt_upper_bound

        for i in range(len(pts)):
            if i != len(pts) - 1:
                pt = logic.apply_theorem("both_leq_max", pt_b)
                pt_1, pt_2 = logic.apply_theorem("conjD1",
                                                 pt), logic.apply_theorem(
                                                     "conjD2", pt)
            else:
                pt_2 = pt_b

            ineq = pt_2.prop

            if ineq.arg1.is_minus() and ineq.arg1.arg.is_number():
                num = ineq.arg1.arg
                expr = less_eq(ineq.arg1.arg1, num - delta)

            else:
                expr = less_eq(ineq.arg1, Real(0) - delta)

            pt_eq_comp = ProofTerm("real_eq_comparison", Eq(ineq, expr))
            leq_pt.insert(0, pt_2.on_prop(replace_conv(pt_eq_comp)))
            if i != len(pts) - 1:
                pt_b = pt_1

        return leq_pt
Exemplo n.º 6
0
Arquivo: real.py Projeto: bzhan/holpy
    def handle_geq_stage2(self, pt_lower_bound, pts, delta):
        # get ⊢ x_i ≥ δ, i = 1...n
        geq_pt = []
        pt_a = pt_lower_bound
        d = set()

        for i in range(len(pts)):
            if i != len(pts) - 1:
                pt = logic.apply_theorem("both_geq_min", pt_a)
                pt_1, pt_2 = logic.apply_theorem("conjD1",
                                                 pt), logic.apply_theorem(
                                                     "conjD2", pt)
            else:
                pt_2 = pt_a

            ineq = pt_2.prop

            if ineq.arg1.is_minus() and ineq.arg1.arg.is_number():
                # move all constant term from left to right in pt_2's prop
                num = ineq.arg1.arg
                expr = greater_eq(ineq.arg1.arg1, num + delta)

            else:
                expr = greater_eq(ineq.arg1, Real(0) + delta)

            pt_eq_comp = ProofTerm("real_eq_comparison", Eq(ineq, expr))
            geq_pt.insert(0, pt_2.on_prop(replace_conv(pt_eq_comp)))

            if i != len(pts) - 1:
                pt_a = pt_1

        return geq_pt
Exemplo n.º 7
0
    def get_proof_term(self, goal, *, args=None, prevs=None):
        assert isinstance(prevs,
                          list) and len(prevs) == 1, "rewrite_goal_with_prev"
        pt = prevs[0]
        C = goal.prop

        # In general, we assume pt.th has forall quantification.
        # First, obtain the patterns
        new_names = logic.get_forall_names(pt.prop)
        new_vars, prev_As, prev_C = logic.strip_all_implies(pt.prop, new_names)

        # Fact used must be an equality
        assert len(
            prev_As) == 0 and prev_C.is_equals(), "rewrite_goal_with_prev"

        for new_var in new_vars:
            pt = pt.forall_elim(new_var)

        # Check whether rewriting using the theorem has an effect
        assert has_rewrite(pt.th, C), "rewrite_goal_with_prev"

        cv = then_conv(top_sweep_conv(rewr_conv(pt)), beta_norm_conv())
        eq_th = cv.eval(C)
        new_goal = eq_th.prop.rhs

        prevs = list(prevs)
        if not new_goal.is_reflexive():
            prevs.append(ProofTerm.sorry(Thm(goal.hyps, new_goal)))
        return ProofTerm('rewrite_goal_with_prev', args=C, prevs=prevs)
Exemplo n.º 8
0
    def get_proof_term(self, goal, prevs=None):
        elems = goal.strip_disj()

        disjs = [tm.arg for tm in elems[:-1]]
        disj_pts = [ProofTerm.assume(disj) for disj in disjs]
        pt0 = disj_pts[0]
        for pt1 in disj_pts[1:]:
            if pt1.lhs == pt0.rhs:
                pt0 = pt0.transitive(pt1)
            elif pt1.lhs == pt0.lhs:
                pt0 = pt0.symmetric().transitive(pt1)
            elif pt1.rhs == pt0.lhs:
                pt0 = pt0.symmetric().transitive(pt1.symmetric())
            elif pt1.rhs == pt0.rhs:
                pt0 = pt0.transitive(pt1.symmetric())

            else:
                print(pt0.prop)
                print(pt1.prop)
                raise NotImplementedError

        if pt0.symmetric().prop == elems[-1]:
            pt0 = pt0.symmetric()

        assert pt0.prop == elems[-1], "%s \n %s" % (str(
            pt0.prop), str(goal.strip_disj()[-1]))

        return ProofTerm("imp_to_or", elems[:-1] + [goal], prevs=[pt0])
Exemplo n.º 9
0
 def get_proof_term(self, t):
     if t.get_type() != IntType:
         return refl(t)
     simp_t = Int(int_eval(t))
     if simp_t == t:
         return refl(t)
     else:
         return ProofTerm('int_eval', Eq(t, int_eval(t)))
Exemplo n.º 10
0
    def get_proof_term(self, prevs):
        p1, p2 = prevs
        lhs_triple = collect_int_polynomial_coeff(p1.arg1)
        rhs_triple = collect_int_polynomial_coeff(p2.arg1)
        lhs_singleton = [(p[1], p[2]) for p in lhs_triple]
        rhs_singleton = [(p[1], p[2]) for p in rhs_triple]
        if lhs_singleton != rhs_singleton or len(lhs_singleton) != len(
                rhs_singleton):
            raise NotImplementedError

        lhs_coeff = [p[0] for p in lhs_triple]
        rhs_coeff = [p[0] for p in rhs_triple]

        ratios = [p1 / p2 for p1, p2 in zip(lhs_coeff, rhs_coeff)]
        if len(set(ratios)) != 1:
            raise NotImplementedError

        lhs_mul = int(rhs_coeff[0] / gcd(lhs_coeff[0], rhs_coeff[0]))
        rhs_mul = int(lhs_coeff[0] / gcd(lhs_coeff[0], rhs_coeff[0]))

        if lhs_mul > 0:
            pt_lhs_mul = ProofTerm('int_const_ineq',
                                   greater(IntType)(Int(lhs_mul), Int(0)))

        if lhs_mul < 0:
            pt_lhs_mul = ProofTerm('int_const_ineq',
                                   less(IntType)(Int(lhs_mul), Int(0)))

        if rhs_mul > 0:
            pt_rhs_mul = ProofTerm('int_const_ineq',
                                   greater(IntType)(Int(rhs_mul), Int(0)))

        if rhs_mul < 0:
            pt_rhs_mul = ProofTerm('int_const_ineq',
                                   less(IntType)(Int(rhs_mul), Int(0)))

        pt_lhs_mul = int_ineq_mul_const_macro().get_proof_term(pt_lhs_mul, p1)
        pt_rhs_mul = int_ineq_mul_const_macro().get_proof_term(pt_rhs_mul, p2)

        # normalize both sides
        pt_lhs_mul_norm = pt_lhs_mul.transitive(norm_eq().get_proof_term(
            pt_lhs_mul.prop.rhs))
        pt_rhs_mul_norm = pt_rhs_mul.transitive(norm_eq().get_proof_term(
            pt_rhs_mul.prop.rhs))

        return pt_lhs_mul_norm.transitive(pt_rhs_mul_norm.symmetric())
Exemplo n.º 11
0
 def get_proof_term(self, t):
     eq_t = norm(t, self.conds)
     if t == eq_t.rhs:
         return refl(t)
     else:
         return ProofTerm('auto',
                          args=eq_t.prop,
                          prevs=self.conds,
                          th=eq_t.th)
Exemplo n.º 12
0
 def get_proof_term(self, tm):
     if not ((tm.is_compares() or tm.is_equals()) and \
         tm.arg1.is_constant() and tm.arg.is_constant()):
         return refl(tm)
     pt = ProofTerm("int_const_ineq", tm)
     if pt.prop.is_not():
         return pt.on_prop(rewr_conv("eq_false"))
     else:
         return pt.on_prop(rewr_conv("eq_true"))
Exemplo n.º 13
0
    def get_proof_term(self, goal, args, prevs):
        assert isinstance(args, str) and len(prevs) == 1, "resolve: type"
        th_name = args
        th = theory.get_theorem(th_name)

        assert th.prop.is_not(), "resolve: prop is not a negation"

        # Checking that the theorem matches the fact is done here.
        return ProofTerm('resolve_theorem', (args, goal.prop), prevs)
Exemplo n.º 14
0
def sympy_solve(goal, pts):
    if pts is None:
        pts = []

    macro = SymPyMacro()
    if macro.can_eval(goal, pts):
        th = Thm(sum([th.hyps for th in pts], ()), goal)
        return ProofTerm('sympy', args=goal, prevs=pts, th=th)
    else:
        raise TacticException
Exemplo n.º 15
0
 def get_proof_term(self, goal, prevs=None):
     """{(not (= x_1 y_1)) ... (not (= x_n y_n)) (not (p x_1 ... x_n)) (p y_1 ... y_n)}
     Special case: (not (= x y)) (not (p x y)) (p y x)
     """
     elems = goal.strip_disj()
     preds, pred_fun, concl = elems[:-2], elems[-2], elems[-1]
     if pred_fun.is_not():
         args_pair = [(i, j) for i, j in zip(pred_fun.arg.strip_comb()[1],
                                             concl.strip_comb()[1])]
     else:
         args_pair = [(i, j) for i, j in zip(pred_fun.strip_comb()[1],
                                             concl.arg.strip_comb()[1])]
     if len(preds) > 1:
         preds_pair = [(i.arg.lhs, i.arg.rhs) for i in preds]
     else:
         preds_pair = [(preds[0].arg.lhs, preds[0].arg.rhs),
                       (preds[0].arg.lhs, preds[0].arg.rhs)]
     if pred_fun.is_not():
         fun = concl.head
     else:
         fun = pred_fun.head
     pt0 = ProofTerm.reflexive(fun)
     pt_args_assms = []
     for arg, pred in zip(args_pair, preds_pair):
         if arg == pred:
             pt_args_assms.append(ProofTerm.assume(Eq(pred[0], pred[1])))
         elif arg[0] == pred[1] and pred[0] == arg[1]:
             pt_args_assms.append(
                 ProofTerm.assume(Eq(pred[0], pred[1])).symmetric())
         else:
             raise NotImplementedError
     pt1 = functools.reduce(lambda x, y: x.combination(y), pt_args_assms,
                            pt0)
     if pred_fun.is_not():
         pt2 = logic.apply_theorem("eq_implies1", pt1).implies_elim(
             ProofTerm.assume(pred_fun.arg))
         return ProofTerm("imp_to_or", elems[:-1] + [goal], prevs=[pt2])
     else:
         pt2 = pt1.on_prop(conv.rewr_conv("neg_iff_both_sides"))
         pt3 = logic.apply_theorem("eq_implies1", pt2).implies_elim(
             ProofTerm.assume(Not(pred_fun)))
         return ProofTerm("imp_to_or", elems[:-1] + [goal], prevs=[pt3])
Exemplo n.º 16
0
    def get_proof_term(self, goal, *, args=None, prevs=None):
        assert isinstance(goal, Thm), "MacroTactic"
        if prevs is None:
            prevs = []

        if args is None:
            args = goal.prop
        else:
            args = (goal.prop, ) + args

        return ProofTerm(self.macro, args, prevs)
Exemplo n.º 17
0
    def get_proof_term(self, goal, args, prevs):
        assert len(goal.hyps) == 0, "vcg_tactic"
        assert goal.prop.is_comb("Valid", 3), "vcg_tactic"
        P, c, Q = goal.prop.args

        # Obtain the theorem [...] |- Valid P c Q
        T = Q.get_type().domain_type()
        pt = vcg_norm(T, goal.prop)

        ptAs = [ProofTerm.sorry(Thm(goal.hyps, A)) for A in pt.assums]
        return ProofTerm("vcg", goal.prop, ptAs)
Exemplo n.º 18
0
def apply_theorem(th_name, *pts, concl=None, inst=None):
    """Wrapper for apply_theorem and apply_theorem_for macros.

    The function takes optional arguments concl, inst. Matching
    always starts with inst. If conclusion is specified, it is
    matched next. Finally, the assumptions are matched.

    """
    typecheck.checkinstance('apply_theorem', pts, [ProofTerm])
    if concl is None and inst is None:
        # Normal case, can use apply_theorem
        return ProofTerm("apply_theorem", th_name, pts)
    else:
        pt = ProofTerm.theorem(th_name)
        if inst is None:
            inst = Inst()
        if concl is not None:
            inst = matcher.first_order_match(pt.concl, concl, inst)
        for i, prev in enumerate(pts):
            inst = matcher.first_order_match(pt.assums[i], prev.prop, inst)
        return ProofTerm("apply_theorem_for", (th_name, inst), pts)
Exemplo n.º 19
0
    def get_proof_term(self, goal, *, args=None, prevs=None):
        if args is None:
            var_names = []
        else:
            var_names = args

        vars, As, C = logic.strip_all_implies(goal.prop, var_names, svar=False)

        pt = ProofTerm.sorry(Thm(list(goal.hyps) + As, C))
        ptAs = [ProofTerm.assume(A) for A in As]
        ptVars = [ProofTerm.variable(var.name, var.T) for var in vars]
        return ProofTerm('intros', None, ptVars + ptAs + [pt])
Exemplo n.º 20
0
    def get_proof_term(self, goal, *, args=None, prevs=None):
        assert isinstance(prevs, list) and len(prevs) >= 1, "apply_prev"
        pt, prev_pts = prevs[0], prevs[1:]

        # First, obtain the patterns
        new_names = logic.get_forall_names(pt.prop)
        new_vars, As, C = logic.strip_all_implies(pt.prop, new_names)
        assert len(prev_pts) <= len(As), "apply_prev: too many prev_pts"

        if args is None:
            inst = Inst()
        else:
            inst = args
        inst = matcher.first_order_match(C, goal.prop, inst)
        for idx, prev_pt in enumerate(prev_pts):
            inst = matcher.first_order_match(As[idx], prev_pt.prop, inst)

        unmatched_vars = [v for v in new_names if v not in inst]
        if unmatched_vars:
            raise theory.ParameterQueryException(
                list("param_" + name for name in unmatched_vars))

        pt = pt.subst_type(inst.tyinst)
        for new_name in new_names:
            pt = pt.forall_elim(inst[new_name])
        if pt.prop.beta_norm() != pt.prop:
            pt = pt.on_prop(beta_norm_conv())
        inst_As, inst_C = pt.prop.strip_implies()

        inst_arg = [inst[new_name] for new_name in new_names]
        new_goals = [
            ProofTerm.sorry(Thm(goal.hyps, A)) for A in inst_As[len(prev_pts):]
        ]
        if set(new_names).issubset({v.name for v in term.get_vars(As)}) and \
           matcher.is_pattern_list(As, []):
            return ProofTerm('apply_fact', args=None, prevs=prevs + new_goals)
        else:
            return ProofTerm('apply_fact_for',
                             args=inst_arg,
                             prevs=prevs + new_goals)
Exemplo n.º 21
0
def combine_mem_bounds(pt1, pt2):
    """Given two inequalities of the form x </<= a and b </<= y, where
    a and b are constants, attempt to form the theorem x </<= y.

    """
    assert pt1.prop.is_less_eq() or pt1.prop.is_less(), "combine_mem_bounds"
    assert pt2.prop.is_less_eq() or pt2.prop.is_less(), "combine_mem_bounds"

    x, a = pt1.prop.args
    b, y = pt2.prop.args

    # First obtain the comparison between a and b
    if eval_hol_expr(a) < eval_hol_expr(b):
        pt_ab = ProofTerm('const_inequality', real.less(a, b))
    elif eval_hol_expr(a) <= eval_hol_expr(b):
        pt_ab = ProofTerm('const_inequality', real.less_eq(a, b))
    else:
        raise TacticException

    # Next, successively combine the inequalities
    pt = inequality_trans(inequality_trans(pt1, pt_ab), pt2)
    return pt
Exemplo n.º 22
0
    def get_proof_term(self, args, pts):

        # First, find the pair i, j such that B_j = ~A_i or A_i = ~B_j, the
        # variable side records the side of the positive literal.
        pt1, pt2 = pts
        disj1 = strip_num(pt1.prop, args[0])
        disj2 = strip_num(pt2.prop, args[1])
        side = None
        for i, t1 in enumerate(disj1):
            for j, t2 in enumerate(disj2):
                if t2 == Not(t1):
                    side = 'left'
                    break
                elif t1 == Not(t2):
                    side = 'right'
                    break
            if side is not None:
                break

        assert side is not None, "resolution: literal not found"

        # If side is wrong, just swap:
        if side == 'right':
            return self.get_proof_term([args[1], args[0]], [pt2, pt1])

        # Move items i and j to the front
        disj1 = [disj1[i]] + disj1[:i] + disj1[i + 1:]
        disj2 = [disj2[j]] + disj2[:j] + disj2[j + 1:]
        eq_pt1 = logic.imp_disj_iff(Eq(pt1.prop, Or(*disj1)))
        eq_pt2 = logic.imp_disj_iff(Eq(pt2.prop, Or(*disj2)))
        pt1 = eq_pt1.equal_elim(pt1)
        pt2 = eq_pt2.equal_elim(pt2)

        if len(disj1) > 1 and len(disj2) > 1:
            pt = logic.apply_theorem('resolution', pt1, pt2)
        elif len(disj1) > 1 and len(disj2) == 1:
            pt = logic.apply_theorem('resolution_left', pt1, pt2)
        elif len(disj1) == 1 and len(disj2) > 1:
            pt = logic.apply_theorem('resolution_right', pt1, pt2)
        else:
            pt = logic.apply_theorem('negE', pt2, pt1)

        # return pt.on_prop(disj_norm())
        disj_new = set(disj1[1:] + disj2[1:])
        # eq_pt_norm = logic.imp_disj_iff(Eq(pt.prop, Or(*disj_new)))
        implies_pt_norm = ProofTerm("imp_disj",
                                    Implies(pt.prop, Or(*disj_new)))
        pt_final = implies_pt_norm.implies_elim(pt)
        self.arity = len(disj_new)
        return pt_final.on_prop(conv.top_conv(conv.rewr_conv("double_neg")))
Exemplo n.º 23
0
Arquivo: real.py Projeto: bzhan/holpy
    def handle_geq_stage1(self, pts):
        if not pts:
            return None, None, None

        # ⊢ min(min(...(min(x_1, x_2), x_3)...), x_n-1), x_n) > 0
        min_pos_pt = functools.reduce(
            lambda pt1, pt2: logic.apply_theorem("min_greater_0", pt1, pt2),
            pts[1:], pts[0])

        # ⊢ 0 < 2
        two_pos_pt = ProofTerm("real_compare", Real(0) < Real(2))

        # ⊢ min(...) / 2 > 0
        min_divides_two_pos = logic.apply_theorem(
            "real_lt_div", min_pos_pt.on_prop(rewr_conv("real_ge_to_le")),
            two_pos_pt).on_prop(rewr_conv("real_ge_to_le", sym=True))

        # ⊢ 2 ≥ 1
        two_larger_one = ProofTerm("real_compare", Real(2) >= Real(1))

        # ⊢ min(...) ≥ min(...) / 2
        larger_half_pt = logic.apply_theorem("real_divides_larger_1",
                                             two_larger_one, min_pos_pt)

        # ⊢ min(...) / 2 = δ_1
        delta_1 = Var("δ_1", RealType)
        pt_delta1_eq = ProofTerm.assume(Eq(larger_half_pt.prop.arg, delta_1))

        # ⊢ min(...) ≥ δ_1
        larger_half_pt_delta = larger_half_pt.on_prop(
            top_conv(replace_conv(pt_delta1_eq)))

        # ⊢ δ_1 > 0
        delta_1_pos = min_divides_two_pos.on_prop(
            arg1_conv(replace_conv(pt_delta1_eq)))

        return larger_half_pt_delta, delta_1_pos, pt_delta1_eq
Exemplo n.º 24
0
Arquivo: real.py Projeto: bzhan/holpy
    def handle_leq_stage1(self, pts):
        if not pts:
            return None, None, None
        # ⊢ max(max(...(max(x_1, x_2), x_3)...), x_n-1), x_n) < 0
        max_pos_pt = functools.reduce(
            lambda pt1, pt2: logic.apply_theorem("max_less_0", pt1, pt2),
            pts[1:], pts[0])

        # ⊢ 0 < 2
        two_pos_pt = ProofTerm("real_compare", Real(2) > Real(0))

        # ⊢ max(...) / 2 < 0
        max_divides_two_pos = logic.apply_theorem("real_neg_div_pos",
                                                  max_pos_pt, two_pos_pt)

        # ⊢ 2 ≥ 1
        two_larger_one = ProofTerm("real_compare", Real(2) >= Real(1))

        # ⊢ max(...) ≤ max(...) / 2
        less_half_pt = logic.apply_theorem("real_neg_divides_larger_1",
                                           two_larger_one, max_pos_pt)

        # ⊢ max(...) / 2 = -δ
        delta_2 = Var("δ_2", RealType)
        pt_delta_eq = ProofTerm.assume(Eq(less_half_pt.prop.arg, -delta_2))

        # ⊢ δ > 0
        delta_pos_pt = max_divides_two_pos.on_prop(
            rewr_conv("real_le_gt"), top_conv(replace_conv(pt_delta_eq)),
            auto.auto_conv())

        # max(...) ≤ -δ
        less_half_pt_delta = less_half_pt.on_prop(
            arg_conv(replace_conv(pt_delta_eq)))

        return less_half_pt_delta, delta_pos_pt, pt_delta_eq
Exemplo n.º 25
0
    def testIntro(self):
        basic.load_theory('logic_base')
        macro = logic.intros_macro()

        Ta = TVar('a')
        x = Var('x', Ta)
        P = Var('P', TFun(Ta, BoolType))
        C = Var('C', BoolType)
        ex_P = Exists(x, P(x))
        pt1 = ProofTerm.assume(ex_P)
        pt2 = ProofTerm.variable('x', Ta)
        pt3 = ProofTerm.assume(P(x))
        pt4 = ProofTerm.sorry(Thm([P(x)], C))
        pt4 = ProofTerm('intros', args=[ex_P], prevs=[pt1, pt2, pt3, pt4])
        prf = pt4.export()
        self.assertEqual(theory.check_proof(prf), Thm([ex_P], C))
Exemplo n.º 26
0
    def get_proof_term(self, t):
        if not t.is_compares():
            raise ConvException('%s is not a comparison.' % str(t))

        pt = refl(t)
        pt_norm_form = pt.on_rhs(norm_eq(), arg1_conv(omega_simp_full_conv()))
        summands = strip_plus(pt_norm_form.rhs.arg1)
        coeffs = [
            int_eval(s.arg1) if not s.is_number() else int_eval(s)
            for s in summands
        ]
        g = functools.reduce(gcd, coeffs)
        if g <= 1:
            return pt

        vars = [s.arg for s in summands if not s.is_number()]
        elim_gcd_coeffs = [int(i / g) for i in coeffs]
        if len(vars) < len(coeffs):
            simp_t = sum([
                coeff * v for coeff, v in zip(elim_gcd_coeffs[1:-1], vars[1:])
            ], elim_gcd_coeffs[0] * vars[0]) + Int(elim_gcd_coeffs[-1])
        else:
            simp_t = sum(
                [coeff * v for coeff, v in zip(elim_gcd_coeffs[1:], vars[1:])],
                elim_gcd_coeffs[0] * vars[0])

        simp_t_times_gcd = Int(g) * simp_t
        pt_simp_t_times_gcd = refl(simp_t_times_gcd).on_rhs(
            omega_simp_full_conv()).symmetric()
        pt_c = ProofTerm('int_const_ineq', greater(IntType)(Int(g), Int(0)))
        if t.is_less():
            gcd_pt = ProofTerm.theorem('int_simp_less')
        elif t.is_less_eq():
            gcd_pt = ProofTerm.theorem('int_simp_leq')
        elif t.is_greater():
            gcd_pt = ProofTerm.theorem('int_simp_gt')
        elif t.is_greater_eq():
            gcd_pt = ProofTerm.theorem('int_simp_geq')

        inst1 = matcher.first_order_match(gcd_pt.prop.arg1, pt_c.prop)
        inst2 = matcher.first_order_match(gcd_pt.prop.arg.rhs.arg1,
                                          simp_t,
                                          inst=inst1)

        pt_simp = gcd_pt.substitution(inst2).implies_elim(pt_c).on_lhs(
            arg1_conv(omega_simp_full_conv()))
        return pt_norm_form.transitive(pt_simp).on_rhs(omega_form_conv())
Exemplo n.º 27
0
def process_file(input, output):
    basic.load_theory('hoare')

    dn = os.path.dirname(os.path.realpath(__file__))
    with open(os.path.join(dn, 'examples/' + input + '.json'),
              encoding='utf-8') as a:
        data = json.load(a)

    output = json_output.JSONTheory(output, ["hoare"],
                                    "Generated from " + input)
    content = data['content']
    eval_count = 0
    vcg_count = 0
    for run in content[:5]:
        if run['ty'] == 'eval':
            com = parse_com(run['com'])
            st1 = mk_const_fun(NatType, nat.zero)
            for k, v in sorted(run['init'].items()):
                st1 = mk_fun_upd(st1, Nat(str_to_nat(k)), Nat(v))
            st2 = mk_const_fun(NatType, nat.zero)
            for k, v in sorted(run['final'].items()):
                st2 = mk_fun_upd(st2, Nat(str_to_nat(k)), Nat(v))
            Sem = imp.Sem(natFunT)
            goal = Sem(com, st1, st2)
            prf = ProofTerm("eval_Sem", goal, []).export()
            rpt = ProofReport()
            th = theory.check_proof(prf, rpt)
            output.add_theorem("eval" + str(eval_count), th, prf)
            eval_count += 1
        elif run['ty'] == 'vcg':
            com = parse_com(run['com'])
            pre = Lambda(st, parse_cond(run['pre']))
            post = Lambda(st, parse_cond(run['post']))
            Valid = imp.Valid(natFunT)
            goal = Valid(pre, com, post)
            prf = imp.vcg_solve(goal).export()
            rpt = ProofReport()
            th = theory.check_proof(prf, rpt)
            output.add_theorem("vcg" + str(vcg_count), th, prf)
            vcg_count += 1
        else:
            raise TypeError

    output.export_json()
Exemplo n.º 28
0
    def get_proof_term(self, goal, prevs=None):
        elems = goal.strip_disj()
        preds, concl = elems[:-1], elems[-1]
        args_pair = [(i, j) for i, j in zip(concl.lhs.strip_comb()[1],
                                            concl.rhs.strip_comb()[1])]
        preds_pair = [(i.arg.lhs, i.arg.rhs) for i in preds]
        fun = concl.lhs.head
        pt0 = ProofTerm.reflexive(fun)
        pt_args_assms = []
        for pair in args_pair:
            r_pair = pair[::-1]
            if pair in args_pair:
                pt_args_assms.append(ProofTerm.assume(Eq(*pair)))
            elif r_pair in args_pair:
                pt_args_assms.append(ProofTerm.assume(Eq(*r_pair)))

        pt1 = functools.reduce(lambda x, y: x.combination(y), pt_args_assms,
                               pt0)
        return ProofTerm("imp_to_or", elems[:-1] + [goal], prevs=[pt1])
Exemplo n.º 29
0
def inequality_solve(goal, pts):
    if pts is None:
        pts = []

    if len(pts) == 0:
        macro = ConstInequalityMacro()
        if macro.can_eval(goal, pts):
            th = macro.eval(goal, pts)
            return ProofTerm('const_inequality', args=goal, prevs=pts, th=th)
        else:
            raise TacticException
    elif len(pts) == 1:
        macro = IntervalInequalityMacro()
        try:
            return macro.get_proof_term(goal, pts)
        except ConvException:
            raise TacticException
        else:
            raise TacticException
    else:
        raise TacticException
Exemplo n.º 30
0
def auto_solve(t, pts=None):
    return ProofTerm('auto', args=t, prevs=pts)