Automated tests Frama-C警告:缺少assigns子句(改为assigns';everything')

Automated tests Frama-C警告:缺少assigns子句(改为assigns';everything'),automated-tests,frama-c,acsl,Automated Tests,Frama C,Acsl,我正在用frama-c测试这个小程序,我不断得到同样的错误。我不知道这是什么意思。我对分配一切意味着什么特别困惑 以下是带有ACSL注释的相关代码: // assuming n is nonnegative and even, f returns n /*@ requires n>=0; */ int f(int n) { int i=0; while (i<n) { i+=2; } //@ assert i==n; return i; } 首先,您

我正在用frama-c测试这个小程序,我不断得到同样的错误。我不知道这是什么意思。我对分配一切意味着什么特别困惑

以下是带有ACSL注释的相关代码:

// assuming n is nonnegative and even, f returns n

/*@ requires n>=0;
*/

int f(int n) {
  int i=0;
  while (i<n) {
    i+=2;
  }
  //@ assert i==n;
  return i;
}

首先,您的属性不是真实的,因为您不要求
n
在函数的前提条件中为偶数。因此,我将向您展示如何在循环体中使用
I+=1
证明程序的变体

assigns
子句是WP要求您为每个循环和每个外部函数调用指定的内容。它必须包含可由循环(或函数)修改的所有内存位置(即变量)的列表。它需要这样才能知道循环不会修改其他所有内容。特别是,在此程序中,WP需要知道,虽然循环中
i
的值可能会改变,但
n
的值不会改变。但是,如果您不告诉它是这种情况,它会假定循环可以分配“一切”,包括
n

要指定此项,可以在循环的正上方插入以下注释:

/*@ loop assigns i; */
如果您尝试证明这一点(在GUI中),您将看到WP可以验证这个assigns子句

然而,您在循环后的断言仍然不能用这一点来证明。这是因为除了assigns子句之外,每个循环还必须有一个循环不变量:在循环的每次迭代之前和之后都是真的。选择正确且足够强大的循环不变量是一门黑暗的艺术,但一般来说,不变量必须是这样的东西,一旦循环条件为false且循环终止,我们就可以在循环结束后得出断言

也就是说,我们想要一个具有以下属性的公式
I
作为不变量:

I && !(i < n)  ==>  i == n
这是自动验证的:

[wp] warning: Missing RTE guards
[wp] 4 goals scheduled
[wp] Proved goals:    4 / 4
    Qed:             4

首先,您的属性不是真实的,因为您不要求
n
在函数的前提条件中为偶数。因此,我将向您展示如何在循环体中使用
I+=1
证明程序的变体

assigns
子句是WP要求您为每个循环和每个外部函数调用指定的内容。它必须包含可由循环(或函数)修改的所有内存位置(即变量)的列表。它需要这样才能知道循环不会修改其他所有内容。特别是,在此程序中,WP需要知道,虽然循环中
i
的值可能会改变,但
n
的值不会改变。但是,如果您不告诉它是这种情况,它会假定循环可以分配“一切”,包括
n

要指定此项,可以在循环的正上方插入以下注释:

/*@ loop assigns i; */
如果您尝试证明这一点(在GUI中),您将看到WP可以验证这个assigns子句

然而,您在循环后的断言仍然不能用这一点来证明。这是因为除了assigns子句之外,每个循环还必须有一个循环不变量:在循环的每次迭代之前和之后都是真的。选择正确且足够强大的循环不变量是一门黑暗的艺术,但一般来说,不变量必须是这样的东西,一旦循环条件为false且循环终止,我们就可以在循环结束后得出断言

也就是说,我们想要一个具有以下属性的公式
I
作为不变量:

I && !(i < n)  ==>  i == n
这是自动验证的:

[wp] warning: Missing RTE guards
[wp] 4 goals scheduled
[wp] Proved goals:    4 / 4
    Qed:             4