Пример #1
0
    def testComputeWP(self):
        Q = Var("Q", TFun(natFunT, BoolType))

        test_data = [
            (Assign(zero, Lambda(s, one)),
             Lambda(s, Q(mk_fun_upd(s, zero, one)))),
            (Seq(Assign(zero, Lambda(s, one)), Assign(one, Lambda(s, Nat(2)))),
             Lambda(s, Q(mk_fun_upd(s, zero, one, one, Nat(2))))),
        ]

        for c, P in test_data:
            prf = imp.compute_wp(natFunT, c, Q).export()
            self.assertEqual(theory.check_proof(prf), Thm([], Valid(P, c, Q)))
Пример #2
0
    def testMkAssign(self):
        a, b = Var("a", TFun(NatType, NatType)), Var("b", BoolType)
        var_map = {a: 0, b: 1}
        s = Var("s", gcl.stateT)
        test_data = [
            ({
                a(one): zero
            }, function.mk_fun_upd(s, Para(Ident(zero), one), NatV(zero))),
            ({
                b: one
            }, function.mk_fun_upd(s, Ident(one), NatV(one))),
        ]

        for assign, res in test_data:
            self.assertEqual(gcl.mk_assign(var_map, s, assign), res)
Пример #3
0
    def testPrintFunction(self):
        f = Var("f", TFun(Ta, Ta))
        Tb = TVar('b')
        Tc = TVar('c')
        g = Var('g', TFun(Tb, Tc))
        h = Var('h', TFun(Ta, Tb))
        test_data = [
            (function.mk_fun_upd(f, a, b), "(f)(a := b)"),
            (function.mk_fun_upd(f, a, b, b, a), "(f)(a := b, b := a)"),
            (function.mk_comp(g, h), "g O h"),
            (function.mk_comp(g, h)(a), "(g O h) a"),
            (function.mk_const_fun(NatType, nat.zero), "%x::nat. (0::nat)"),
        ]

        basic.load_theory('function')
        with global_setting(unicode=False):
            for t, s in test_data:
                self.assertEqual(printer.print_term(t), s)
Пример #4
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()
Пример #5
0
    def testProveAvalIFail(self):
        s = fun_upd_of_seq(1, 7)
        s2 = Var("s2", TFun(NatType, NatType))
        s3 = function.mk_fun_upd(s2, zero, one)
        macro = expr.prove_avalI_macro()

        # Value does not match
        self.assertFalse(macro.can_eval(expr.avalI(s, V(one), Nat(5))))

        # State cannot be evaluated
        self.assertFalse(macro.can_eval(expr.avalI(s2, V(one), Nat(5))))
        self.assertFalse(macro.can_eval(expr.avalI(s3, V(one), Nat(5))))

        # Goal is not avalI
        self.assertFalse(macro.can_eval(Eq(V(one), N(zero))))
Пример #6
0
def mk_assign(var_map, s, assigns):
    """Given a dictionary of assignments, form the corresponding term.

    Example: given var_map {a: 0, b: 1}, where a is a function
    and b is a scalar.

    mk_assign(var_map, s, {a(i): 2}) = (s)(Para (Ident 0) i := 2)
    mk_assign(var_map, s, {b: 1}) = (s)(Ident 1 := 1)

    """
    assign_args = []
    for k, v in assigns.items():
        k2 = convert_term(var_map, s, k)
        assert k2.fun == s, "mk_assign: key is not an identifer."
        assign_args.append(k2.arg)
        assign_args.append(convert_term(var_map, s, v))

    return function.mk_fun_upd(s, *assign_args)
Пример #7
0
def compute_wp(T, c, Q):
    """Compute the weakest precondition for the given command
    and postcondition. Here c is the program and Q is the postcondition.
    The computation is by case analysis on the form of c. The function
    returns a proof term showing [...] |- Valid P c Q, where P is the
    computed precondition, and [...] contains the additional subgoals.

    """
    if c.is_const("Skip"):  # Skip
        return apply_theorem("skip_rule", concl=Valid(T)(Q, c, Q))
    elif c.is_comb("Assign", 2):  # Assign a b
        a, b = c.args
        s = Var("s", T)
        P2 = Lambda(s, Q(function.mk_fun_upd(s, a, b(s).beta_conv())))
        return apply_theorem("assign_rule",
                             inst=Inst(b=b),
                             concl=Valid(T)(P2, c, Q))
    elif c.is_comb("Seq", 2):  # Seq c1 c2
        c1, c2 = c.args
        wp1 = compute_wp(T, c2, Q)  # Valid Q' c2 Q
        wp2 = compute_wp(T, c1, wp1.prop.args[0])  # Valid Q'' c1 Q'
        return apply_theorem("seq_rule", wp2, wp1)
    elif c.is_comb("Cond", 3):  # Cond b c1 c2
        b, c1, c2 = c.args
        wp1 = compute_wp(T, c1, Q)
        wp2 = compute_wp(T, c2, Q)
        res = apply_theorem("if_rule", wp1, wp2, inst=Inst(b=b))
        return res
    elif c.is_comb("While", 3):  # While b I c
        _, I, _ = c.args
        pt = apply_theorem("while_rule", concl=Valid(T)(I, c, Q))
        pt0 = ProofTerm.assume(pt.assums[0])
        pt1 = vcg(T, pt.assums[1])
        return pt.implies_elim(pt0, pt1)
    else:
        raise NotImplementedError
Пример #8
0
 def testStripFunUpd(self):
     self.assertEqual(strip_fun_upd(f), (f, []))
     self.assertEqual(strip_fun_upd(mk_fun_upd(f, a1, b1)), (f, [(a1, b1)]))
     self.assertEqual(strip_fun_upd(mk_fun_upd(f, a1, b1, a2, b2)),
                      (f, [(a1, b1), (a2, b2)]))
Пример #9
0
 def testMkFunUpd(self):
     self.assertEqual(mk_fun_upd(f, a1, b1, a2, b2),
                      mk_fun_upd(mk_fun_upd(f, a1, b1), a2, b2))
Пример #10
0
def fun_upd_of_seq(*ns):
    return mk_fun_upd(function.mk_const_fun(NatType, zero),
                      *[Nat(n) for n in ns])