2016-11-18 21 views
0

我正在使用frama-c鋁-20160502版本,我想在大型程序中找到依賴關係。在命令行中使用選項-deps時,我發現缺少一些依賴關係。特別是當幾個條件加入一個條件時,只要一個條件爲假,依賴性分析就會停止。在這個例子中的位置:甚至對「死枝」做Frama-c顯示依賴關係

#include<stdio.h> 
#include<stdbool.h> 

/*Global variable definitions*/ 
bool A = true; 
bool B = false; 
bool C = true; 
bool X; 
bool Y; 

bool res; 


void main(){ 

     if (A && B && C) { 
       res = X; 
     }else res = Y; 
} 

當我嘗試:frama-c -deps program.c

郵資顯示以下依存關係:

[從] ======相關內容COMPUTED ======

這些依賴關係在終止用於執行終止成立:

[從]功能主要: RES FROM A; B; ÿ

[從] ====== DEPENDENCIES ======

OF END因此它不會達到的條件C,因爲已經B是假的。

我不知道是否有辦法告訴frama計算所有依賴項,即使條件未滿足。我嘗試使用-slevel選項,但沒有結果。我知道有一種方法可以使用間隔Frama_C_interval(0,1),但是當我使用它時,使用此函數的變量不會顯示在依賴項中。我想得到X和Y依賴於A,B,C和水平取決於A,B,C,X,Y

任何想法?

+0

請注意,您稱之爲「死分支」的語法結構對程序執行沒有語義影響(例如'&& true')。因爲Frama-C的依賴分析是基於語義的,所以你可能不得不「欺騙」他們考慮外部分支(例如'volatile','Frama_C_interval'等),或者嘗試設計一個語法分析(例如用一個訪客)可以計算你的語法依賴的概念。 – anol

回答

0

From插件使用Value分析插件的結果。在示例中,AB的值是足夠精確的該值能夠推斷到達C之前該條件完全確定(因爲&&操作者懶惰地評估,從左至右),因此C從不影響的結果,並因此不是From的觀點的依賴。

不幸的是,Frama_C_interval不能直接在全局初始化中使用:

user error: Call to Frama_C_interval in constant. 

你可以,但是,使用 「黑客」(並不總是最好的解決方案,但在這裏工作):

volatile bool nondet; 
bool A = nondet; 
bool B = nondet; 
bool C = nondet; 
... 

請注意,因爲nondetvolatile,所以爲每個變量A,BC分配了不同的非確定性值。

在這種情況下,價值必須考慮條件句的兩個分支,因此C成爲你的榜樣的依賴,因爲它有可能會Cmain執行過程中被讀取。然後,您將有:

 These dependencies hold at termination for the executions that terminate: 
[from] Function main: 
    res FROM A; B; C; X; Y 

注意一些插件與volatile變量打交道時需要特殊的處理,所以這並不總是最好的解決方案。

然而,這隻處理一些種類的依賴關係。正如Value Analysis user manual的第6章所述,From插件計算功能性,命令性和操作性依賴性。這些做而不是包括間接控制依賴關係,正如你提到的那些,這些如X from A, B, C。對於那些,你需要PDG(程序依賴圖)插件,但它目前沒有依賴關係的文本輸出。您可以使用-pdg來計算它,然後使用-pdg-dot <file>以點(graphviz)格式導出依賴關係圖。這是我爲你的main功能(使用揮發性黑客如前所述):

PDG for the main function

最後,作爲一個側面說明:-slevel主要是用來提高精度,但在你的例子中,你已經有太多精度(也就是說,Value已經能夠推斷C永遠不會被main讀取)。

+0

非常感謝您的回答,這非常有幫助。我嘗試了-pdg選項,但對於較大的程序來說,通過眼睛來查找依賴關係有點麻煩。然而如果用於每個變量,則易失性定義非常有趣且已解決問題。 –

+0

不幸的是,這個解決方案似乎只能部分工作,因爲在執行過程中每當A,B或C的值發生變化時,懶惰評估就會使依賴關係消失。因此,我需要以某種方式設置這個懶惰的評估在一個更一般的解決方案,以Frama-C遵循所有可能的執行路徑。 –

+0

將A,B和C自己聲明爲「volatile」是否有意義?對它們的每一次讀/寫都將是非確定性的。但是這可能會改變你的程序的語義,而這種方式並不是你想要的。 – anol