基于中间语言的+JNI内存泄漏检查

合集下载

内存泄漏检测原理

内存泄漏检测原理

内存泄漏检测原理
内存泄漏是指在程序运行时,由于程序中的某些代码未能正确释放已经分配的内存空间,导致系统中存在大量没有被使用的内存空间,从而导致系统性能下降、崩溃甚至瘫痪的现象。

为了避免内存泄漏对系统造成的影响,我们需要进行内存泄漏检测。

内存泄漏检测的原理是通过跟踪程序运行时的内存分配和释放
情况,检测出程序中存在的内存泄漏问题。

一般来说,内存泄漏检测器会在程序运行时记录下每次内存分配和释放的情况,并将它们保存在一个内存分配表中。

当程序结束时,内存泄漏检测器会比对内存分配表和内存释放表,如果发现有未被释放的内存,则会提示用户程序中存在内存泄漏问题。

在实际应用中,内存泄漏检测器可以通过静态分析和动态分析两种方式进行检测。

静态分析是指在编译阶段对程序进行分析,通过检查变量的生命周期和内存分配与释放的情况,来判断程序中是否存在内存泄漏问题。

动态分析则是在程序运行时对程序进行监控,实时监测内存分配和释放的情况,以及内存使用情况,来检测程序中是否存在内存泄漏问题。

总之,内存泄漏检测是保证程序运行稳定和性能优化的重要手段。

通过使用内存泄漏检测器,我们可以及时发现和解决程序中的内存泄漏问题,提高程序的稳定性和性能,从而提高用户的体验。

- 1 -。

内存泄漏检测原理

内存泄漏检测原理

内存泄漏检测原理
内存泄漏是指程序在分配内存后,没有正确释放,导致程序运行
时内存占用量不断增加,直到系统无法再分配新的内存而崩溃。

因此,内存泄漏是程序开发过程中常见的问题。

为了解决内存泄漏问题,我们需要通过一些工具和技术进行检测。

其中一种常见的方法是使用内存泄漏检测工具。

大部分的内存泄漏检
测工具,都是通过在程序运行时动态的跟踪、记录和分析内存分配的
过程,从而找到内存泄漏的位置。

具体的原理如下:
1.内存泄漏检测工具会在程序运行时注入一些代码,用于跟踪内
存的分配和释放。

2.当程序分配内存时,内存泄漏检测工具会记录下分配的内存地
址和大小等信息。

3.当程序释放内存时,内存泄漏检测工具会将该内存地址标记为
可用。

4.当程序结束时,内存泄漏检测工具会扫描内存中所有未释放的
内存块。

5.如果发现存在未释放的内存块,则会输出相应的错误信息,并
指出该内存块的位置和大小等信息。

通过这种方式,内存泄漏检测工具可以在程序运行时检测到内存
泄漏的问题,帮助开发人员快速定位问题并进行修复。

为了确保程序
的性能和稳定性,开发人员应该尽可能的避免内存泄漏问题的发生,同时定期使用内存泄漏检测工具进行检测和修复。

如何进行代码的内存泄漏检测与优化

如何进行代码的内存泄漏检测与优化

如何进行代码的内存泄漏检测与优化代码的内存泄漏是指程序在运行过程中未能正确释放不再使用的内存,导致系统中出现大量无用的内存占用,最终可能导致系统性能下降甚至崩溃。

因此,内存泄漏检测和优化是软件开发过程中非常重要的一环。

本文将介绍如何进行代码的内存泄漏检测与优化,以确保程序的健壮性和性能。

一、内存泄漏的检测方法1.静态代码分析工具:静态代码分析工具可以扫描源代码,检测潜在的内存泄漏问题。

常见的静态代码分析工具有Coverity、PVS-Studio、Cppcheck等,通过这些工具可以及时发现代码中可能存在的内存泄漏问题。

2.动态代码分析工具:动态代码分析工具是在程序运行时对内存的使用情况进行监控和分析,从而检测内存泄漏问题。

常见的动态代码分析工具有Valgrind、Dr.Memory等,这些工具可以帮助开发人员发现程序运行时的内存泄漏问题。

3.内存泄漏检测工具:除了静态和动态代码分析工具外,还有一些专门用于检测内存泄漏的工具,如LeakCanary(Android平台)、LeakSanitizer(GCC和Clang编译器)等,这些工具可以帮助开发人员快速定位和修复内存泄漏问题。

二、内存泄漏的优化方法1.及时释放内存:在程序中及时释放不再使用的内存是最基本的内存泄漏优化方法。

对于动态申请的内存,一定要在使用完毕后及时调用free或delete进行释放,避免内存泄漏发生。

2.使用智能指针:智能指针是一种用于管理动态内存的工具,可以自动管理内存的申请和释放,避免手动释放内存时产生的错误。

C++中有shared_ptr、unique_ptr等智能指针,能够有效避免内存泄漏问题。

3.避免循环引用:循环引用是一种常见的内存泄漏原因,当两个对象相互引用时,可能导致对象之间无法被正确释放。

解决方法是使用弱引用(weak_ptr)来打破循环引用,避免内存泄漏的发生。

4.优化数据结构和算法:优化数据结构和算法能够减少内存的使用,降低内存泄漏问题的发生。

jni内存泄露问题

jni内存泄露问题

1、当java和c回调传的参数过多的时候,会出现内存泄露问题,列如程序运行一段时间之后,莫名的出现如下错误JNI ERROR (app bug): local reference table overflow (max=512)Failed adding to JNI local ref table (has 512 entries)VM aborting2、引起这个bug的原因有如下几个:上层传递参数String 给下层C语言,当底层使用完数据之后,一定要掉用ReleaseStringUTFChars接口将内存释放掉,不然当传递次数多了之后会导致系统奔溃JNIEXPORT jint JNICALL test_string(JNIEnv *env, jobject obj,jstring j_usrname,jstring j_passwd,jint j_host_id){int usr_id =1;const char *usrname = env->GetStringUTFChars (j_usrname, NULL);LOGD("usrname = %s",usrname);env->ReleaseStringUTFChars (j_usrname, usrname);return 1;}3、底层jni里面C语言接口调用上层java的方法时候,一定要释放obj类,不然也会导致系统奔溃,如下列子:底层子线程当中要调用上层的java的方法3、1在cpp接口程序里面定义全局变量JavaVM *g_jvm=NULL;jobject g_obj = NULL;3、2在创建线程函数之前,给这两个变量赋值JNIEXPORT jint JNICALL init(JNIEnv *env, jobject obj,jint mode){env->GetJavaVM(&g_jvm);g_obj = env->NewGlobalRef(obj);pthread_t tid;pthread_create(&tid,NULL,testjni,NULL);}3、3在线程函数里面调用上层的一个void fun(int a);方法(注:只要在jni底层,除了自己用onload映射出来接口相对于整个APP来说是主线程函数以外,其它c函数接口都视为子线程函数)void *testjni(void *arg){JNIEnv *env;jmethodID met;jclass cls;while(1){if(g_jvm->AttachCurrentThread(&env, NULL) != JNI_OK){LOGD("%s: AttachCurrentThread() failed", __FUNCTION__);return NULL;}cls = env->GetObjectClass(g_obj);met =env->GetMethodID(cls, "fun","(I)V");env->CallVoidMethod(g_obj, met, 10);env->DeleteLocalRef(g_obj); //注意必须释放缓存数据sleep(1);}return NULL;}。

C语言中的内存泄漏检测与处理

C语言中的内存泄漏检测与处理

C语言中的内存泄漏检测与处理章节一:引言在编程过程中,内存泄漏是一种常见的问题。

内存泄漏指的是在程序运行期间,动态分配的内存没有被正确释放,导致内存资源的浪费。

C语言作为一种强大而灵活的编程语言,也容易出现内存泄漏的问题。

本文将介绍C语言中的内存泄漏检测与处理方法。

章节二:内存泄漏的原因内存泄漏通常发生在动态内存分配的过程中,其原因主要有以下几个方面:1.忘记释放内存:程序员在分配内存后,忘记了调用相应的释放函数来释放内存,导致内存泄漏。

2.错误的释放内存:程序员错误地释放了未分配的内存或多次释放同一块内存,造成内存泄漏。

3.程序逻辑错误:程序逻辑错误导致在释放内存之前就跳出了函数或循环,导致内存泄漏。

章节三:静态检测工具为了避免内存泄漏的发生,可以使用一些静态检测工具来帮助我们发现潜在的内存泄漏问题。

这些工具可以在编译阶段对代码进行检查,发现内存泄漏的可能性。

1. lintlint是一种静态代码分析工具,可以检查源代码中的潜在问题。

它可以检测未释放的内存、未初始化的指针等问题,并给出相应的警告提示。

使用lint工具可以帮助程序员及早发现并修复内存泄漏问题。

2. Clang Static AnalyzerClang Static Analyzer是一种基于LLVM的静态代码分析工具,可以在编译时对C语言代码进行静态分析。

它可以检测出潜在的内存泄漏问题,并给出详细的报告。

Clang Static Analyzer具有高度精确的分析能力,可以帮助程序员及时发现和解决内存泄漏问题。

章节四:动态检测工具除了静态检测工具外,还可以使用一些动态检测工具来检测内存泄漏。

动态检测工具可以在程序运行时监视内存分配和释放的情况,并在发现内存泄漏时给出警告。

1. ValgrindValgrind是一种开源的动态检测工具,可以检测出内存泄漏、使用未初始化的内存、访问已释放内存等问题。

Valgrind可以通过在程序运行时对内存进行跟踪和分析,帮助程序员发现和修复内存泄漏问题。

内存泄漏的检测定位和解决经验总结

内存泄漏的检测定位和解决经验总结

内存泄漏的检测定位和解决经验总结内存泄漏是指在程序运行过程中,分配的内存一直没有被释放,导致内存的使用量越来越大,最终耗尽系统资源,造成程序崩溃。

内存泄漏是一种常见的程序缺陷,需要及时发现和解决。

一、检测内存泄漏的方法有以下几种:1. 静态代码检查:通过静态代码分析工具进行检查,工具可以扫描代码中的内存分配和释放情况,并发现潜在的内存泄漏问题。

常用的静态代码检查工具包括Coverity、PMD等。

2. 动态代码检查:通过运行时检查工具对程序进行监控,记录内存分配和释放的情况,检查是否有未释放的内存。

常用的动态代码检查工具包括Valgrind、Dr.Memory等。

3. 内存使用分析工具:通过监控程序的内存使用情况,包括内存的分配与释放,内存占用量等信息,来判断是否存在内存泄漏。

常用的内存使用分析工具有Google Performance Tools、Eclipse Memory Analyzer 等。

二、定位内存泄漏的方法有以下几种:1.添加日志:在程序中添加日志跟踪内存的分配与释放情况,当发现内存没有被释放时,通过日志定位问题的位置。

可以通过添加打印语句或者使用专门的日志工具来完成日志记录。

2. 使用内存调试工具:内存调试工具可以跟踪程序中的内存分配和释放情况,并将未被释放的内存标记出来。

通过分析工具提供的报告,可以定位内存泄漏的位置。

常用的内存调试工具有Valgrind、Dr.Memory等。

3. 内存堆栈分析:当程序出现内存泄漏时,通过分析内存堆栈可以得到导致内存泄漏的代码路径。

可以使用工具来进行内存堆栈分析,例如Eclipse Memory Analyzer。

三、解决内存泄漏的方法有以下几种:1. 显式释放内存:在程序中显式地调用释放内存的函数,确保内存被正确地释放。

例如,在使用动态内存分配函数malloc或new分配内存后,必须使用free或delete释放内存。

2. 自动垃圾回收:使用编程语言或框架提供的垃圾回收机制,自动释放不再使用的内存。

基于中间语言的+JNI内存泄漏检查

基于中间语言的+JNI内存泄漏检查

计算机研究与发展DOI:10.7544桙issn1000‐1239.2015.20131909JournalofComputerResearchandDevelopment52(4):898906,2015 收稿日期:2013-12-17;修回日期:2014-05-12 基金项目:国家自然科学基金项目(61272086);“核高基”国家科技重大专项基金项目(2012ZX01039‐004‐08)基于中间语言的JNI内存泄漏检查蒋挺宇1 王 鹏1 杨 述1 褥 震1 董 渊1 王生原1 嵇智源21(清华大学计算机科学与技术系 北京 100084)2(科技部高技术研究发展中心 北京 100044)(Jiangty08@gmail.com)DetectionofJNIMemoryLeaksBasedonExtendedBytecodeJiangTingyu1,WangPeng1,YangShu1,RuZhen1,DongYuan1,WangShengyuan1,andJiZhiyuan21(DepartmentofComputerScienceandTechnology,TsinghuaUniversity,Beijing100084)2(HighTechnologyResearchandDevelopmentCenter,MinistryofScienceandTechnology,Beijing100044)Abstract TheJavanativeinterface(JNI)enablesJavacoderunninginaJavavirtualmachine(JVM)tobecalledbynativecode,butthedifferenceofsecurityfeaturesbetweenlanguagesmakesitasecurityweakness,whichcannotbedetectedbyexistinganalysismethods.Commonlyuseddetectionmethodsaremainlybasedontheanalysisofintermediatelanguage,whichisinvalidinthisJNIcase,sincethelackofanintermediaterepresentationtobridgeJavaandC++.ThispaperanalyzesJNIfromaJava桙C++cross‐languageperspectiveandfocusesonmemoryleakswhichfrequentlyoccurinJNIcalls.Inordertoovercomelanguagebarriers,thispaperproposesextendedBytecode(Bytecode倡)instructionsasinterpretationofC++semantics.Ourcontributionsaredescribedasfollows:1)DefineablockmemorymodelwhichiscompatiblewithbothJavaandC++;2)DesigntranslationrulesfromC++toextendedJavaBytecodebasedonLLVM桙LLJVM;3)Constructamethodcallgraph,extractabstractanddetectmemoryleaksinJNIcallsbyinterproceduralanalysis.ExperimentsontypicalJNIcodewithmemoryleakfeaturesshowthatouranalysisworkcandetectmemoryleaksinJava桙C++accurately,andisofimportantsignificanceincross‐linguisticprogrammingandvulnerabilityanalysis.Keywords Javanativeinterface(JNI);cross‐linguisticanalysis;semanticextension;Bytecode;memoryleak摘 要 JNI技术支持Java与本地C桙C++的相互调用,在Android等混合语言实现的系统中有着广泛应用,但语言之间的安全特性差异使其成为安全薄弱环节,现有的分析方法难以处理多语言相互调用产生的安全缺陷.以JNI调用中易产生的内存泄漏为例,开展Java桙C++JNI跨语言分析的研究.采用扩展的JavaBytecode(Bytecode倡)指令作为C++语义的解释来消除跨语言分析的障碍.围绕JNI调用中内存泄漏的问题,做了以下3方面工作:1)定义兼容Java桙C++语言的分块内存模型;2)基于LLVM桙LLJVM,设计实现了C++到Bytecode倡的翻译策略;3)建立方法调用图,提取方法摘要,利用过程间分析方法检测JNI调用中的内存泄漏.针对具有典型内存泄漏特征的JNI实例翻译检测表明,该工作能够准确检测出Java桙C++混合语言中的内存泄漏,对于JNI混合语言编程的理解和漏洞分析具有重要价值.关键词 Java本地调用;跨语言分析;语义扩展;字节码;内存泄漏中图法分类号 TP314 JNI(Javanativeinterface)编程是一项复杂的工作,其编程规范[1]中列出了多达15种JNI编程中容易出现的错误,这些错误很难通过编译器来发现.除了程序员使用JNI调用失误而造成的程序错误之外,黑客们也开始针对软件系统中的JNI接口缺陷,编写恶意代码来越过Java虚拟机的保护机制,以达到非法的目的.Android操作系统基于Linux开源操作系统,是目前最为流行的移动操作系统[2].为方便开发,Android采用Java作为其应用程序开发语言,而底层库则由本地C代码实现,两者通过Dalvik虚拟机以及JNI机制进行通信.本文研究发现,Android2畅2系统中有JNI接口3186个,其中443个采用C语言实现,其余2743个均采用C++语言实现,C++实现的JNI接口中有1837个位于系统核心框架frameworks中.由于Java语言和C++语言之间的安全特性差异,这些JNI接口成为安全薄弱环节,一旦出现问题,后果可能十分严重.2010年Kaspersky首次发现了针对Android系统的SMS木马,其危害是泄漏个人数据[3].之后,Android平台上恶意代码呈井喷之势爆发,至今仍保持着较高的增长速度.Davi等人[4]详细介绍了一种利用JNI接口对本地C代码进行溢出攻击的原理和代码实例,该方法可以轻易突破Android的权限保护和JVM(Javavirtualmachine)的沙箱保护,在不经过任何授权的情况下获取超级用户权限.由于JVM桙Dalvik对本地代码高度的信任,JNI接口缺陷逐渐成为恶意软件利用的重灾区[5].目前对于Java程序的安全监测和验证工作主要是基于Bytecode开展研究,但这种方式无法针对混合语言开展分析,大多数的检测器选择完全忽略本地代码的危害,所以难以得到准确的结果.本文提出了一种从JNI两端整体来分析程序的方案,针对JNI接口的多语言编程模型,将整个程序翻译到扩展的JavaBytecode中间表示,利用过程间分析达到跨语言检测的目的.1 相关工作综述1.1 现有分析检测技术在JNI调用中,Java代码和本地代码的交互是程序的主体,现有技术手段往往仅在一端开展安全检测,无法有效处理JNI中由于跨语言控制流带来的安全问题.针对JavaBytecode的开源静态检测工具有很多.Findbugs[6]采用Visitor模式,查找代码中与某种缺陷模式匹配的错误.但是,Findbugs专注于过程内分析,对于跨过程分析的能力十分有限.Soot是一个Java优化和分析框架,可以解析class文件,构建控制流图和调用图,执行指针指向和空指针分析,并且支持数据流分析.Soot[7]框架比较适合构建专门的JavaBytecode分析器.另外一些检测技术仅在本地代码端展开.Lint[8]一类的工具采用类型分析方法,手工对访问内存的操作进行大量注释以辅助内存分析,且没有利用控制流信息,结果的准确性有限.Kondoh等人利用静态分析技术在缺陷查找工具BEAM[9]中实现了针对本地C代码的分析,对JNI编程范例中所列包括资源泄漏在内的几项错误进行检测[10],可以分析特定接口函数导致的资源泄漏问题,但局限于函数过程内部,检测范围有限.这些方法在JavaBytecode类型、语义、逻辑系统以及验证等方面取得了大量研究成果,如果能利用JavaBytecode实现本地代码语义的解释,这些成果会大大降低Java桙C++JNI跨语言分析的代价.1.2 JNI接口的分析现状JNI分析的最大难点就是如何消除多语言对分析器的影响.Zhao等人[11]给出一种Bitcode中间表示的形式化模型,用于构造和验证可信的LLVM优化器,而LLJVM项目还提供了一种将LLVMBitcode翻译为JavaBytecode的框架,支持C语言特征[12].但是这些翻译通常并不提供针对JNI问题检测的跨语言处理,给检测带来很大困难,在这些中间语言上重新构建JNI缺陷分析器的代价又很大.Furr和Foster设计了JSaffire来寻找JNI相关的类型错误[13];Kondoh和Onodera设计了一个类似的类型检测系统;Tan等人建立了SafeJNI[14]和ILEA[15]框架方法,寻找Java桙CJNI接口中的安全错误.这些方法对JavaBytecode进行了一定的扩展,将C语言翻译到扩展的JavaBytecode,使Java分析器可以理解C代码的语义,并对之进行形式化验证.该方法只需建立C语言到Bytecode的翻译器,省略了很多C语言的复杂特性,利用丰富的Java分析技术,避免高昂的开销,对JavaBytecode指令的扩展侧重于翻译后的可检查性.但上述方法局限于C语言,无法处理C++代码,而本地代码中C++的比例不断增大,而且包含更多的语言特性,因此需要进一步的研究.998蒋挺宇等:基于中间语言的JNI内存泄漏检查1.3 本文研究内容为了检测Java程序中JNI调用涉及多语言交互所引发的问题,本文提出将不同语言向同一中间表示转换、然后基于中间表示展开分析的方案,构建如图1所示的Java桙C++跨语言静态分析与检测平台.Fig.1 Workflowchart.图1 工作流程图Java应用程序中,本地代码实际比例相对Java语言要低,而且JavaBytecode作为编译后的二进制码可以保留足够的类型信息,并且有一些成熟的Bytecode分析框架可以利用.本文将本地语言向扩展的JavaBytecode转换,称之为Bytecode倡.如图1所示,将Bytecode倡和JavaBytecode作为一个整体开展分析.平台基于模式匹配的方式,针对不同的缺陷模式制定不同的翻译策略,将JNI调用中的本地C++代码翻译到Bytecode倡,消除不同语言的隔阂,然后扩展JavaBytecode分析工具针对具体的缺陷开展分析.因为内存泄漏是较为常见的本地代码缺陷,而且由于多语言的交互变得更加隐蔽,所以本文以它为突破口先完成JNI调用中的内存泄漏检测.2 C++到Bytecode倡的翻译技术LLVM的Bitcode拥有简单、独立的类型系统,拥有地址计算指令和处理高级语言异常处理的功能,可以保留C++的语言信息.LLJVM项目提供了Bitcode到Bytecode转换的框架,采用运行时动态库的方式实现对C语言特征的支持.LLJVM不能支持C++,而且它的翻译策略引入很多不必要的复杂信息,所以不适合本文需要的静态分析和检测要求.但是,LLJVM提供了一个可利用的Bitcode到Bytecode的翻译框架,只需在此框架上设计适合静态分析的翻译策略,提供对C++语言的支持就可以实现C++源码到Bytecode倡的翻译,本文设计的翻译策略如下:首先利用LLVM编译器C++前端llvm‐g++将C++源码翻译到LLVMBitcode;然后用翻译器对C++程序预处理,获取其中包含的类相关信息;最后结合对Bitcode语义的分析,使用本文设计的简洁翻译策略,将Bitcode翻译到Bytecode倡.2.1 内存模型C++和Java两种存储模型无法直接匹配,堆的操作也有很大差异,可能产生内存泄漏,需要设计合适的JNI存储模型,实现两种语言之间的内存模型匹配.本文建立分块内存模型(blockmodel)来解决Java桙C++的内存模型不同的问题.在分块模型中,存储堆由若干块组成,一个块可以被垃圾回收机制管理,与Java内存模型匹配,可称为J堆;其他块必须通过显式的内存分配或释放指令操作与C++的内存模型匹配,称为C堆.每个块是一个从地址到值的映射,允许地址加减,适合内存计算.这个模型与Bitecode的堆存储模型也是吻合的.在此模型基础上,可以使用Bytecode倡统一描述Java桙C++JNI接口两端对内存的操作行为,为C++到Bytecode的翻译建立基础.2.2 翻译策略与类型映射Bytecode倡是由Java字节码Bytecode扩展而来,语言特性与Java具有一定的一致性,要将C++翻译到Bytecode倡关键在于C++与Java的类型映射.本文的思路是将C++中包括基本类型在内的所有类型映射到Java的数组、类或接口等拥有引用的类型上,通过引用来模拟C++中的指针特性.为此,需要设计一套完整的C++到Java的类型映射,且尽量利用Java现有的类型简化翻译及检测的复杂度.本文定义:MapType(c)=j,其中,c为C++中的类型,j为Java中的类型.2.2.1 基本类型映射C++与Java的基本数据类型大致是相同的,例如int,double等,简单的做法就是直接对其映射,但考虑到C++中的内存访问操作,基本类型间的直接映射是无法满足需求的,例如以下代码:inti=5,倡pi=&i;009计算机研究与发展 2015,52(4)倡pi=8.Java中无法通过指针对数据进行操作,可以将int这样的基本类型对应到Java中的类或数组来获得类似于指针或别名的效果,即MapType(int)=int[]. 这样,使用数组下标可以模拟指针的加减运算以及内存操作.2.2.2 基本类型指针对于基本类型,本文可以用数组来模拟表示,但基本类型的指针仅使用数组已经无法满足要求,本文考虑设计Java类来对应,以int倡为例:ClassintP{ int[]data; intindex;};data对应int的映射,index用来处理指针加减运算.如下是C++代码:inti[10];int倡pi=&i,倡pi2;pi2=pi+2;其中,pi,pi2对应的Java类中,data域相同,index不同,可以通过index模拟两者间的加减运算.2.2.3 对象指针指向对象的指针与指向基本类型的指针基本相同,只是因为Java本身有对象引用,所以无需再利用数组封装了.对象指针可以用如下类表示:ClassobjectP{ object[]data; intindex;};其中,object为类名,基于此可递归构造诸如object倡倡这样的多级对象指针.2.2.4 函数指针C++中调用函数既可以直接调用,也可以通过函数指针调用;但在Java中,函数均被封装在类和接口中.同样地,对于函数指针,可以通过Java接口引用来模拟.C++函数指针指向的具体函数行为,在Java中可以通过继承特定接口的子类来实现.2.3 JNI接口函数及库函数处理JNI接口函数是连接Java端和本地代码端的纽带,使Java和本地代码能够相互调用通信.根据JNI接口函数的功能和使用方式,分如下3种情况处理:1)用于注册本地函数入口的接口函数.由于该类函数并不影响分析过程,因而在JNI两端合并到Bytecode倡之后不再需要,故不作翻译,最后在中间代码布局中体现即可.2)与内存泄漏无关的接口函数.这些函数的功能各样且实现复杂,但与内存泄漏无关,本文不对其具体翻译,只将其加入到白名单中即可.此外,为了不影响控制流桙数据流分析,对此类函数返回值取任意值,并对JavaBytecode扩展一条指令以实现此功能,C++标准库和第三方库函数也可采用此方式处理.3)可能导致内存泄漏的函数.类似GetString‐Chars桙ReleaseStringChars这样的接口函数,翻译其具体操作比较复杂,若检测内存泄漏,则可以扩展JavaBytecode的内存操作指令.设计native_new桙native_delete指令,用于内存的显式分配与释放.这只需用native‐new桙native‐delete来标记可能发生泄漏的接口函数,而不需要翻译具体的分配和释放过程.在分块内存模型上,完成上述对白名单函数的处理以及显式的内存分配释放,需要扩展以下3条Bytecode倡指令:1)native_new棟class棡.在C堆创建一个新对象,不受垃圾回收机制管理,必须通过native_delete显式释放.2)native_delete.释放当前栈顶通过native_new分配的对象.3)random棟type棡.在当前栈顶放置一个type类型的随机值.通过上述设计,就可以将JNI两端基本对应,将C++语言翻译到中间表示Bytecode倡.3 基于过程间分析的JNI漏洞检测3.1 内存泄漏模式内存泄漏的本质都是失去对动态分配内存的控制.从检测角度来说,本文将内存泄漏总结为2种模式:1)分配内存后,没有释放;2)分配内存后,指向该块内存的变量发生变化,导致无法释放.对内存泄漏模式来说,根据本地代码的内存分配与释放的匹配建模,可以建立基于内存泄漏模式的有限状态机,将内存变量分为3个不同的状态{UnAllocated,Allocated,Error},各种状态的含义为:UnAllocated表示变量未被分配内存;Allocated表示变量已被分配内存;Error是故障状态.109蒋挺宇等:基于中间语言的JNI内存泄漏检查可以通过构造如图2所示的状态转换图描述和寻找这样的问题.Fig.2 Statetransitionofmemoryleak.图2 内存泄漏状态转换图状态转移条件如表1所示:Table1 StateTransitionConditions表1 状态转换条件StateTransitionStateTransitionConditionsUnAllocated→AllocatedAllocatememoryforvariables.Allocated→UnAllocatedReleasememoryofvariables.Allocated→AllocatedOtheroperation.Allocated→ErrorProgramexitsorvariablesareinaccessible.3.2 过程间JNI内存泄漏检测设计根据分析的范围和目标,分析方法可以分为过程内分析和过程间分析;而JNI调用可能涉及内存泄漏问题,其本质上是C++函数和Java方法互相调用的结果,并非局限于一个方法内,因此必须进行过程间分析.此外针对内存泄漏,只要有一条程序运行路径没有达成内存申请与释放的匹配,本文就可以认为程序有出现内存泄漏的风险,所以还需要进行路径敏感的分析策略.过程间分析[16‐18]与路径敏感分析[19‐21]已经有不少相关的研究和对应的工具出现,他们都有各自的关注点.本文的内存泄漏检测是基于数据流分析的,需要完成过程间的数据流分析,当遇到方法调用时如何处理方法对数据流产生的影响是解决问题的关键.基于摘要的过程间分析方法非常灵活,可以根据分析的需求定义不同的摘要信息,按照摘要的详细程度也可以控制分析的精度,具有较好的扩展性,能够很方便地扩展到大规模的程序分析中去.本文设计了如图3所示的基于摘要过程间分析框架.整个过程间分析系统可以分为3大块,分别是对Bytecode倡的预处理模块、过程内分析模块以及过程间分析与方法摘要模块,具体如下:1)预处理模块是对转化好的Bytecode倡进行分Fig.3 Interproceduralanalysis.图3 过程间分析框架图析,生成对应规模的调用图,对涉及到的所有方法进行排序,不考虑方法自身直接递归的情况,同时初始化方法摘要.2)过程内分析模块是整个系统的核心模块,因为过程间分析最终要通过方法摘要转化到过程内分析.该模块生成每个方法的控制流图,实施实际的内存泄漏检测,获取与应用方法摘要,保留分析后的结果.3)过程间分析与方法摘要模块是整个分析过程的连接枢纽,主要是提供过程间分析框架,按照顺序组织分析的过程,通过过程内分析的结果生成方法摘要,在分析结束后报告结果.3.3 基于Soot的过程间内存泄漏检测实现Soot是加拿大McGill大学Sable研究小组开发的针对JavaBytecode的优化和分析工具,它面向不同的分析和优化目的建立了各种内部的中间表示,既可以辅助过程内分析,也能为过程间分析提供支持,而且具有较好的扩展性,所以本文选择Soot作为本文分析工具的基础框架.3.3.1 调用图生成和预处理Soot提供了多种不同调用图算法的具体实现,无论使用哪种调用图构建算法,只是相对地提高了精度,还需要自己实现调用图的修剪工作.读入原始调用图后,从调用图的入口节点按照调用关系做一个广度优先遍历,只有能从入口节点直接或间接到达而且没有被过滤器过滤的方法才会被加入辅助调用图中,它的前驱和后继都会被保存下来.为减少后期迭代的次数,需要对这些方法进行拓扑排序,由于调用图不保证无环,采用对辅助调用图节点倒序排序.209计算机研究与发展 2015,52(4)3.3.2 过程内分析和摘要提取Soot中提供3种不同的数据流分析框架,由于内存缺陷是路径敏感,所以本文采用Forward‐Branched‐FlowAnalysis框架,它具备不同的信息通过各分支的分支节点传播的分析能力,对应着路径敏感的数据流分析.检测方法通过扩展上述框架实现,对每一个程序语句节点s的数据流值集合In[s],提供了2个数据流值集合来表述语句转换后的新数据流值集合———直接流向的集合(fallthroughOUT)和分支流向的集合(branchOUT),用以保存语句不同分支的数据流值,达到路径敏感的目的.摘要提取在过程内分析的基础上进行,每个方法结束时我们保留必要的数据流状态信息,作为这个函数的摘要.3.3.3 过程间分析检测完成过程间分析,需要组织整个分析过程,建立过程间分析框架,对所有方法进行分析,定义过程间分析类.分析在类的成员方法中展开,基于经典的工作队列算法实现,具体过程是按拓扑排序对每个方法开展分析,执行过程内分析算法.当遇到方法调用时,获得被调用方法的摘要,将其对数据流状态的影响作用于上下文中,完成分析后生成方法的摘要,如果摘要信息与已保存的信息不同,就对所有调用过它的方法重新分析,获得新的摘要信息,如此迭代直到所有方法的摘要信息都不再改变时,就完成了分析过程.整个过程中,方法摘要信息以及进行过程间分析时的控制流处理对于检查方法的精度有着决定性的影响.详细的摘要信息能够扩大检测的覆盖率;精细的控制流处理对于加强大规模复杂程序的检测准确率、降低误判情况更有帮助.目前的分析检测策略能准确检测出典型内存泄漏,设计扩展更大规模更复杂的分析策略以应用到更复杂的场景中也是我们下一步的研究方向.4 典型内存泄漏检测过程实现了整个安全检测方法之后,本文对实际的Java桙C++JNI调用混合语言程序进行检测,并简要介绍分析过程,如下是一个典型的JNI环境中内存泄漏实例:1)Java代码:…⑩privatestaticnativevoidallocobj();皕瑏瑡privatestaticnativevoidreleaseobj();皕瑏瑢publicvoidtestrun(booleanflag){皕瑏瑣for(inti=0;i<100000;i++){皕瑏瑤 allocobj();皕瑏瑥 if(flag)releaseobj();桙倡mayleak倡桙皕瑏瑦 }皕瑏瑧}皕瑏瑨static{Sytem.loadLibrary(“leak‐jni”);}…2)C++代码:…⑤classClock{…⑩private:皕瑏瑡intA[10000];皕瑏瑢}皕瑏瑣staticClock倡f=NULL;皕瑏瑤extern“C”{皕瑏瑥JNIEXPORTvoidJNICALLJava_test_HelloJNI_allocobj(JNIEnv倡env,jobjectthiz){皕瑏瑦 f=newClock();皕瑏瑧}皕瑏瑨JNIEXPORTvoidJNICALLJava_test_HelloJNI_releaseobj(JNIEnv倡env,jobjectthiz){皕瑏瑩 deletef;皕瑐瑠}}JNI本地函数Java_test_HelloJNI_allocobj(),Java_test_HelloJNI_releaseobj()分别实现了内存申请和释放,Android应用程序Java代码中函数testrun()通过JNI接口调用这2个函数,内存释放与参数flag的取值有关,并非所有执行路径上都能够调用内存释放操作,因此可能造成内存泄漏,大量的内存泄漏可能导致当前进程崩溃,采用已有的分析工具尚无法对此类跨语言跨过程的漏洞进行分析.如果仅在Java端代码展开分析,结果如下:代iconst_0①istore_2②goto18(+16)…309蒋挺宇等:基于中间语言的JNI内存泄漏检查⑤invokestatic #27棟cn桙ysh桙Ytool桙tests桙Test桙allocobj()V棡…⑧iload_1⑨ifeq15(+6)…皕瑏瑢invokestatic #29棟cn桙ysh桙Ytool桙tests桙Test桙releaseobj()V棡…皕瑏瑥iinc2by1…皕瑏瑨iload_2皕瑏瑩sipush10000…皕瑐瑢if_icmplt5(-17)…皕瑐瑥returnJava端对于allocobj和releaseobj的分析仅限于2个本地方法声明,而对其实际的操作功能一无所知,所以在此基础分析难以找到问题.按照本文的方案,将C++代码转化为Bytecode倡,并与Java合并后allocobj和releaseobj转化为本地静态方法,对应地调用了native_new和native_delete指令,且有两者的具体实现:…皕瑔瑩swap皕瑖瑠getfield #94棟org桙thu桙lljvm桙helper桙_jarray_JNITYP2桙dataIndex]…皕瑖瑣aload_1皕瑖瑤aastore皕瑖瑥invokestatic #117棟org桙thu桙lljvm桙helper桙ClockP1桙native_new()棡…皕瑖瑨astore6…皕瑘瑠aload6…皕瑘瑢astore7…经过分析可以得到2个方法的摘要分别为allocobj({棟f,ClockP2,{f},A棡}),releaseobj(State(f,A);{棟f,ClockP2,{f},U棡}).allocobj的摘要表示该方法进行的操作:给类Clock的指针f进行了分配内存操作;A代表Allocate.releaseobj的摘要,表示该方法进行的操作:给类Clock的指针f进行了类型释放操作;U代表Unallocate,同时操作前状态是已为f分配了内存;State表示操作涉及的变量的内存状态.因而,通过摘要可以确定allocobj方法和releaseobj需要配对出现.至此,问题被转化为Bytecode倡语言内过程间分析.分析流程如图4所示:Fig.4 Analysisprogressoftestrun.图4 testrun方法分析流程allocobj方法结束后的数据流集为{棟f,ClockP2,{f},A棡},releaseobj的数据流集为{棟f,ClockP2,{f},U棡},经过变换作为2个方法的摘要.在数据流合并操作merge(T,F)之后,数据流集为{棟f,ClockP2,{f},A棡},此时testrun退出,数据流状态为f已分配内存,没有释放,报告一个可能内存泄漏的检查点.表2为对多种内存泄漏问题检测结果,所使用的例子来自现有的JNI内存泄漏代码以及研究中设计的简单例子,经测试均可通过本文的分析方法找到问题所在.Table2 ResultsofMemoryLeakDetection表2 对多种内存泄漏问题的检测结果ProblemsDetectionResultsNotatalltheprogramexecutionpathtoreleaseallocatedmemory.SuccessMemoryisallocatedbutnotreleasedinmethodcall.SuccessMemoryisallocatedmanytimesbutonlyreleasedonceinaloop.SuccessAllocateandreleaseactionnotmatchinginsomepath.Success通过对多个例子的分析对比,本文方法能够将JNI两端语言转换到同一中间表示,且保留内存操409计算机研究与发展 2015,52(4)作的语义特征,消除多语言带来的分析障碍.虽然大规模复杂样例的测试验证有待进一步研究完善,但通过典型例子的实验论证了方法的有效性和可行性.5 结论及未来工作展望随着使用Java语言开发的应用程序日益增多,对性能的要求以及嵌入式操作系统的需要越来越高,JNI本地接口技术发挥着越发重要的作用.由于JNI接口所调用的本地语言如C++,在安全机制上与Java语言存在着明显的差异,导致两者交互调用的过程中可能存在安全隐患.现有的检测工具大多仅能在Java或本地代码一端进行检测,已有的跨语言分析技术也局限于Java桙C或者过程内分析,无法有效地处理JNI中Java桙C++间由于跨语言控制流带来的安全问题.针对这一情况,本文设计实现了基于扩展的JavaBytecode(Bytecode倡)中间语言的过程间分析检测方法,并以典型的内存泄漏代码为例进行了实验.结果表明,本文工作能够准确检测出Java桙C++混合语言中的内存泄漏问题.JNI跨语言调用可能引发的安全缺陷并不局限于内存泄漏,目前的翻译和检测主要围绕内存泄漏,但整个方案的设计已经考虑到了将来的扩展性.因此,下一步的工作是在完善现有方法的基础上扩展跨语言检测平台的功能,并进行更大范围的量化分析和有效性验证,主要包括:C++中强制类型转换等操作尚未进行扩展,接下来可根据不同安全缺陷特征进行完善;对于JavaBytecode扩展指令进行形式化的验证;构建更多的跨语言检测模型,应用到更大规模的分析环境中去.致谢 在此,我们向对本文的工作给予建议的同行,特别是Intel中国研究院陈兴中先生、中国科学技术大学冯新宇教授和华保健副教授、Lehigh大学谭刚博士等人以及第十二届全国软件与应用学术会议(NASAC2013)的评审专家们表示感谢!参考文献[1]LiangSheng.TheJavaNativeInterfaceProgrammer摧sGuideandSpecification[M].Reading,MA:Addison‐Wesley,1999[2]DevelopersofAndroid.WhatisAndroid[EB桙OL].2011[2012‐02‐10].http:桙桙developer.android.com桙guide桙basics桙what‐is‐android.htm[3]PerezS.FirsttrojanforAndroidphonesgoeswild[EB桙OL].2012[2012‐03‐10].http:桙桙readwrite.com桙2010桙08桙09桙first_trojan_for_android_phones_goes_wild[4]DaviL,DmitrienkoA,SadeghiA‐R,etal.Privilegeescalationattacksonandroid[G]桙桙LNCS6531:Procofthe13thIntConfonInformationSecurity.Berlin:Springer,2011:346360[5]SchmidtAD,SchmidtHG,BatyukL,etal.Smartphonemalwareevolutionrevisited:Androidnexttarget[C]桙桙Procofthe4thIntConfonMaliciousandUnwantedSoftware.Piscataway,NJ:IEEE,2009:17[6]AyewahN,PughW,MorgenthalerJD,etal.UsingFindBugsonproductionsoftware[C]桙桙Procofthe22ndACMSIGPLANConfonObject‐OrientedProgrammingSystemsandApplicationsCompanion.NewYork:ACM,2007:805806[7]EinarssonA,NielsenJD.Asurvivor摧sguidetoJavaprogramanalysiswithSoot(Version1.1)[EB桙OL].(2008‐07‐17)[2012‐03‐10].http:桙桙www.brics.dk桙SootGuide[8]DevelopersofAndroid.AndroidLint[EB桙OL].2011[2012‐02‐10].http:桙桙tools.android.com桙tips桙lint[9]BrandD.Errordetectionbydataflowanalysisrestrictedtoexecutablepaths[EB桙OL].NewYork:IBMTJWatsonResearchCenter,1999[2012‐03‐04].http:桙桙www.research.ibm.com桙da桙beam.htmls[10]KondohG,OnoderaT.FindingbugsinJavanativeinterfaceprograms[C]桙桙Procofthe2008IntSymponSoftwareTestingandAnalysis.NewYork:ACM,2008:109118[11]ZhaoJianzhou,NagarakatteS,MartinMM,etal.FormalizingtheLLVMintermediaterepresentationforverifiedprogramtransformations[J].ACMSIGPLANNotices,2012,47(1):427440[12]RobertsDA.LLJVM[EB桙OL].2012[2012‐10‐23].http:桙桙da.vidr.cc桙projects桙lljvm[13]FurrM,FosterJS.PolymorphicTypeInferencefortheJNI[M].Berlin:Springer,2006:309324[14]TanGang,AppelAW,ChakradharS,etal.SafeJavanativeinterface[C]桙桙ProcofIEEEIntSymponSecureSoftwareEngineering.Piscataway,NJ:IEEE,2006:97106[15]TanGang,MorrisettG.ILEA:Inter‐languageanalysisacrossJavaandC[J].ACMSIGPLANNotices,2007,42(10):3956[16]BoddenE.Inter‐proceduraldataflowanalysiswithifds桙ideandsoot[C]桙桙ProcoftheACMSIGPLANIntWorkshoponStateoftheArtinJavaProgramAnalysis.NewYork:ACM,2012:38[17]RepsT,HorwitzS,SagivM.Preciseinterproceduraldataflowanalysisviagraphreachability[C]桙桙Procofthe22ndACMSIGPLAN‐SIGACTSymponPrinciplesofProgrammingLanguages.NewYork:ACM,1995:4961[18]SharirM,PnueliA.ProgramFlowAnalysis:TheoryandApplications[M].EnglewoodCliffs,NJ:Prentice‐Hall,1981:189233509蒋挺宇等:基于中间语言的JNI内存泄漏检查[19]CadarC,GaneshV,PawlowskiPM,etal.EXE:Automaticallygeneratinginputsofdeath[J].ACMTransonInformationandSystemSecurity,2008,12(2):1024[20]DilligI,DilligT,AikenA.Sound,completeandscalablepath‐sensitiveanalysis[J].ACMSIGPLANNotices,2008,43(6):270280[21]DorN,AdamsS,DasM,etal.Softwarevalidationviascalablepath‐sensitivevalueflowanalysis[J].ACMSIGSOFTSoftwareEngineeringNotes,2004,29(4):1222JiangTingyu,bornin1990.MastercandidateattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering.WangPeng,bornin1980.MasterattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering(wphf1980@163.com).YangShu,bornin1978.MasterattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering(come_go@163.com).RuZhen,bornin1991.MastercandidateattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering(ruzhen9999@163.com).DongYuan,bornin1973.PhD,associateprofessorattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.MemberofChinaComputerFederation.Hismainresearchinterestsincludeoperatingsystem,compilerandlanguage‐basedsecurity(dongyuan@tsinghua.edu.cn).WangShengyuan,bornin1964.PhD,associateprofessorattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.SeniormemberofChinaComputerFederation.Hismainresearchinterestsincludeprogramminglanguagesandsystems,petrinetapplication(wwssyy@tsinghua.edu.cn).JiZhiyuan,bornin1956.SeniorEngineerintheHighTechnologyResearchandDevelopmentCenter.Hismainresearchinterestsincludecomputerscienceandembeddedsoftware,technologymanagementofthenationalscienceandtechnologyplan(jzy@htrdc.com).609计算机研究与发展 2015,52(4)基于中间语言的 JNI内存泄漏检查作者:蒋挺宇, 王鹏, 杨述, 褥震, 董渊, 王生原, 嵇智源, Jiang Tingyu, Wang Peng , Yang Shu, Ru Zhen, Dong Yuan, Wang Shengyuan, Ji Zhiyuan作者单位:蒋挺宇,王鹏,杨述,褥震,董渊,王生原,Jiang Tingyu,Wang Peng,Yang Shu,Ru Zhen,Dong Yuan,Wang Shengyuan(清华大学计算机科学与技术系 北京 100084), 嵇智源,JiZhiyuan(科技部高技术研究发展中心 北京 100044)刊名:计算机研究与发展英文刊名:Journal of Computer Research and Development年,卷(期):2015(4)引用本文格式:蒋挺宇.王鹏.杨述.褥震.董渊.王生原.嵇智源.Jiang Tingyu.Wang Peng.Yang Shu.Ru Zhen.Dong Yuan.Wang Shengyuan.Ji Zhiyuan基于中间语言的 JNI内存泄漏检查[期刊论文]-计算机研究与发展 2015(4)。

内存泄漏排查流程过程和方法

内存泄漏排查流程过程和方法

内存泄漏排查流程过程和方法一、内存泄漏的初步判断1.1 观察系统症状当怀疑有内存泄漏时,首先得看看系统的一些表现。

如果系统变得越来越慢,就像蜗牛爬一样,那很可能是内存泄漏捣的鬼。

还有啊,程序运行的时间越长,可用内存就越少,这也是个很明显的信号。

就好比一个水桶有个小漏洞,水一直流出去,桶里的水就越来越少啦。

1.2 查看资源占用情况我们可以查看系统的资源监视器之类的工具。

看看内存的使用量是不是一直往上涨,就像气球不断被吹气一样。

如果内存使用量只增不减,那内存泄漏的可能性就很大了。

二、定位内存泄漏的源头2.1 代码审查这时候就得卷起袖子好好审查代码啦。

看看有没有一些地方在不断地创建对象,但是却没有及时释放。

比如说,有些新手写代码,就像一个马虎的厨师做菜,只知道往锅里加料,却忘记把用过的锅刷干净。

像在循环里不断创建新的对象,却没有在合适的地方销毁,这就是典型的内存泄漏隐患。

2.2 借助工具检测有不少好用的工具能帮我们大忙呢。

像Valgrind这个工具就像是一个侦探,能够嗅出内存泄漏的蛛丝马迹。

它可以详细地告诉我们是哪段代码在搞鬼,就像给我们指出小偷藏在哪里一样。

还有一些编程语言自带的内存分析工具,也非常实用。

2.3 分析内存分配模式我们要仔细分析内存是怎么分配的。

如果发现有一些内存块被分配后,很长时间都没有被再次使用,就像被遗忘在角落里的宝藏一样,那这里就很可能存在内存泄漏。

而且如果大量的小内存块不断被分配,却没有被回收,这也可能是内存泄漏的一种表现形式。

三、解决内存泄漏问题3.1 修复代码逻辑一旦确定了内存泄漏的源头,就要赶紧修复代码逻辑。

如果是对象没有及时释放,那就得在合适的地方加上释放的代码。

这就好比收拾房间,用过的东西要放回原位或者扔掉,不能让它们一直在房间里占地方。

3.2 进行测试验证修复完代码可不能就这么算了,还得进行测试验证。

要确保内存泄漏的问题真的被解决了。

可以长时间运行程序,看看内存使用情况是不是稳定了。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

计算机研究与发展DOI:10.7544桙issn1000‐1239.2015.20131909JournalofComputerResearchandDevelopment52(4):898906,2015 收稿日期:2013-12-17;修回日期:2014-05-12 基金项目:国家自然科学基金项目(61272086);“核高基”国家科技重大专项基金项目(2012ZX01039‐004‐08)基于中间语言的JNI内存泄漏检查蒋挺宇1 王 鹏1 杨 述1 褥 震1 董 渊1 王生原1 嵇智源21(清华大学计算机科学与技术系 北京 100084)2(科技部高技术研究发展中心 北京 100044)(Jiangty08@gmail.com)DetectionofJNIMemoryLeaksBasedonExtendedBytecodeJiangTingyu1,WangPeng1,YangShu1,RuZhen1,DongYuan1,WangShengyuan1,andJiZhiyuan21(DepartmentofComputerScienceandTechnology,TsinghuaUniversity,Beijing100084)2(HighTechnologyResearchandDevelopmentCenter,MinistryofScienceandTechnology,Beijing100044)Abstract TheJavanativeinterface(JNI)enablesJavacoderunninginaJavavirtualmachine(JVM)tobecalledbynativecode,butthedifferenceofsecurityfeaturesbetweenlanguagesmakesitasecurityweakness,whichcannotbedetectedbyexistinganalysismethods.Commonlyuseddetectionmethodsaremainlybasedontheanalysisofintermediatelanguage,whichisinvalidinthisJNIcase,sincethelackofanintermediaterepresentationtobridgeJavaandC++.ThispaperanalyzesJNIfromaJava桙C++cross‐languageperspectiveandfocusesonmemoryleakswhichfrequentlyoccurinJNIcalls.Inordertoovercomelanguagebarriers,thispaperproposesextendedBytecode(Bytecode倡)instructionsasinterpretationofC++semantics.Ourcontributionsaredescribedasfollows:1)DefineablockmemorymodelwhichiscompatiblewithbothJavaandC++;2)DesigntranslationrulesfromC++toextendedJavaBytecodebasedonLLVM桙LLJVM;3)Constructamethodcallgraph,extractabstractanddetectmemoryleaksinJNIcallsbyinterproceduralanalysis.ExperimentsontypicalJNIcodewithmemoryleakfeaturesshowthatouranalysisworkcandetectmemoryleaksinJava桙C++accurately,andisofimportantsignificanceincross‐linguisticprogrammingandvulnerabilityanalysis.Keywords Javanativeinterface(JNI);cross‐linguisticanalysis;semanticextension;Bytecode;memoryleak摘 要 JNI技术支持Java与本地C桙C++的相互调用,在Android等混合语言实现的系统中有着广泛应用,但语言之间的安全特性差异使其成为安全薄弱环节,现有的分析方法难以处理多语言相互调用产生的安全缺陷.以JNI调用中易产生的内存泄漏为例,开展Java桙C++JNI跨语言分析的研究.采用扩展的JavaBytecode(Bytecode倡)指令作为C++语义的解释来消除跨语言分析的障碍.围绕JNI调用中内存泄漏的问题,做了以下3方面工作:1)定义兼容Java桙C++语言的分块内存模型;2)基于LLVM桙LLJVM,设计实现了C++到Bytecode倡的翻译策略;3)建立方法调用图,提取方法摘要,利用过程间分析方法检测JNI调用中的内存泄漏.针对具有典型内存泄漏特征的JNI实例翻译检测表明,该工作能够准确检测出Java桙C++混合语言中的内存泄漏,对于JNI混合语言编程的理解和漏洞分析具有重要价值.关键词 Java本地调用;跨语言分析;语义扩展;字节码;内存泄漏中图法分类号 TP314 JNI(Javanativeinterface)编程是一项复杂的工作,其编程规范[1]中列出了多达15种JNI编程中容易出现的错误,这些错误很难通过编译器来发现.除了程序员使用JNI调用失误而造成的程序错误之外,黑客们也开始针对软件系统中的JNI接口缺陷,编写恶意代码来越过Java虚拟机的保护机制,以达到非法的目的.Android操作系统基于Linux开源操作系统,是目前最为流行的移动操作系统[2].为方便开发,Android采用Java作为其应用程序开发语言,而底层库则由本地C代码实现,两者通过Dalvik虚拟机以及JNI机制进行通信.本文研究发现,Android2畅2系统中有JNI接口3186个,其中443个采用C语言实现,其余2743个均采用C++语言实现,C++实现的JNI接口中有1837个位于系统核心框架frameworks中.由于Java语言和C++语言之间的安全特性差异,这些JNI接口成为安全薄弱环节,一旦出现问题,后果可能十分严重.2010年Kaspersky首次发现了针对Android系统的SMS木马,其危害是泄漏个人数据[3].之后,Android平台上恶意代码呈井喷之势爆发,至今仍保持着较高的增长速度.Davi等人[4]详细介绍了一种利用JNI接口对本地C代码进行溢出攻击的原理和代码实例,该方法可以轻易突破Android的权限保护和JVM(Javavirtualmachine)的沙箱保护,在不经过任何授权的情况下获取超级用户权限.由于JVM桙Dalvik对本地代码高度的信任,JNI接口缺陷逐渐成为恶意软件利用的重灾区[5].目前对于Java程序的安全监测和验证工作主要是基于Bytecode开展研究,但这种方式无法针对混合语言开展分析,大多数的检测器选择完全忽略本地代码的危害,所以难以得到准确的结果.本文提出了一种从JNI两端整体来分析程序的方案,针对JNI接口的多语言编程模型,将整个程序翻译到扩展的JavaBytecode中间表示,利用过程间分析达到跨语言检测的目的.1 相关工作综述1.1 现有分析检测技术在JNI调用中,Java代码和本地代码的交互是程序的主体,现有技术手段往往仅在一端开展安全检测,无法有效处理JNI中由于跨语言控制流带来的安全问题.针对JavaBytecode的开源静态检测工具有很多.Findbugs[6]采用Visitor模式,查找代码中与某种缺陷模式匹配的错误.但是,Findbugs专注于过程内分析,对于跨过程分析的能力十分有限.Soot是一个Java优化和分析框架,可以解析class文件,构建控制流图和调用图,执行指针指向和空指针分析,并且支持数据流分析.Soot[7]框架比较适合构建专门的JavaBytecode分析器.另外一些检测技术仅在本地代码端展开.Lint[8]一类的工具采用类型分析方法,手工对访问内存的操作进行大量注释以辅助内存分析,且没有利用控制流信息,结果的准确性有限.Kondoh等人利用静态分析技术在缺陷查找工具BEAM[9]中实现了针对本地C代码的分析,对JNI编程范例中所列包括资源泄漏在内的几项错误进行检测[10],可以分析特定接口函数导致的资源泄漏问题,但局限于函数过程内部,检测范围有限.这些方法在JavaBytecode类型、语义、逻辑系统以及验证等方面取得了大量研究成果,如果能利用JavaBytecode实现本地代码语义的解释,这些成果会大大降低Java桙C++JNI跨语言分析的代价.1.2 JNI接口的分析现状JNI分析的最大难点就是如何消除多语言对分析器的影响.Zhao等人[11]给出一种Bitcode中间表示的形式化模型,用于构造和验证可信的LLVM优化器,而LLJVM项目还提供了一种将LLVMBitcode翻译为JavaBytecode的框架,支持C语言特征[12].但是这些翻译通常并不提供针对JNI问题检测的跨语言处理,给检测带来很大困难,在这些中间语言上重新构建JNI缺陷分析器的代价又很大.Furr和Foster设计了JSaffire来寻找JNI相关的类型错误[13];Kondoh和Onodera设计了一个类似的类型检测系统;Tan等人建立了SafeJNI[14]和ILEA[15]框架方法,寻找Java桙CJNI接口中的安全错误.这些方法对JavaBytecode进行了一定的扩展,将C语言翻译到扩展的JavaBytecode,使Java分析器可以理解C代码的语义,并对之进行形式化验证.该方法只需建立C语言到Bytecode的翻译器,省略了很多C语言的复杂特性,利用丰富的Java分析技术,避免高昂的开销,对JavaBytecode指令的扩展侧重于翻译后的可检查性.但上述方法局限于C语言,无法处理C++代码,而本地代码中C++的比例不断增大,而且包含更多的语言特性,因此需要进一步的研究.998蒋挺宇等:基于中间语言的JNI内存泄漏检查1.3 本文研究内容为了检测Java程序中JNI调用涉及多语言交互所引发的问题,本文提出将不同语言向同一中间表示转换、然后基于中间表示展开分析的方案,构建如图1所示的Java桙C++跨语言静态分析与检测平台.Fig.1 Workflowchart.图1 工作流程图Java应用程序中,本地代码实际比例相对Java语言要低,而且JavaBytecode作为编译后的二进制码可以保留足够的类型信息,并且有一些成熟的Bytecode分析框架可以利用.本文将本地语言向扩展的JavaBytecode转换,称之为Bytecode倡.如图1所示,将Bytecode倡和JavaBytecode作为一个整体开展分析.平台基于模式匹配的方式,针对不同的缺陷模式制定不同的翻译策略,将JNI调用中的本地C++代码翻译到Bytecode倡,消除不同语言的隔阂,然后扩展JavaBytecode分析工具针对具体的缺陷开展分析.因为内存泄漏是较为常见的本地代码缺陷,而且由于多语言的交互变得更加隐蔽,所以本文以它为突破口先完成JNI调用中的内存泄漏检测.2 C++到Bytecode倡的翻译技术LLVM的Bitcode拥有简单、独立的类型系统,拥有地址计算指令和处理高级语言异常处理的功能,可以保留C++的语言信息.LLJVM项目提供了Bitcode到Bytecode转换的框架,采用运行时动态库的方式实现对C语言特征的支持.LLJVM不能支持C++,而且它的翻译策略引入很多不必要的复杂信息,所以不适合本文需要的静态分析和检测要求.但是,LLJVM提供了一个可利用的Bitcode到Bytecode的翻译框架,只需在此框架上设计适合静态分析的翻译策略,提供对C++语言的支持就可以实现C++源码到Bytecode倡的翻译,本文设计的翻译策略如下:首先利用LLVM编译器C++前端llvm‐g++将C++源码翻译到LLVMBitcode;然后用翻译器对C++程序预处理,获取其中包含的类相关信息;最后结合对Bitcode语义的分析,使用本文设计的简洁翻译策略,将Bitcode翻译到Bytecode倡.2.1 内存模型C++和Java两种存储模型无法直接匹配,堆的操作也有很大差异,可能产生内存泄漏,需要设计合适的JNI存储模型,实现两种语言之间的内存模型匹配.本文建立分块内存模型(blockmodel)来解决Java桙C++的内存模型不同的问题.在分块模型中,存储堆由若干块组成,一个块可以被垃圾回收机制管理,与Java内存模型匹配,可称为J堆;其他块必须通过显式的内存分配或释放指令操作与C++的内存模型匹配,称为C堆.每个块是一个从地址到值的映射,允许地址加减,适合内存计算.这个模型与Bitecode的堆存储模型也是吻合的.在此模型基础上,可以使用Bytecode倡统一描述Java桙C++JNI接口两端对内存的操作行为,为C++到Bytecode的翻译建立基础.2.2 翻译策略与类型映射Bytecode倡是由Java字节码Bytecode扩展而来,语言特性与Java具有一定的一致性,要将C++翻译到Bytecode倡关键在于C++与Java的类型映射.本文的思路是将C++中包括基本类型在内的所有类型映射到Java的数组、类或接口等拥有引用的类型上,通过引用来模拟C++中的指针特性.为此,需要设计一套完整的C++到Java的类型映射,且尽量利用Java现有的类型简化翻译及检测的复杂度.本文定义:MapType(c)=j,其中,c为C++中的类型,j为Java中的类型.2.2.1 基本类型映射C++与Java的基本数据类型大致是相同的,例如int,double等,简单的做法就是直接对其映射,但考虑到C++中的内存访问操作,基本类型间的直接映射是无法满足需求的,例如以下代码:inti=5,倡pi=&i;009计算机研究与发展 2015,52(4)倡pi=8.Java中无法通过指针对数据进行操作,可以将int这样的基本类型对应到Java中的类或数组来获得类似于指针或别名的效果,即MapType(int)=int[]. 这样,使用数组下标可以模拟指针的加减运算以及内存操作.2.2.2 基本类型指针对于基本类型,本文可以用数组来模拟表示,但基本类型的指针仅使用数组已经无法满足要求,本文考虑设计Java类来对应,以int倡为例:ClassintP{ int[]data; intindex;};data对应int的映射,index用来处理指针加减运算.如下是C++代码:inti[10];int倡pi=&i,倡pi2;pi2=pi+2;其中,pi,pi2对应的Java类中,data域相同,index不同,可以通过index模拟两者间的加减运算.2.2.3 对象指针指向对象的指针与指向基本类型的指针基本相同,只是因为Java本身有对象引用,所以无需再利用数组封装了.对象指针可以用如下类表示:ClassobjectP{ object[]data; intindex;};其中,object为类名,基于此可递归构造诸如object倡倡这样的多级对象指针.2.2.4 函数指针C++中调用函数既可以直接调用,也可以通过函数指针调用;但在Java中,函数均被封装在类和接口中.同样地,对于函数指针,可以通过Java接口引用来模拟.C++函数指针指向的具体函数行为,在Java中可以通过继承特定接口的子类来实现.2.3 JNI接口函数及库函数处理JNI接口函数是连接Java端和本地代码端的纽带,使Java和本地代码能够相互调用通信.根据JNI接口函数的功能和使用方式,分如下3种情况处理:1)用于注册本地函数入口的接口函数.由于该类函数并不影响分析过程,因而在JNI两端合并到Bytecode倡之后不再需要,故不作翻译,最后在中间代码布局中体现即可.2)与内存泄漏无关的接口函数.这些函数的功能各样且实现复杂,但与内存泄漏无关,本文不对其具体翻译,只将其加入到白名单中即可.此外,为了不影响控制流桙数据流分析,对此类函数返回值取任意值,并对JavaBytecode扩展一条指令以实现此功能,C++标准库和第三方库函数也可采用此方式处理.3)可能导致内存泄漏的函数.类似GetString‐Chars桙ReleaseStringChars这样的接口函数,翻译其具体操作比较复杂,若检测内存泄漏,则可以扩展JavaBytecode的内存操作指令.设计native_new桙native_delete指令,用于内存的显式分配与释放.这只需用native‐new桙native‐delete来标记可能发生泄漏的接口函数,而不需要翻译具体的分配和释放过程.在分块内存模型上,完成上述对白名单函数的处理以及显式的内存分配释放,需要扩展以下3条Bytecode倡指令:1)native_new棟class棡.在C堆创建一个新对象,不受垃圾回收机制管理,必须通过native_delete显式释放.2)native_delete.释放当前栈顶通过native_new分配的对象.3)random棟type棡.在当前栈顶放置一个type类型的随机值.通过上述设计,就可以将JNI两端基本对应,将C++语言翻译到中间表示Bytecode倡.3 基于过程间分析的JNI漏洞检测3.1 内存泄漏模式内存泄漏的本质都是失去对动态分配内存的控制.从检测角度来说,本文将内存泄漏总结为2种模式:1)分配内存后,没有释放;2)分配内存后,指向该块内存的变量发生变化,导致无法释放.对内存泄漏模式来说,根据本地代码的内存分配与释放的匹配建模,可以建立基于内存泄漏模式的有限状态机,将内存变量分为3个不同的状态{UnAllocated,Allocated,Error},各种状态的含义为:UnAllocated表示变量未被分配内存;Allocated表示变量已被分配内存;Error是故障状态.109蒋挺宇等:基于中间语言的JNI内存泄漏检查可以通过构造如图2所示的状态转换图描述和寻找这样的问题.Fig.2 Statetransitionofmemoryleak.图2 内存泄漏状态转换图状态转移条件如表1所示:Table1 StateTransitionConditions表1 状态转换条件StateTransitionStateTransitionConditionsUnAllocated→AllocatedAllocatememoryforvariables.Allocated→UnAllocatedReleasememoryofvariables.Allocated→AllocatedOtheroperation.Allocated→ErrorProgramexitsorvariablesareinaccessible.3.2 过程间JNI内存泄漏检测设计根据分析的范围和目标,分析方法可以分为过程内分析和过程间分析;而JNI调用可能涉及内存泄漏问题,其本质上是C++函数和Java方法互相调用的结果,并非局限于一个方法内,因此必须进行过程间分析.此外针对内存泄漏,只要有一条程序运行路径没有达成内存申请与释放的匹配,本文就可以认为程序有出现内存泄漏的风险,所以还需要进行路径敏感的分析策略.过程间分析[16‐18]与路径敏感分析[19‐21]已经有不少相关的研究和对应的工具出现,他们都有各自的关注点.本文的内存泄漏检测是基于数据流分析的,需要完成过程间的数据流分析,当遇到方法调用时如何处理方法对数据流产生的影响是解决问题的关键.基于摘要的过程间分析方法非常灵活,可以根据分析的需求定义不同的摘要信息,按照摘要的详细程度也可以控制分析的精度,具有较好的扩展性,能够很方便地扩展到大规模的程序分析中去.本文设计了如图3所示的基于摘要过程间分析框架.整个过程间分析系统可以分为3大块,分别是对Bytecode倡的预处理模块、过程内分析模块以及过程间分析与方法摘要模块,具体如下:1)预处理模块是对转化好的Bytecode倡进行分Fig.3 Interproceduralanalysis.图3 过程间分析框架图析,生成对应规模的调用图,对涉及到的所有方法进行排序,不考虑方法自身直接递归的情况,同时初始化方法摘要.2)过程内分析模块是整个系统的核心模块,因为过程间分析最终要通过方法摘要转化到过程内分析.该模块生成每个方法的控制流图,实施实际的内存泄漏检测,获取与应用方法摘要,保留分析后的结果.3)过程间分析与方法摘要模块是整个分析过程的连接枢纽,主要是提供过程间分析框架,按照顺序组织分析的过程,通过过程内分析的结果生成方法摘要,在分析结束后报告结果.3.3 基于Soot的过程间内存泄漏检测实现Soot是加拿大McGill大学Sable研究小组开发的针对JavaBytecode的优化和分析工具,它面向不同的分析和优化目的建立了各种内部的中间表示,既可以辅助过程内分析,也能为过程间分析提供支持,而且具有较好的扩展性,所以本文选择Soot作为本文分析工具的基础框架.3.3.1 调用图生成和预处理Soot提供了多种不同调用图算法的具体实现,无论使用哪种调用图构建算法,只是相对地提高了精度,还需要自己实现调用图的修剪工作.读入原始调用图后,从调用图的入口节点按照调用关系做一个广度优先遍历,只有能从入口节点直接或间接到达而且没有被过滤器过滤的方法才会被加入辅助调用图中,它的前驱和后继都会被保存下来.为减少后期迭代的次数,需要对这些方法进行拓扑排序,由于调用图不保证无环,采用对辅助调用图节点倒序排序.209计算机研究与发展 2015,52(4)3.3.2 过程内分析和摘要提取Soot中提供3种不同的数据流分析框架,由于内存缺陷是路径敏感,所以本文采用Forward‐Branched‐FlowAnalysis框架,它具备不同的信息通过各分支的分支节点传播的分析能力,对应着路径敏感的数据流分析.检测方法通过扩展上述框架实现,对每一个程序语句节点s的数据流值集合In[s],提供了2个数据流值集合来表述语句转换后的新数据流值集合———直接流向的集合(fallthroughOUT)和分支流向的集合(branchOUT),用以保存语句不同分支的数据流值,达到路径敏感的目的.摘要提取在过程内分析的基础上进行,每个方法结束时我们保留必要的数据流状态信息,作为这个函数的摘要.3.3.3 过程间分析检测完成过程间分析,需要组织整个分析过程,建立过程间分析框架,对所有方法进行分析,定义过程间分析类.分析在类的成员方法中展开,基于经典的工作队列算法实现,具体过程是按拓扑排序对每个方法开展分析,执行过程内分析算法.当遇到方法调用时,获得被调用方法的摘要,将其对数据流状态的影响作用于上下文中,完成分析后生成方法的摘要,如果摘要信息与已保存的信息不同,就对所有调用过它的方法重新分析,获得新的摘要信息,如此迭代直到所有方法的摘要信息都不再改变时,就完成了分析过程.整个过程中,方法摘要信息以及进行过程间分析时的控制流处理对于检查方法的精度有着决定性的影响.详细的摘要信息能够扩大检测的覆盖率;精细的控制流处理对于加强大规模复杂程序的检测准确率、降低误判情况更有帮助.目前的分析检测策略能准确检测出典型内存泄漏,设计扩展更大规模更复杂的分析策略以应用到更复杂的场景中也是我们下一步的研究方向.4 典型内存泄漏检测过程实现了整个安全检测方法之后,本文对实际的Java桙C++JNI调用混合语言程序进行检测,并简要介绍分析过程,如下是一个典型的JNI环境中内存泄漏实例:1)Java代码:…⑩privatestaticnativevoidallocobj();皕瑏瑡privatestaticnativevoidreleaseobj();皕瑏瑢publicvoidtestrun(booleanflag){皕瑏瑣for(inti=0;i<100000;i++){皕瑏瑤 allocobj();皕瑏瑥 if(flag)releaseobj();桙倡mayleak倡桙皕瑏瑦 }皕瑏瑧}皕瑏瑨static{Sytem.loadLibrary(“leak‐jni”);}…2)C++代码:…⑤classClock{…⑩private:皕瑏瑡intA[10000];皕瑏瑢}皕瑏瑣staticClock倡f=NULL;皕瑏瑤extern“C”{皕瑏瑥JNIEXPORTvoidJNICALLJava_test_HelloJNI_allocobj(JNIEnv倡env,jobjectthiz){皕瑏瑦 f=newClock();皕瑏瑧}皕瑏瑨JNIEXPORTvoidJNICALLJava_test_HelloJNI_releaseobj(JNIEnv倡env,jobjectthiz){皕瑏瑩 deletef;皕瑐瑠}}JNI本地函数Java_test_HelloJNI_allocobj(),Java_test_HelloJNI_releaseobj()分别实现了内存申请和释放,Android应用程序Java代码中函数testrun()通过JNI接口调用这2个函数,内存释放与参数flag的取值有关,并非所有执行路径上都能够调用内存释放操作,因此可能造成内存泄漏,大量的内存泄漏可能导致当前进程崩溃,采用已有的分析工具尚无法对此类跨语言跨过程的漏洞进行分析.如果仅在Java端代码展开分析,结果如下:代iconst_0①istore_2②goto18(+16)…309蒋挺宇等:基于中间语言的JNI内存泄漏检查⑤invokestatic #27棟cn桙ysh桙Ytool桙tests桙Test桙allocobj()V棡…⑧iload_1⑨ifeq15(+6)…皕瑏瑢invokestatic #29棟cn桙ysh桙Ytool桙tests桙Test桙releaseobj()V棡…皕瑏瑥iinc2by1…皕瑏瑨iload_2皕瑏瑩sipush10000…皕瑐瑢if_icmplt5(-17)…皕瑐瑥returnJava端对于allocobj和releaseobj的分析仅限于2个本地方法声明,而对其实际的操作功能一无所知,所以在此基础分析难以找到问题.按照本文的方案,将C++代码转化为Bytecode倡,并与Java合并后allocobj和releaseobj转化为本地静态方法,对应地调用了native_new和native_delete指令,且有两者的具体实现:…皕瑔瑩swap皕瑖瑠getfield #94棟org桙thu桙lljvm桙helper桙_jarray_JNITYP2桙dataIndex]…皕瑖瑣aload_1皕瑖瑤aastore皕瑖瑥invokestatic #117棟org桙thu桙lljvm桙helper桙ClockP1桙native_new()棡…皕瑖瑨astore6…皕瑘瑠aload6…皕瑘瑢astore7…经过分析可以得到2个方法的摘要分别为allocobj({棟f,ClockP2,{f},A棡}),releaseobj(State(f,A);{棟f,ClockP2,{f},U棡}).allocobj的摘要表示该方法进行的操作:给类Clock的指针f进行了分配内存操作;A代表Allocate.releaseobj的摘要,表示该方法进行的操作:给类Clock的指针f进行了类型释放操作;U代表Unallocate,同时操作前状态是已为f分配了内存;State表示操作涉及的变量的内存状态.因而,通过摘要可以确定allocobj方法和releaseobj需要配对出现.至此,问题被转化为Bytecode倡语言内过程间分析.分析流程如图4所示:Fig.4 Analysisprogressoftestrun.图4 testrun方法分析流程allocobj方法结束后的数据流集为{棟f,ClockP2,{f},A棡},releaseobj的数据流集为{棟f,ClockP2,{f},U棡},经过变换作为2个方法的摘要.在数据流合并操作merge(T,F)之后,数据流集为{棟f,ClockP2,{f},A棡},此时testrun退出,数据流状态为f已分配内存,没有释放,报告一个可能内存泄漏的检查点.表2为对多种内存泄漏问题检测结果,所使用的例子来自现有的JNI内存泄漏代码以及研究中设计的简单例子,经测试均可通过本文的分析方法找到问题所在.Table2 ResultsofMemoryLeakDetection表2 对多种内存泄漏问题的检测结果ProblemsDetectionResultsNotatalltheprogramexecutionpathtoreleaseallocatedmemory.SuccessMemoryisallocatedbutnotreleasedinmethodcall.SuccessMemoryisallocatedmanytimesbutonlyreleasedonceinaloop.SuccessAllocateandreleaseactionnotmatchinginsomepath.Success通过对多个例子的分析对比,本文方法能够将JNI两端语言转换到同一中间表示,且保留内存操409计算机研究与发展 2015,52(4)作的语义特征,消除多语言带来的分析障碍.虽然大规模复杂样例的测试验证有待进一步研究完善,但通过典型例子的实验论证了方法的有效性和可行性.5 结论及未来工作展望随着使用Java语言开发的应用程序日益增多,对性能的要求以及嵌入式操作系统的需要越来越高,JNI本地接口技术发挥着越发重要的作用.由于JNI接口所调用的本地语言如C++,在安全机制上与Java语言存在着明显的差异,导致两者交互调用的过程中可能存在安全隐患.现有的检测工具大多仅能在Java或本地代码一端进行检测,已有的跨语言分析技术也局限于Java桙C或者过程内分析,无法有效地处理JNI中Java桙C++间由于跨语言控制流带来的安全问题.针对这一情况,本文设计实现了基于扩展的JavaBytecode(Bytecode倡)中间语言的过程间分析检测方法,并以典型的内存泄漏代码为例进行了实验.结果表明,本文工作能够准确检测出Java桙C++混合语言中的内存泄漏问题.JNI跨语言调用可能引发的安全缺陷并不局限于内存泄漏,目前的翻译和检测主要围绕内存泄漏,但整个方案的设计已经考虑到了将来的扩展性.因此,下一步的工作是在完善现有方法的基础上扩展跨语言检测平台的功能,并进行更大范围的量化分析和有效性验证,主要包括:C++中强制类型转换等操作尚未进行扩展,接下来可根据不同安全缺陷特征进行完善;对于JavaBytecode扩展指令进行形式化的验证;构建更多的跨语言检测模型,应用到更大规模的分析环境中去.致谢 在此,我们向对本文的工作给予建议的同行,特别是Intel中国研究院陈兴中先生、中国科学技术大学冯新宇教授和华保健副教授、Lehigh大学谭刚博士等人以及第十二届全国软件与应用学术会议(NASAC2013)的评审专家们表示感谢!参考文献[1]LiangSheng.TheJavaNativeInterfaceProgrammer摧sGuideandSpecification[M].Reading,MA:Addison‐Wesley,1999[2]DevelopersofAndroid.WhatisAndroid[EB桙OL].2011[2012‐02‐10].http:桙桙developer.android.com桙guide桙basics桙what‐is‐android.htm[3]PerezS.FirsttrojanforAndroidphonesgoeswild[EB桙OL].2012[2012‐03‐10].http:桙桙readwrite.com桙2010桙08桙09桙first_trojan_for_android_phones_goes_wild[4]DaviL,DmitrienkoA,SadeghiA‐R,etal.Privilegeescalationattacksonandroid[G]桙桙LNCS6531:Procofthe13thIntConfonInformationSecurity.Berlin:Springer,2011:346360[5]SchmidtAD,SchmidtHG,BatyukL,etal.Smartphonemalwareevolutionrevisited:Androidnexttarget[C]桙桙Procofthe4thIntConfonMaliciousandUnwantedSoftware.Piscataway,NJ:IEEE,2009:17[6]AyewahN,PughW,MorgenthalerJD,etal.UsingFindBugsonproductionsoftware[C]桙桙Procofthe22ndACMSIGPLANConfonObject‐OrientedProgrammingSystemsandApplicationsCompanion.NewYork:ACM,2007:805806[7]EinarssonA,NielsenJD.Asurvivor摧sguidetoJavaprogramanalysiswithSoot(Version1.1)[EB桙OL].(2008‐07‐17)[2012‐03‐10].http:桙桙www.brics.dk桙SootGuide[8]DevelopersofAndroid.AndroidLint[EB桙OL].2011[2012‐02‐10].http:桙桙tools.android.com桙tips桙lint[9]BrandD.Errordetectionbydataflowanalysisrestrictedtoexecutablepaths[EB桙OL].NewYork:IBMTJWatsonResearchCenter,1999[2012‐03‐04].http:桙桙www.research.ibm.com桙da桙beam.htmls[10]KondohG,OnoderaT.FindingbugsinJavanativeinterfaceprograms[C]桙桙Procofthe2008IntSymponSoftwareTestingandAnalysis.NewYork:ACM,2008:109118[11]ZhaoJianzhou,NagarakatteS,MartinMM,etal.FormalizingtheLLVMintermediaterepresentationforverifiedprogramtransformations[J].ACMSIGPLANNotices,2012,47(1):427440[12]RobertsDA.LLJVM[EB桙OL].2012[2012‐10‐23].http:桙桙da.vidr.cc桙projects桙lljvm[13]FurrM,FosterJS.PolymorphicTypeInferencefortheJNI[M].Berlin:Springer,2006:309324[14]TanGang,AppelAW,ChakradharS,etal.SafeJavanativeinterface[C]桙桙ProcofIEEEIntSymponSecureSoftwareEngineering.Piscataway,NJ:IEEE,2006:97106[15]TanGang,MorrisettG.ILEA:Inter‐languageanalysisacrossJavaandC[J].ACMSIGPLANNotices,2007,42(10):3956[16]BoddenE.Inter‐proceduraldataflowanalysiswithifds桙ideandsoot[C]桙桙ProcoftheACMSIGPLANIntWorkshoponStateoftheArtinJavaProgramAnalysis.NewYork:ACM,2012:38[17]RepsT,HorwitzS,SagivM.Preciseinterproceduraldataflowanalysisviagraphreachability[C]桙桙Procofthe22ndACMSIGPLAN‐SIGACTSymponPrinciplesofProgrammingLanguages.NewYork:ACM,1995:4961[18]SharirM,PnueliA.ProgramFlowAnalysis:TheoryandApplications[M].EnglewoodCliffs,NJ:Prentice‐Hall,1981:189233509蒋挺宇等:基于中间语言的JNI内存泄漏检查[19]CadarC,GaneshV,PawlowskiPM,etal.EXE:Automaticallygeneratinginputsofdeath[J].ACMTransonInformationandSystemSecurity,2008,12(2):1024[20]DilligI,DilligT,AikenA.Sound,completeandscalablepath‐sensitiveanalysis[J].ACMSIGPLANNotices,2008,43(6):270280[21]DorN,AdamsS,DasM,etal.Softwarevalidationviascalablepath‐sensitivevalueflowanalysis[J].ACMSIGSOFTSoftwareEngineeringNotes,2004,29(4):1222JiangTingyu,bornin1990.MastercandidateattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering.WangPeng,bornin1980.MasterattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering(wphf1980@163.com).YangShu,bornin1978.MasterattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering(come_go@163.com).RuZhen,bornin1991.MastercandidateattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.Hismainresearchinterestsincludesystemsoftwareandsoftwareengineering(ruzhen9999@163.com).DongYuan,bornin1973.PhD,associateprofessorattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.MemberofChinaComputerFederation.Hismainresearchinterestsincludeoperatingsystem,compilerandlanguage‐basedsecurity(dongyuan@tsinghua.edu.cn).WangShengyuan,bornin1964.PhD,associateprofessorattheDepartmentofComputerScienceandTechnology,TsinghuaUniversity.SeniormemberofChinaComputerFederation.Hismainresearchinterestsincludeprogramminglanguagesandsystems,petrinetapplication(wwssyy@tsinghua.edu.cn).JiZhiyuan,bornin1956.SeniorEngineerintheHighTechnologyResearchandDevelopmentCenter.Hismainresearchinterestsincludecomputerscienceandembeddedsoftware,technologymanagementofthenationalscienceandtechnologyplan(jzy@htrdc.com).609计算机研究与发展 2015,52(4)。

相关文档
最新文档