Analisi e Verifica di Programmi
Laboratorio di AVP
Corso di Laurea in Informatica
AA 2009-’10
Tino Cortesi
Analisi e Verifica
Cosa
Individuare proprietà interessanti dei nostri programmi:
Valori prodotti, dipendenze, uso, terminazione
Perché:
Verifica, Debugging
Type checking
Verifica di asserzioni
Ottimizzazioni:
Compile time garbage collection
Ottimizzazioni source-to-source
Come
Le proprietà non banali dei programmi sono indecidibili o
computazionalmente molto costose (NP)
Approssimazioni o condizioni sufficienti
Tino Cortesi
Analisi e Verifica di Programmi
2
L’impatto degli errori run-time
Il 50% degli attacchi alla sicurezza dei sistemi
avviene tramite buffer overruns (Microsoft Security
Bulletins MS02-065, MS04-111 etc.
La maggior parte dei crash in sistemi embedded è
dovuta a overflow di vario tipo.
Tino Cortesi
Analisi e Verifica di Programmi
3
Guyana francese, 4 giugno 1996
Lancio di ARIANE 5
$600 miliardi di dollari bruciati per
un errore del software:
un dato a 64 bit in virgola mobile
venne convertito in un intero a
16 bit con segno, questa operazione
causò una trap del processore:il
numero in virgola mobile era troppo
grande per poter essere rappresentato
con un intero a 16 bit.
(autodistruzione a 39 secondi dal lancio
Tino Cortesi
Analisi e Verifica di Programmi
4
Marte, Mars Polar Lander si spegne il 3 dicembre 1999
per una variabile non inizializzata.
Tino Cortesi
Analisi e Verifica di Programmi
5
Sillabo del corso
Elementi di Teoria dei Reticoli
Interpretazione Astratta
Correttezza dell’analisi - Connessioni di Galois - Widening
Applicazioni a problemi di sicurezza
Applicazioni nell’ambito delle basi di dati
Dataflow Analysis
Liveness Analysis
Reaching Definitions - Constant Folding - Available
Expressions
Basic Blocks - Value Numbering - Alias Analysis
Loop Optimizations
Model Checking
Seminari di ricerca su temi di Analisi e Verifica di Programmi
Progetto: realizzazione guidata di codice per un’analizzatore
statico
Tino Cortesi
Analisi e Verifica di Programmi
6
Bibliografia
F.Nielson, H.R.Nielson, C. Hankin Principles of Static Analysis
Springer Verlag, 2004
B. Berard et al. Systems and Software Verification
Springer Verlag, 1999
B,A,Davey, H,A, Priestly; Introduction to Lattices and Orders,
Cambridge, 2006
Altri testi utili:
A. W. Appel, Modern Compiler Implementation in Java
Cambridge Univ. Press, 1998
Steven Mucknick, Compiler Design Implementation
Morgan Kaufmann Publ., 1997
Articoli su journals o proceedings di conferenze
Tino Cortesi
Analisi e Verifica di Programmi
7
Introduzione
Analisi
Metodo conoscitivo che procede dall’individuazione e
dallo studio dei particolari
Scomposizione di un tutto organico nelle sue parti
Tino Cortesi
Analisi e Verifica di Programmi
9
Analisi Statica di Programmi
Tecniche automatiche per inferire a tempo di
compilazione informazione approssimata sul
comportamento run-time dei programmi
Applicazioni:
Ottimizzazione di compilatori
Verifica automatica dei programmi
Certificazione - validazione del software
Sicurezza
Tino Cortesi
Analisi e Verifica di Programmi
10
Esempio
Cosa voglio verificare: assenza di un certo tipo di
errori run-time (es. overflow)
Come posso astrarre i valori numerici: Intervalli Poliedri (disuguaglianze lineari)
Quale teoria posso usare: Interpretazione astratta
Tino Cortesi
Analisi e Verifica di Programmi
11
Etichettatura
input n;
m:=2;
while n>1 do
m:= m * n;
n:= n-1;
output m;
Tino Cortesi
(1) input n;
(2) m:=2;
while (3) n>1 do
(4) m:= m * n;
(5) n:= n-1;
(6) output m;
Analisi e Verifica di Programmi
12
Grafo di flusso
1
input n
(1) input n;
(2) m:=2;
while (3) n>1 do
(4) m:= m * n;
(5) n:= n-1;
(6) output m;
2
m:= 2
3
n>1
4
m:= m*n
5
n:= n-1
Tino Cortesi
Analisi e Verifica di Programmi
6
output m
13
Possiamo inferire mediante analisi statica
che al punto (6) il valore della variabile m
sarà pari per qualsiasi valore di input n.
1
input n
2
Per fare questo l’analisi dovrà propagare
“parity information”
m:= 2
3
Possiamo assegnare ad ogni variabile uno
dei tre “valori”:
Pari
il valore è
sicuramente pari
Dispari
il valore è
sicuramente dispari
Non_So
il valore può essere
pari oppure dispari
Tino Cortesi
Analisi e Verifica di Programmi
n>1
4
m:= m*n
5
n:= n-1
6
output m
14
(1) n Non_So
(1) input n;
(2)
(2) m:= 2;
while (3) n>1 do
(3)
(4) m:= m * n;
(4)
(5) n:= n - 1;
(5)
(6) output m;
(6)
Tino Cortesi
Analisi e Verifica di Programmi
m
n
m
n
m
n
m
n
m
n
m
Non_So
Non_So
Non_So
Non_So
Pari
Non_So
Pari
Non_So
Pari
Non_So
Pari
15
Questo programma, dato un
intero positivo n, calcola il
doppio del fattoriale: 2 * (n!)
(1) input n;
(2) m:= 2;
while (3) n>1 do
(4) m:= m * n;
n=1
n=2
n=3
n=4
(5) n:= n - 1;
(6) output m;
…
…
…
…
l’output
l’output
l’output
l’output
è
è
è
è
2
4
12
48
pari!
Tino Cortesi
Analisi e Verifica di Programmi
16
(1) input n;
(2) m:= 1;
while (3) n>1 do
(4) m:= m * n;
(5) n:= n - 1;
(6) output m;
Tino Cortesi
Questo programma, dato un
intero positivo n, calcola il
fattoriale: n!
In questo caso l’analisi
precedente non restituisce
nessuna informazione utile sulla
parità di m.
Questo è corretto (per n=1…)
Ma nemmeno se restringiamo
l’input a n pari e n>1 l’analisi è
precisa: in (3) sia n che m sono
Non_So.
Analisi e Verifica di Programmi
17
Precisione e Correttezza
Questa perdita di precisione è una caratteristica comune delle
tecniche di analisi statica
La maggior parte delle proprietà sui programmi che si vogliono
inferire sono indecidibili (o NP-complete), quindi non possiamo
pensare di inferirle con precisione (ed in tempi ragionevoli)
Dobbiamo assicurarci che il risultato dell’analisi sia in ogni caso
corretto:
Se l’analisi dice SI allora sicuramente la proprietà è verificata
Se l’analisi dice NO allora può darsi che la proprietà non sia
verificata
Tino Cortesi
Analisi e Verifica di Programmi
18
Esempio
Sappiamo che il problema della terminazione è
indecidibile (halting problem)
programmi
programmi che
terminano
Tino Cortesi
Analisi e Verifica di Programmi
19
programmi che
potrebbero terminare
programmi che
sicuramente terminano
programmi
programmi che
terminano
Tino Cortesi
Analisi e Verifica di Programmi
20
Precisione e Correttezza
Un’analisi di terminazione può essere quindi di due
tipi:
“Definite”
SI
il programma sicuramente termina
NO
il programma potrebbe non terminare
“Possible”
SI
il programma può terminare
NO
il programma sicuramente non termina
Tino Cortesi
Analisi e Verifica di Programmi
21
Precisione e Correttezza
Le tecniche di analisi che introdurremo si dicono
“semantics-based”.
Questo significa che l’informazione ottenuta
dall’analisi può essere dimostrata corretta rispetto
alla semantica del linguaggio di programmazione
Tino Cortesi
Analisi e Verifica di Programmi
22
Compilatori ottimizzanti
Un compilatore ottimizzante trasforma un programma
per migliorare la sua efficienza senza modificarne
l’output.
Trasformazioni che migliorano l’efficienza:
Allocazione dei registri
Eliminazione delle sotto-espressioni comuni: se una
espressione viene calcolata più di una volta, elimina le
ripetizioni
Eliminazione di “dead-code”: cancella una computazione il
cui risultato non viene mai usato
“Constant folding”: se gli operandi di un’espressione sono
costanti, il calcolo può essere fatto a tempo di compilazione.
Tino Cortesi
Analisi e Verifica di Programmi
23
Escape Analysis
Consideriamo queste due procedure in C:
typedef int A[10000];
typedef A* B;
void esegui1(){
int i;
B b;
b = (A*) malloc(sizeof(A));
for (i=0; i<100; i++)
(*b)[i]=0;
free(b);
}
Tino Cortesi
Analisi e Verifica di Programmi
void esegui2(){
int i;
A a;
for (i=0; i<100; i++)
a[i]=0;
}
24
ambiente
typedef int A[10000];
typedef A* B;
void esegui1(){
int i;
B b;
b = (A*) malloc(sizeof(A));
for (i=0; i<100; i++)
(*b)[i]=0;
free(b);
}
int
i
B
b
memoria
stack
heap
0
L’array viene allocato nello heap e poi eliminato...
Tino Cortesi
Analisi e Verifica di Programmi
25
ambiente
typedef int A[10000];
int
i
A
a
memoria
stack
heap
0
void esegui2(){
int i;
A a;
for (i=0; i<100; i++)
a[i]=0;
}
L’array viene allocato nello stack e poi eliminato...
Tino Cortesi
Analisi e Verifica di Programmi
26
allocare nello heap costa...
for (i=0; i<1000000; i++)
esegui1();
// circa 90 sec
for (i=0; i<1000000; i++)
esegui2();
// circa 35 sec
I programmi “sembrano” uguali, ma l’allocazione nello heap fa sì che il
primo sia tre volte più lento del secondo...
Se riesco a “predire” che una variabile dinamica “non esce” dalla
procedura dov’è introdotta, posso sostituirla con una variabile locale.
Tino Cortesi
Analisi e Verifica di Programmi
27
Esiste il compilatore ottimo?
Definiamo “fully optimizing compiler” un compilatore che
trasforma un programma P nel programma Opt(P) che è il più
piccolo programma con lo stesso output di P.
Dato un programma Q che non produce nessun output e non
termina, Opt(Q) è facile da trovare: è il programma L1: goto L1;
Supponiamo di avere un fully optimizing compiler. Potremmo
usarlo per risolvere il problema della terminazione:
per vedere se esiste un input per il quale P termina, basta
vedere se Opt(P) è il programma L1: goto L1;
Ma sappiamo che il problema della terminazione è indecidibile,
ovvero che non esiste nessun algoritmo che lo risolve. Quindi
non può esistere nemmeno un fully optimizing compiler.
Tino Cortesi
Analisi e Verifica di Programmi
28
Ottimizzazione del codice
Idea: anziché chiedere al programmatore di preoccuparsi
dell’efficienza del programma, si può demandare a un
compilatore ottimizzanti la trasformazione di un codice
inefficiente in uno (equivalente) con performances migliori
Control-Flow
Analysis
Tino Cortesi
Analisi
Analisi e Verifica di Programmi
Trasformazioni
29
Trasformazioni ottimizzanti
Le trasformazioni che un compilatore ottimizzante può operare
seguono principalmente la seguente metodologia:
Analisi: attraversa il grafo di flusso del programma e
raccogli informazioni su cosa può succedere a tempo si
esecuzione
Trasformazioni: modifica il programma per renderlo in
qualche modo più veloce. L’informazione ottenuta dall’analisi
garantisce che il risultato del nuovo programma è uguale a
quello del programma originario
Tino Cortesi
Analisi e Verifica di Programmi
30
Tecniche di Analisi Statica
Per definire un’analisi statica dobbiamo preoccuparci
di:
Come specificarla
Come implementarla efficientemente
Come provarne la correttezza
Tino Cortesi
Analisi e Verifica di Programmi
31
Principali tecniche
Abstract Interpretation
Valutazione Parziale
Dataflow Analysis
Control Flow Analysis
Model Checking
Type Systems
Tino Cortesi
Analisi e Verifica di Programmi
32
Scarica

Analisi e Verifica di Programmi