一种基于符号执行的内存泄漏检测方法技术

技术编号:13421327 阅读:66 留言:0更新日期:2016-07-28 12:47
本发明专利技术针对内存泄漏缺陷,提出一种基于符号执行的内存泄漏检测方法,首先对于被测试的源代码,使用静态分析工具处理,得到静态内存泄漏警报;然后,把用源代码和内存泄漏警报,同时输入插桩器,得到插桩后的代码。接着,把插桩后的代码输入测试用例生成模块,生成大量测试用例并执行所有测试用例。每个测试用例运行结束后都有对目标内存对象泄漏情况汇报,最后综合所有测试执行的输出,对内存泄漏测试结果进行判定。本方法解决了静态内存泄漏分析的误报问题和动态测试的漏报问题,并利用符号执行技术生成测试用例,减少了静态分析内存泄漏结果的人工验证工作。提高了动态执行的效率。

【技术实现步骤摘要】
一种基于符号执行的内存泄漏检测方法
本专利技术属于软件工程和软件测试领域,尤其涉及一种软件内存泄漏检测方法,主要利用符号执行技术来解决静态内存泄漏分析的误报问题和动态测试的漏报问题。
技术介绍
在C/C++程序中,内存泄漏是指程序中动态分配的内存由于某种原因没有释放,导致系统无法再次分配该内存。内存泄漏分为两种情况:引用丢失和忘记释放。引用丢失是指失去了所有指向动态分配内存对象的指针或引用,使得该内存对象不可达。忘记释放是指动态分配的内存虽然有指针或引用可达,但在程序运行余下部分没有访问和释放。静态分析内存泄漏不用实际运行程序,而是分析源代码的结构来检测内存泄漏。静态分析一般是先为代码建立模型,定义内存泄漏缺陷的模式,然后在代码中查询匹配预定义的错误模式,得到错误报告。动态分析方法通过实时监控内存的分配和访问状态来实现对内存泄漏缺陷的检测。一般采用插桩的方式在测试程序中插入监视代码,检查内存的分配,使用和释放情况。符号执行指的是使用符号变量代替具体变量,不执行程序的前提下模拟程序执行来进行相关分析的技术。相对于给程序一个普通的输入,符号执行提供符号来表示任意的输入值。程序执行时把具体的操作替换为相应的符号操作。当程序运行到基于符号化变量的分支时,系统同时沿着两条路径运行,并在每条路径上维护一个称为路径条件的约束集合。路径条件表示程序沿着这条路径执行应满足的约束。当一条路径终止或遇到错误,把路径条件解析成具体值,能得到一个测试用例。如果把这个测试用例输入到原始的测试代码,它能沿着相同的路径执行并触发同样的错误。LLVM是一个模块化和可重用的编译器的工具集合。它包含大量对C/C++源代码,中间代码的编译和优化处理工具。LLVMPass是一个用来实现程序的转换和优化的框架。Pass以LLVM中间代码作为输入,提供了大量API让程序员能够在中间代码级别上查找,插入和删除指令。静态内存泄漏分析是按照代码的结构模型和规则来查找内存泄漏,由于模型的不完备性,只能尽可能多找到疑似内存泄漏的情况,因此会有很多误报。大量的静态分析的疑似内存泄漏警报,需要逐条人工验证,这个过程费时费力。而动态测试内存泄漏的方法,需要测试用例驱动测试,没有测试用例经过的代码就检查不出是否泄漏。而且由于没有目标,动态测试需要对整个被测代码插桩,运行效率不高。
技术实现思路
针对现有技术中存在的内存泄漏缺陷,本专利技术利用静态分析指导动态测试的混合方法,提出一种基于符号执行的内存泄漏检测方法,解决静态内存泄漏分析的误报问题和动态测试的漏报问题。为了实现本专利技术的专利技术目的,本专利技术的技术方案为,一种基于符号执行的内存泄漏检测方法:首先对于被测试的源代码,使用静态分析工具处理,得到内存泄漏警报;然后把源代码和内存泄漏警报,同时输入插桩器,得到插桩后的代码;接着,把插桩后的代码输入测试用例生成模块,生成大量测试用例并执行所有测试用例。每个测试用例运行结束后都有对目标内存泄漏情况汇报,最后综合所有测试执行的输出,对内存泄漏测试结果进行判定。判定结果是在静态分析报告的基础上,进一步把内存泄漏分为MUST-LEAK,LIKELY-NOT-LEAK,BLOAT和MAY-LEAK四类。其中,MUST-LEAK类型表示该内存一定泄漏;LIKELY-NOT-LEAK表示该泄漏很可能是错的;BLOAT表示虽然该内存不太可能泄漏,但在疑似泄漏点之后没有访问,应该提前释放;最后没有测试用例覆盖到其路径的泄漏归为MAY-LEAK;最后只有MAY-LEAK类别需要人工验证。本专利技术所述的基于符号执行的内存泄漏检测方法步骤如下:1)对于被测试的源代码,使用静态分析工具处理,得到内存泄漏警报;11)对静态分析工具输出的内存泄漏警报信息进行预处理,得到内存泄漏的位置信息和程序路径,整理成能识别的格式并保存在文件中;12)一个静态分析内存泄漏警报记为p=(a,lb11,lb22,…,e),包括内存分配点a,分支点lb和泄漏点e。分支点lb的上标b∈{T,F},分别表示if语句的true分支和false分支。警报表示在程序点a分配的目标内存在e点之后可能失去所有引用发生内存泄漏;2)对被测代码进行插桩,首先读取预处理过的内存泄漏警报,在代码中可能发生内存泄漏的位置进行插桩,记录所有内存的创建、访问和释放信息,并判断程序执行是否完整经过目标路径;21)在程序开头和结尾的插桩分别是做初始化工作(内存泄漏报告的读取,数据结构的创建等)和收尾工作(结果输出);22)在所有目标内存分配指令后插桩,记录目标内存的创建信息;23)在所有内存释放指令后插桩,判断目标内存是否释放;24)在所有内存访问指令后插桩,判断目标内存释放访问过;3)通过代码插桩,对程序的执行路径进行跟踪,来检查程序执行时经过了哪些目标路径,具体步骤如下:31)读取所有内存泄漏警报的路径,每个路径点包含所在源代码文件名、行号和类型;32)遍历被测代码所有指令,如果该指令所在文件名和行号属于目标路径,则插入函数调用指令调用插桩函数reportAtFortifyNode(文件名,行号);33)在reportAtFortifyNode(文件名,行号)中设置对应路径点执行到的标记,在所有内存泄漏报告的路径点,判断执行是否完整经过目标路径;4)通过插桩代码,对目标内存进行跟踪和记录,来判断在一次测试执行后,该目标内存是否被访问和释放。定义一个状态机来描述目标内存的状态转换(见说明书附图3):41)每个目标内存在刚创建时处于CREATED状态;42)如果之后程序执行经过它所在的内存泄漏路径上的泄漏点e,就把状态转换为LP;43)在LP之后,如果程序依然访问了该目标内存,则把它的状态设置为USEDAFTERLP;44)接着释放了该目标内存,则该目标内存没有泄漏,变成状态LNL(LIKELY-NOT-LEAK);45)如果目标内存在LP之后没有被访问,最后释放了,则进入状态BLOAT;46)还有一种情况是,目标内存在程序还没执行到泄漏点时就释放了。把它标记为DFREED(直接释放)。5)基于符号执行技术生成能够覆盖这些内存泄漏路径的测试用例,并运行测试用例,分析得到针对内存泄漏缺陷的测试结果。在静态分析报告的基础上,进一步把内存泄漏分为MUST-LEAK,LIKELY-NOT-LEAK,BLOAT和MAY-LEAK四类。其中,MUST-LEAK类型表示该内存一定泄漏;LIKELY-NOT-LEAK表示该泄漏很可能是错的;BLOAT表示虽然该内存不太可能泄漏,但在疑似泄漏点之后没有访问,应该提前释放;最后没有测试用例覆盖到其路径的泄漏归为MAY-LEAK;最后只有MAY-LEAK类别需要人工验证。51)对一个警报,检查a分配的目标内存,在程序的结尾是否释放。只要存在一个测试用例的运行,经过完整的目标路径p之后,a点分配的目标内存在程序结尾处没有释放,则该内存一定泄漏,该警报就被归类为MUST-LEAK;52)如果对每个测试用例的执行,在程序点a分配的目标内存在疑似的泄漏点e之后仍然被访问到,并且在程序结尾处都释放了,那么该内存发生泄漏的可能性就很低。无法保证该内存真的不泄漏,因此,把满足这种情况的测试结果称为LIKELY-NOT-LEAK(很可能不泄本文档来自技高网
...

【技术保护点】
一种基于符号执行的内存泄漏检测方法,其特征在于,包括以下步骤:步骤1,对于被测试的源代码,使用静态分析工具处理,得到内存泄漏警报;步骤2,对被测代码插桩:读取所述内存泄漏警报,在代码中可能发生内存泄漏的位置进行插桩,记录所有内存的创建、访问和释放信息;步骤3,通过对被测代码插桩,对程序的执行路径进行跟踪,来检查程序执行时经过了哪些目标路径;步骤4,根据插桩的输出结果,用一个状态机来判断在一次测试执行后,该目标内存是否被访问和释放;步骤5,基于符号执行技术生成能够覆盖内存泄漏路径的测试用例,并运行测试用例,对内存泄漏的测试结果进行判定。

【技术特征摘要】
1.一种基于符号执行的内存泄漏检测方法,其特征在于,包括以下步骤:步骤1,对于被测试的源代码,使用静态分析工具处理,得到内存泄漏警报;步骤2,对被测代码插桩:读取所述内存泄漏警报,在代码中可能发生内存泄漏的位置进行插桩,记录所有内存的创建、访问和释放信息;步骤3,通过对被测代码插桩,对程序的执行路径进行跟踪,来检查程序执行时经过了哪些目标路径;步骤4,根据插桩的输出结果,用一个状态机来判断在一次测试执行后,该目标内存是否被访问和释放;步骤5,基于符号执行技术生成能够覆盖内存泄漏路径的测试用例,并运行测试用例,对内存泄漏的测试结果进行判定;内存泄漏判定结果包括:MUST-LEAK,LIKELY-NOT-LEAK,BLOAT和MAY-LEAK;其中MAY-LEAK类别需要人工验证;MUST-LEAK类型表示“该内存一定泄漏”;LIKELY-NOT-LEAK表示“该泄漏很可能是错的”;BLOAT表示“虽然该内存不太可能泄漏,但在疑似泄漏点之后没有访问,应该提前释放”;最后“没有测试用例覆盖到其路径的泄漏”归为MAY-LEAK;内存泄漏判定步骤为:对所述内存泄漏警报,检查内存分配点a分配的目标内存在程序的结尾是否释放:若存在一个测试用例的运行,经过完整的目标路径p之后,a点分配的目标内存在程序结尾处没有释放,则其一定发生内存泄漏,该警报就被归类为MUST-LEAK;若对每个测试用例的执行,在a点分配的目标内存在疑似的泄漏点e之后仍然被访问到,并且在程序结尾处都释放了,那么其有较低的可能性发生泄漏,称为LIKELY-NOT-LEAK;若a点分配的目标内存最终释放,但在疑似的泄漏点e之后没有访问过,这类内存对象占据着有限的内存资源却没有使用,也会对程序的运行效率造成影响,称为BLOAT;若所有的测试用例均没有完整地覆盖所述内存泄漏警报对应的内存泄漏路径,则称为MAY-LEAK。2.根据权利要求1所述的内存泄漏检测方法,其特征在于,步骤1进一步包括:步骤11,对所述内存泄漏警报进行预处理,得到内存泄漏的位置...

【专利技术属性】
技术研发人员:王兵邓波刘宇李海龙战茅许帅施寅生洪斌周严王林章
申请(专利权)人:北京系统工程研究所南京大学
类型:发明
国别省市:北京;11

网友询问留言 已有0条评论
  • 还没有人留言评论。发表了对其他浏览者有用的留言会获得科技券。

1