2

我正在使用 VST 2.5 和 Coq 8.11.0

forward_call使用非标准调用约定执行函数时出错。最小代码示例:

struct t {
  int t_1;
  int t_2;
};

struct t test_aux() {
  struct t ret;
  ret.t_1 = 1;
  ret.t_2 = 2;
  return ret;
}

void test_f() {
  test_aux();
}

VST 规格:

Require Import VST.floyd.proofauto. 
Require Import example.

Definition Vprog : varspecs. mk_varspecs prog. Defined. Instance CompSpecs : compspecs. make_compspecs prog. Defined.

Open Scope Z.

Definition aux_spec : ident * funspec :=   DECLARE _test_aux
    WITH res : val
    PRE [tptr (Tstruct _t noattr)]
      PROP ()
      PARAMS (res)
      GLOBALS ()
      SEP (data_at_ Tsh (Tstruct _t noattr) res)
    POST [tvoid]
      PROP ()
      LOCAL ()
      SEP (data_at Tsh (Tstruct _t noattr) 
                   (Vint (Int.repr 1), Vint (Int.repr 2)) res).

Definition test_spec : ident * funspec :=   DECLARE _test_f
    WITH temp : val
    PRE []
      PROP ()
      PARAMS ()
      GLOBALS ()
      SEP (data_at_ Tsh (Tstruct _t noattr) temp)
    POST [tvoid]
      PROP ()
      LOCAL ()
      SEP ().

Definition Gprog := ltac:(with_library prog [aux_spec; test_spec]).

Theorem test : semax_body Vprog Gprog f_test_f test_spec. Proof.   start_function.   Fail forward_call (nullval). Admitted.

错误:

Unable to unify  "Tfunction (Tcons (tptr (Tstruct _t noattr)) Tnil)
    tvoid cc_default" with  "Tfunction (Tcons (tptr (Tstruct _t noattr)) Tnil)
    tvoid
    {|
    cc_vararg := false;
    cc_unproto := false;
    cc_structret := true |}".

我不知道这是错误还是预期行为,所以我在这里有几个问题:

1)这是一个错误吗?

2)如果不是,有什么解决方法可以证明这种情况?

更新:

在使用以下解决结构复制限制的解决方法后,我们遇到了这个问题:我们struct_normalize : statement -> statement在 Coq 中定义了一个函数,用逐字段赋值替换结构赋值。因此,我们假设我们正在调用的函数中没有结构复制。也就是说,我们可以test_aux从上面的例子中验证。所以问题是:

  1. forward_call失败只是因为cc_structret := truetest_auxAST中吗?

  2. 鉴于我们对函数进行规范化并从函数体中删除结构复制,相应地更改structret值并继续证明是否安全?

4

1 回答 1

2

不幸的是,VST 不支持结构复制、结构传递或结构返回。另请参阅此问题。所以你不能在不改变它的情况下验证这个程序。

于 2020-04-21T19:52:14.677 回答