Frama-C是否提供任何工具来证明函数的运行时特性,例如执行时间(可能是指令计数)和堆内存空间(计算为分配的字节数)?
答案 0 :(得分:2)
Frama-C在C级工作。 Metrics插件可以在非常接近原始版本(-metrics -metrics-ast cabs
)的源版本上提供一些指标(例如语句计数),或者在规范化源上(通常称为 Cil)提供一些指标(例如语句计数)它使用的代码)。但是,它不了解汇编代码,因此无法提供有关此级别执行时间的精确信息。
由于编译器优化会影响代码生成,因此Frama-C给出的数字可能会或可能不会接近编译器生成的数字,具体取决于启用的优化,编译器和目标体系结构的已知信息,在一般情况下,Frama-C不能给予任何保证;在特定情况下,可以开发插件来提供一些这样的信息(例如Cost plug-in, mentioned here使用注释来尝试和维护源代码和编译代码之间的一些对应关系,然后使用它们来提供一些执行时间信息)。
有一个选项-metrics-locals-size
,可以粗略估计函数的堆栈内存使用情况。与前一种情况一样,这只是基于源代码的估计。编译器可能会堆栈分配用于计算临时子表达式的临时变量,或者用于寄存器溢出,因此Frama-C给出的数字不能用于最坏情况的堆栈估计。
ACSL支持动态内存分配,因此理论上可以编写有关它的注释。但是,当前的插件并没有提供直接的方法来精确处理这个问题。它可能需要为Eva编写一个新插件或至少一个抽象域。
Eva目前处理动态分配,但可能不足以以有趣的方式估算堆大小。可以为Eva开发一个抽象域来跟踪这些信息(添加malloc
并减去free
s)并计算堆内存空间的过度激活 ,但这需要能够限制包含分配的循环的迭代次数(否则上限将是无限的)。精确度取决于程序的复杂程度。
对于运行时验证,E-ACSL插件已经跟踪了一些堆栈/堆信息使用情况(即使它当前没有导出给用户),所以理论上可以编写一个类似于//@ assert heap_size <= \old(heap_size) + 42;
的断言,并在运行已检测程序时在运行时检查。
答案 1 :(得分:1)
为了补充anol的答案,PathCrawler插件(在线版本可以自由使用,但插件本身是专有的)已用于生成涵盖C函数所有路径的测试用例集。这个article解释了哪些假设可以作为WCET测量的基础,但基本上问题是anol已经提到的问题:没有准确了解编译器和底层硬件所做的工作,这不是Frama-C本身提供的东西,事情会非常粗糙。
显然,最近的一些工作采用了相同的路径,使用PathCrawler生成执行跟踪,覆盖了足够大部分的搜索空间,作为阿姆斯特丹的bachelor project。