Предположим, мы имеем следующий C аннотированный код:Доказывающий выходы SMT «неизвестно», несмотря на сильные доказанными утверждения
#define L 3
int a[L] = {0};
/*@ requires \valid(a+(0..(L - 1)));
ensures \forall int j; 0 <= j < L ==> (a[j] == j); */
int main() {
int i = 0;
/*@ loop assigns i, a[0..(i-1)];
loop invariant inv1: 0 <= i <= L;
loop invariant inv2:
\forall int k; 0 <= k < i ==> a[k] == k;
*/
while (i < L) {
a[i] = i;
i++;
}
/*@ assert final_progress:
\forall int k; 0 < k < L ==> a[k] == a[k-1] + 1;
assert final_c:
a[2] == a[1] - 1; */
return 0;
}
Почему Alt-Ergo/Z3 дает «неизвестно» или тайм-ауты для final_c утверждения, несмотря на то, что final_progress заявление было доказано? Мне бы очень хотелось увидеть «Недействительно» для таких явно (с точки зрения пользователя) недопустимых утверждений.
$ frama-c -wp -wp-rte -wp-prover z3 test2.c
..
[wp] [z3] Goal typed_main_assert_final_c : Unknown (455ms)
$ frama-c -wp -wp-rte -wp-prover alt-ergo test2.c
..
[wp] [Alt-Ergo] Goal typed_main_assert_final_c : Timeout
Я отмечаю этот вопрос как решенный, но все же я не понимаю почему так. После того, как SMT-решатель сможет получить sat/unsat/unknown. Возможно, это потому, что решатель должен пройти все возможные количественные значения, чтобы претендовать на что-то как «недействительное», но я сомневаюсь, что это практично. – Evgeniy
@Evgeniy: Вы правы, что это возможно. Это просто, что плагин WP не поддерживает свойства маркировки как недействительные. Например, плагин Value Analysis поддерживает свойства маркировки как недопустимые. –
@ Evgeniy: На самом деле, похоже, в руководстве имеется опция '-wp-unsat-model '. Тем не менее, я получаю сообщение об ошибке при попытке использовать этот параметр с помощью Frama-C Sodium: '[kernel] user error: option \' -wp-unsat-model 'неизвестно. ' –