这次我证明函数调用其他。vars.c
:
int pure0 ()
{
return 0;
}
int get0(int* arr)
{
int z = pure0();
return 0;
}
我的证明开始 - verif_vars.v
:
Require Import floyd.proofauto.
Require Import vars.
Local Open Scope logic.
Local Open Scope Z.
Definition get0_spec :=
DECLARE _get0
WITH sh : share, arr : Z->val, varr : val
PRE [_arr OF (tptr tint)]
PROP ()
LOCAL (`(eq varr) (eval_id _arr);
`isptr (eval_id _arr))
SEP (`(array_at tint sh arr 0 100) (eval_id _arr))
POST [tint] `(array_at tint sh arr 0 100 varr).
Definition pure0_spec :=
DECLARE _pure0
WITH sh : share
PRE []
PROP ()
LOCAL ()
SEP ()
POST [tint] local(`(eq (Vint (Int.repr 0))) retval).
Definition Vprog : varspecs := nil.
Definition Gprog : funspecs := get0_spec :: pure0_spec ::nil.
Lemma body_pure0: semax_body Vprog Gprog f_pure0 pure0_spec.
Proof.
start_function.
forward.
Qed.
Lemma body_get0: semax_body Vprog Gprog f_get0 get0_spec.
Proof.
start_function.
name arrarg _arr.
forward_call (sh).
entailer!.
这导致了目标:
2 subgoals, subgoal 1 (ID 566)
Espec : OracleKind
sh : share
arr : Z -> val
varr : val
Delta := abbreviate : tycontext
POSTCONDITION := abbreviate : ret_assert
MORE_COMMANDS := abbreviate : statement
Struct_env := abbreviate : type_id_env.type_id_env
arrarg : name _arr
============================
Forall (closed_wrt_vars (eq _z')) [`(array_at tint sh arr 0 100 varr)]
subgoal 2 (ID 567) is:
DO_THE_after_call_TACTIC_NOW
我想它说明了函数调用不会改变arr
内容,这对我来说很明显。
我能用这个目标做什么?哪种策略适用于此,该声明的确切含义是什么?我是否应该丰富pure0
规范以某种方式指出它不会修改任何内容?