#include<stdio.h>
#define N 6
#define M 10
typedef int bool;
#define true 1
#define false 0
unsigned int nondet_uint();
typedef unsigned __CPROVER_bitvector[M] bitvector;
unsigned int zeroTon(unsigned int n) {
unsigned int result = nondet_uint();
__CPROVER_assume(result >=0 && result <=n);
return result ;
};
//Constrine the value between 0 and 1
unsigned int nondet (){
unsigned int num = nondet_uint();
__CPROVER_assume( num>= 0 && num <= 1);
return num;
};
void main() {
unsigned int pos , i, j, k;
unsigned int len = 0;
bool Ch , Ck , C0 ;
bitvector compartment1 , compartment2 , compartment3 , compartment4, compartment5, compartment6;
bitvector nodes[N] = {compartment1, compartment2, compartment3, compartment4, compartment5, compartment6};
// Represent the graph with given topology
unsigned int graph[N][N];
for(i=0;i <N; i++) {
for(j=0;j<N;j++) {
graph[i][j] = nondet();
}
}
unsigned int p[N] ;
unsigned int ticks;
//Make sure that graph is one connected : just find one hamiltonian cycle
//make sure elements are in between node no's and all are distinct
for(i=0; i<N; i++) {
p[i] = zeroTon(5);
}
for(i=0; i <N; i++) {
for(j=0; (j<N) && (j!=i) ; j++) {
if( p[i] != p[j]){
C1 = C1 && 1;
}
else {
C1 = C1 && 0;
}
}
}
//hamiltonian One exists
for(i=0;i<N-1;i++) {
if( graph[p[i]][p[i+1]] == 1) {
Ch = Ch && 1;
}
else {
Ch = Ch && 0;
}
}
len =0;
for(i=0;i<N;i++) {
for(j=0;j<N; j++){
if (graph[i][j] == 1) {
len = len + 1;
}
}
}
//THIS IS GOING IN INFINITE LOOP ?? WHY ??
for(i=0;i<len;i++) {
printf("i'm a disco dancer ");
}
__CPROVER_assert(!(Ch && C1) , "Graph has an ham path");
}
我只是试图获得具有汉密尔顿路径的总节点6的图形。这适用于上面的代码。但是当我尝试使用len即总数时,我会在cbmc run中获得无限的展开。
以上代码运行良好,除非我使用len迭代。 cbmc运行进入无限平仓?谁能解释一下。
答案 0 :(得分:1)
我不确定堆栈溢出的政策,但为了澄清问题,我发布了牛津大学的Martin在CBMC支持论坛上发布的答案。
以上代码运行良好,除非我使用len迭代。 cbmc运行 进入无限循环?谁能解释一下。
简短回答:是的,预计会使用--unwind
答案很长:CBMC对循环边界的检测相对简单;它 只会停止展开循环(没有循环展开限制) 在符号期间,分支条件可以静态简化为false 执行。
因为图的值是非确定性的,所以len的值 将是不确定的。当然,我们从其余的方式知道 代码工作len&lt; = N * N但这不能通过 仅仅简化,因此CBMC没有意识到&#39;这个循环 放松不会自行终止。
为什么我们不让绑定检测变得更聪明?比如说,跟踪间隔 变量?除非你有完整的决策程序,否则我们可以 在那里,你总能找到这样的案例。如果你把一个完整的 决定程序在那里你要么做基于路径的象征 执行,这是我们的symex工具所做的,或者你正在做的事情 增量BMC(我们有可用的工具,它们可能合并 进入下一版CBMC),取决于你是否正在决定 单独或一起展开和断言。
感谢所有人的帮助。