首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >介绍ACSL/Frama-C的数学函数规范

介绍ACSL/Frama-C的数学函数规范
EN

Stack Overflow用户
提问于 2014-06-24 15:29:54
回答 1查看 522关注 0票数 4

是否可以在ACSL中为通常在-lm编译时调用的函数实现规范,如sqrt?我把它用于Frama的插件WP。

这里有一个小例子来说明我想做什么。

代码语言:javascript
复制
/*@ requires sqrt_spec: \forall float x; 
             \model(sqrt(x)) * \model(sqrt(x)) == \model(x);  
    ensures [...] */  

void f (...) {
double y = sqrt x;
[...]
}

显然,如果我这样做,WP会哭,因为当我在注释中使用sqrt时,sqrt并不存在。

内核用户错误:注释中的未绑定函数sqrt

所以我想定义一个抽象的sqrt,但是我的测试都没有用:

代码语言:javascript
复制
#define sqrt(x) (...)

对于这件事,我看不出我能做什么(.)因为我想要一个抽象的定义,而不是重新实现整个浮动sqrt。

代码语言:javascript
复制
/*@  axiomatic SqrtSpec {
logic real sqrt (real x);
} */

而这次解决不了我的问题:

函数sqrt既没有代码也没有规范,从原型生成默认赋值。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2014-06-24 19:02:50

Frama有一个内置逻辑函数\sqrt,它对real号进行操作(请注意,内置函数和谓词通常以反斜杠\作为前缀,以避免与现有C标识符发生冲突)。尽管如此,为sqrt提供一个公理定义并不难。

代码语言:javascript
复制
axiomatic Sqrt {
  logic real sqrt(real);
  axiom real_def: \forall real x; x >= 0 ==> x == sqrt(x) * sqrt(x);
}

另外,请注意,Gappa (http://gappa.gforge.inria.fr/)是唯一知道浮点(相对于实数)的自动验证程序,但是即使您已经安装了它,完成处理浮点计算的验证义务也是非常困难的。

更新

如果您想将double sqrt(double) (和/或float sqrt(float))公理化,其思想将是描述相对于在reals上操作的\sqrt结果的错误,即类似于

代码语言:javascript
复制
axiomatic Sqrt {
  logic float sqrt(float sqrt);
  axiom sqrt_def: \forall float x; \is_finite(x) && x>= 0.0 ==> sqrt(x) ==  (float)\sqrt(x);
}

当然,这种描述可能有点限制性。你可能想要像\abs(sqrt(x) - \sqrt(x)) <= err_bound * \sqrt(x)这样的东西,但我必须承认,我在浮点计算方面不够流利,无法从头顶上给出适当的err_bound值。

更新2

假设您有一个具有您想要的属性的逻辑 sqrt,那么说C sqrt具有相同的行为只是给它一个契约的问题:

代码语言:javascript
复制
/*@ requires \is_finite(x); //unless you want to play with NaN or infinities 
    assigns \nothing;
    ensures \result == sqrt(x);
 */
extern float sqrt(float x);

函数的规范在链接阶段被合并,所以这个契约是用math.h编写的(注意:在标准的标头sqrt中接受(并返回)一个double,是sqrtffloat上操作)还是在您自己的文件中。

票数 4
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/24390651

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档