230 likes | 386 Views
Scope Logic 工具研究进展. 赵建华 南京大学计算机系 2012.11.3 苏州. 目录. Scope Logic 介绍 工具介绍 基本框架介绍 公式的分类 公式的状态 证明公式的基本方式 自动化 未来的工作. Scope Logic 介绍( 1 ). Scope Logic 介绍( 2 ). Scope Logic 介绍( 3 ). if(a>b) Assert i: {…..} a = a – b Assert j: {a = a@i - b} …. 工具的基本框架. 交互式证明工具,支持一定程度的自动化
E N D
Scope Logic工具研究进展 赵建华 南京大学计算机系 2012.11.3 苏州
目录 • Scope Logic介绍 • 工具介绍 • 基本框架介绍 • 公式的分类 • 公式的状态 • 证明公式的基本方式 • 自动化 • 未来的工作
Scope Logic介绍(3) if(a>b) Assert i: {…..} a = a – b Assert j: {a = a@i - b} …
工具的基本框架 • 交互式证明工具,支持一定程度的自动化 • 使用Proof In Code的方式证明程序 • 允许用户自定义函数,函数的内存范围函数、以及这些函数具有的性质(工具不保证这些函数的正确性) • 公式被写在不同的程序点上, • 一个程序点上可以有多个公式 • 通过渐进的方式证明程序 • 使用SMT Solver Z3进行程序点内部的公式推导
公式的分类 • 强制公式 • 必须证明的公式,以防止零除、数组越界、空指针引用、… • 由工具在打开源程序时自动添加 • 自生公式 • 必然成立的公式,包括if/while语句的conditions,赋值语句之后的等式等 • 部分由工具直接添加,部分由用户输入 • 用户输入的公式
公式的状态 • 由工具或用户插入的公式有两种状态 • 待证明:公式输入后尚未证明 • 已证明:该公式已经可以由其它公式作为依据证明。 • 可以依赖于待证明的公式,所以已证明的公式未必成立 • 如果它依赖的公式被删除/修改,则该公式会重新变成待证明状态 • 在程序入口处的公式可以看作前置条件,不需要证明。 • 当一个程序中所有的公式都处于证明状态时,这些公式就都确定成立了
公式的证明方式 • 自生 • 只要程序运行到程序点i,该公式一定成立 • 注:在赋值/Alloc语句之后的自生公式证明略有变化 • 传播 • 公式p在程序点上成立是因为p在其他程序点上成立 • @证明 • p可以由同一程序点i上的公式p’加上一些@i而得到 • 推导 • 一个公式可以由同一个程序点上的公式推导得到
传播证明(if) • if语句 • P在if语句之前成立,则在两个分支之前都成立 • P在两个分支之后都成立,则在if语句之后成立 • 操作: • 在if之前的公式P被拷贝到两个分支之前 • 这两个公式已证明,且依赖于原来的p • 在某分支之后的公式P被拷贝到 • 另外一个分支之后,待证明 • if语句之后,已经证明,依赖于两个分支之后的P
传播证明(if) ASSERT0( a>0 && b>0; ) while(a>0 && b>0) { ASSERT2( P:a>0 && b>0 ) if(a>b) ASSERT3( ) a = a – (b/a)*a; ASSERT4( ) else ASSERT5( ) b = b – (a/b)*b; ASSERT6( ) ASSERT7( ) } ASSERT7( ) a>0 && b>0 //依赖于P@2) a>0 && b>0 //依赖于P@2 P’:gcd(a,b)==gcd(a@0,b@0) gcd(a,b)==gcd(a@0,b@0) //待证明 gcd(a,b)==gcd(a@0,b@0) //依赖于P’@4和P’@6
传播(while) • while语句 • 如果P在while语句之前、以及循环体之后成立,那么P在循环体之后,以及循环之后都成立 • P实际上是循环不变式 • while语句之前的公式被复制到 • 循环体之后,待证明 • 循环体之前以及while语句之后,依赖于语句之前的公式和语句之后的公式 • 仅当确认P是循环不变式时才可以传播
传播(while) ASSERT0( P:a>0 && b>0; ) while(a>0 && b>0) { ASSERT2( ) if(a>b) ASSERT3( ) a = a – (b/a)*a; ASSERT4( ) else ASSERT5( ) b = b – (a/b)*b; ASSERT6( ) ASSERT7( ) } ASSERT7( ) P:a>=0 && b>=0 //依赖于P@0和P@7 P:a>=0 && b>=0 //待证明 P:a>=0 && b>=0 //依赖于P@0和P@7
传播(复制/alloc) ASSERT0( a>0 && b>0; ) while(a>0 && b>0) { ASSERT2( ) if(a>b) ASSERT3( P:a@3>b; ) a = a – (b/a)*a; ASSERT4( ) else ASSERT5( ) b = b – (a/b)*b; ASSERT6( ) ASSERT7( ) } ASSERT7( ) Q:&a!=&b //待证明 a@3>b //已经证明,依赖于P@3,Q@3
@证明 • 自动判断p能否由同assert中某公式加@i而得到 ASSERT0( a>0 && b>0; ) while(a>0 && b>0) { ASSERT2( ) if(a>b) ASSERT3( P:a>b; ) a = a – (b/a)*a; ASSERT4( ) else ASSERT5( ) b = b – (a/b)*b; ASSERT6( ) ASSERT7( ) } ASSERT7( ) Q:a@3>b //依赖于P
推导 • 只在同程序点上的公式之间进行 • 使用SMT Solver Z3完成
辅助的自动化功能 • @证明方式 • 简单的涉及取地址运算的公式证明和简化 • 基本块内部的证明 • 在受限条件下,能够在基本块入口处生成公式的前置条件 • 数据流分析 • 整数变量的取值范围 • 空指针分析 • 单链表分析
将来的工作 • 完成常见递归数据结构的递归函数和性质的定义 • 单链表,双向链表,二叉树 • 开放数据流分析的接口,增加更多数据流分析功能 • 基于模式的自动证明方式 • 支持局部推导和过程调用