I'm using VST 2.5 and Coq 8.11.0
Got an error while doing forward_call
on function with non-standard calling convention.
Minimal code example:
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 specs:
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.
Error:
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 |}".
I don't know if this is a bug or intended behavior, so I have a few questions here:
1) Is this a bug?
2) If not, what workarounds exists to prove such cases?
UPDATE:
We ran into this problem after using the following workaround around the struct-copying restriction: we define a struct_normalize : statement -> statement
function in Coq that replaces struct assignments with field-by-field assignments. Hence we are working under the assumption that there is no struct copy-ing in the function we are calling. That is, we can verify the test_aux
from the example above. So the questions are:
Does forward_call
fail only because cc_structret := true
in the test_aux
AST?
Given that we normalize the functions and remove stucture-copying from the bodies of the functions, is it safe to change structret
value accordingly and proceed with the proof?
Unfortunately, VST does not support struct-copying, struct-passing, or struct-returning. See also this question. So you can't verify this program without changing it.