一种汇编冗余指令的检测方法及装置与流程

文档序号:17160317发布日期:2019-03-20 00:36阅读:227来源:国知局
一种汇编冗余指令的检测方法及装置与流程
本发明涉及计算机程序分析和代码优化领域,具体涉及汇编代码中的冗余指令检测问题,特别涉及一种汇编冗余指令的检测方法及装置。
背景技术
:冗余指令检测是计算机软件开发和维护活动中一项重要的任务,在软件维护、软件缺陷检测、程序理解等多个领域中都有广泛的应用。如果人工排查冗余指令,不仅费力易错,也无法保证检测的完备性和正确性。本专利提出一种冗余指令的自动化检测方法,避免了人工消耗和失误,保证了测试的完备性和正确性。汇编程序中的代码可分为主体代码和不相关代码,主体代码可分为标号和指令,指令可细分为数据传输指令、算术运算指令、逻辑运算指令、串指令及(程序)转移指令。从数据处理的角度讲,寄存器存在两种状态,被读或被写。某些寄存器在某一时刻的状态被称为寄存器状态集合,在某段时间内的状态变换被称为寄存器状态转移集合。控制流图cfg(controlflowgraph)是以基本块为节点的有向图满足下述条件:n表示程序p中的一个基本块。e表示两个基本块之间的控制流,ni,nj∈n。基本块是一段只含有一个入口和一个出口的指令序列。基本块是构成控制流图的最小单元,也是冗余指令检测的最小单元。一般而言,同样的功能,汇编代码可以比高级语言实现更高的性能。但由于汇编代码不直观的特点,开发者往往难以高效实现,通常会出现一些对寄存器的冗余调用。另外,静态二进制翻译中也通常会出现一些冗余汇编代码,而现有的优化方法大部分集中在中间代码层,对目标代码中存在的大量冗余指令较少关注。参考文献(“二进制翻译关键技术研究”,马湘宁,中国科学院,2004年4月1日)主要对中间代码层进行了优化研究,并未对目标代码中存在的大量冗余指令进行关注。技术实现要素:针对存在的上述问题,本发明提出一种汇编冗余指令的检测方法及装置,通过本发明可以快速、准确的检测出汇编冗余指令,从而更有利于进行代码优化。本发明要解决的技术问题是:对于包含大量跳转语句的汇编代码,如何检测其中的冗余指令。本发明提出一种冗余指令检测方法。为了实现上述目的,本发明采用以下技术方案:一种汇编冗余指令的检测方法,包括以下步骤:步骤1:设定指令集数据表,所述指令集数据表包括汇编代码对应的所有指令的操作符、类型及对应的寄存器读写模式,根据指令集数据表对汇编代码进行预处理;步骤2:逐行遍历预处理后的汇编代码,利用正则表达式匹配每行汇编代码的首单词,匹配成功则认为该行汇编代码是标号,否则认为该行汇编代码是指令;若该行汇编代码是指令,则该行汇编代码的首单词为当前指令的操作符,通过当前指令的操作符和指令集数据表得出当前指令的类型,标记预处理后的汇编代码中的转移指令,并通过指令集数据表得出非转移指令的寄存器读写模式;步骤3:依据所述寄存器读写模式,获取当前指令的寄存器使用情况;步骤4:根据当前指令的寄存器使用情况,根据冗余指令检测规则判断当前指令是否为冗余指令,若当前指令为冗余指令,则对冗余指令进行删除。进一步地,所述预处理包括:通过指令集数据表对所述代码进行逐行遍历,通过字符串匹配行首单词的方式,识别并删除代码中的不相关代码。进一步地,所述步骤2还包括:以汇编代码中的标号和转移指令为间隔,将汇编代码划分为若干基本块,利用转移指令得出各基本块间的跳转关系,从而获得汇编代码的控制流图及所有运行分支。进一步地,所述步骤3包括:逐条遍历基本块中的指令,利用0和1记录寄存器状态,获取各基本块的寄存器状态转移集合,依据汇编代码的控制流图链接各基本块,获取各运行分支的寄存器状态转移集合。进一步地,所述根据当前指令的操作符和指令集数据表得出寄存器读写模式具体指:根据当前指令的操作符采用字符串匹配的方法,在指令集数据表中查询操作符对应的寄存器读写模式。进一步地,所述冗余指令检测规则为:如果寄存器在使用时连续出现两条写指令,则认为第一条写指令为冗余指令;如果寄存器在使用时运行分支的最后一条指令为写指令,则认为该指令为冗余指令。进一步地,所述根据冗余指令检测规则对冗余指令进行删除具体指:根据上述规则标记各运行分支的冗余指令,若某指令在所有运行分支中都被标记为冗余,则认为该指令冗余,删除该指令。一种汇编冗余指令的检测装置,包括:预处理模块,用于设定指令集数据表,所述指令集数据表包括汇编代码对应的所有指令的操作符及对应的寄存器读写模式,根据指令集数据表对汇编代码进行预处理;匹配模块,用于逐行遍历预处理后的汇编代码,利用正则表达式匹配每行汇编代码的首单词,匹配成功则认为该行汇编代码是标号,否则认为该行汇编代码是指令;若该行汇编代码是指令,则该行汇编代码的首单词为当前指令的操作符,通过当前指令的操作符和指令集数据表得出当前指令的类型,标记预处理后的汇编代码中的转移指令,并通过指令集数据表得出非转移指令的寄存器读写模式;获取模块,用于依据所述寄存器读写模式,获取当前指令的寄存器使用情况;删除模块,用于根据当前指令的寄存器使用情况,根据冗余指令检测规则判断当前指令是否为冗余指令,若当前指令为冗余指令,则对冗余指令进行删除。进一步地,所述获取模块还包括:划分模块,用于以汇编代码中的标号和转移指令为间隔,将汇编代码划分为若干基本块,利用转移指令得出各基本块间的跳转关系,从而获得汇编代码的控制流图及所有运行分支。与现有技术相比,本发明具有的有益效果:1.本发明提出了冗余指令检测规则,有效地得出代码中对寄存器冗余使用的指令,并对冗余使用的指令进行删除,方便进行代码优化。2.本发明通过设定指令集数据表的方式,有效支持了对不同指令集的汇编代码的冗余指令检测,扩展了方法的应用范围。3.本发明改进了冗余指令标注方法,利用0、1表示寄存器的使用状态,将复杂的寄存器调用关系转化为二进制字符串,方便代码中各指令的寄存器使用情况的获取。4.本发明通过转移指令获取程序的控制流图,实现了检测路径的全覆盖,保证了结果的可靠性。附图说明图1为本发明实施例的一种汇编冗余指令的检测方法的基本流程图。图2为本发明实施例的代码的控制流图。图3为本发明实施例的一种汇编冗余指令的检测装置的结构示意图。具体实施方式下面结合附图和具体的实施例对本发明做进一步的解释说明:实施例一:如图1所示,一种汇编冗余指令的检测方法,包括以下步骤:步骤s101:设定指令集数据表,所述指令集数据表包括汇编代码对应的所有指令的操作符、类型及对应的寄存器读写模式,根据指令集数据表对汇编代码进行预处理;本实施例中,汇编指令包括如下类型:数据传输指令、算术运算指令、逻辑运算指令、串指令及(程序)转移指令;本实施例中,寄存器读写模式包括“被读”和“被写”两种寄存器状态。所述预处理包括:通过指令集数据表对所述代码进行逐行遍历,通过字符串匹配行首单词的方式,识别并删除代码中的不相关代码。作为一种可实施方式,本实施例的指令集数据表为“神威·太湖之光”平台指令集。具体地,将“神威·太湖之光”平台指令集作为指令集数据表,输入待检测汇编代码段1,通过指令集数据表对汇编代码段1进行逐行遍历,通过字符串匹配行首单词的方式,自动检测并删除汇编代码段1中的注释、数据定义伪指令(.quad、.short、.byte等)、符号定义伪指令(.set、.global、.extern等)、控制伪指令(.section、.text、.align等)、预编译指令(头文件包含、宏替换、条件编译等)等不相关代码,得到汇编代码段2。汇编代码段1为:汇编代码段2为:步骤s102:逐行遍历预处理后的汇编代码,利用正则表达式匹配每行汇编代码的首单词,匹配成功则认为该行汇编代码是标号,否则认为该行汇编代码是指令;若该行汇编代码是指令,则该行汇编代码的首单词为当前指令的操作符,通过当前指令的操作符和指令集数据表得出当前指令的类型,标记预处理后的汇编代码中的转移指令,并通过指令集数据表得出非转移指令的寄存器读写模式;非转移指令即为数据传输指令、算术运算指令、逻辑运算指令及串指令。所述步骤s102还包括:以汇编代码中的标号和转移指令为间隔,将汇编代码划分为若干基本块,利用转移指令得出各基本块间的跳转关系,从而获得汇编代码的控制流图及所有运行分支。具体地,本实施例中预处理后的汇编代码为汇编代码段2,首先利用正则表达式“.*:”匹配汇编代码段2中每行汇编代码的首单词,匹配成功则认为该行汇编代码是标号,否则认为该行汇编代码是指令;若该行汇编代码是标号,则将当前行标注为pi,其中i从0开始,每次标记后递增1;若该行汇编代码是指令,通过该行汇编代码的首单词(操作符)查询指令集数据表,得出对应的指令类型,若当前指令为转移指令,则将当前行标注为pi,其中i从0开始,每次标记后递增1;若该行汇编代码为指令,但并非转移指令,则在指令集数据表中查询当前指令的操作符,获取对应的寄存器读写模式。步骤s103:依据所述寄存器读写模式,获取当前指令的寄存器使用情况;所述步骤s103包括:逐条遍历基本块中的指令,利用0和1记录寄存器状态,获取各基本块的寄存器状态转移集合,依据汇编代码的控制流图链接各基本块,获取各运行分支的寄存器状态转移集合。具体地,根据指令的寄存器读写模式,记录当前指令的寄存器状态。当前指令的寄存器状态若为被读,则将当前指令的寄存器状态标注为0,当前指令的寄存器状态若为被写,则将当前指令的寄存器状态标注为1。最终,每个寄存器都会对应生成一个二进制字符串,即该寄存器的状态转移集合,如表1所示。表1汇编代码段2对应的寄存器状态转移集合表寄存器名状态转移集合x010000000t0100t11010t210010t311010t50f0111f1001010f210f31010f410f510f61010f710f22001f28000000表格1中的二进制字符串是串行瀑布式读取代码获取得到的,并未考虑汇编代码内部的跳转关系。因而,有必要根据跳转关系重新划分寄存器的状态转移集合。(pi,p(i+1))之间的汇编代码被视为一个基本块,并编号为nj,j从0开始,每次标记后递增1,由此可将汇编代码段2划分为5个基本块,分别为基本块ⅰ、基本块ⅱ、基本块ⅲ、基本块ⅳ和基本块ⅴ,如汇编代码段3所示。汇编代码段3为:从n0开始,若基本块内最后一条指令为转移指令,则提取该转移指令的目标地址,与代码中的标号进行字符串匹配,匹配到的标号即为新分支的起点,如此递归便可获得汇编代码段3的控制流图,如图2所示。然后根据汇编代码段3的控制流图,组合各基本块,得到各运行分支的寄存器状态转移集合。各运行分支(运行分支1:ⅰ→ⅳ、运行分支2:ⅰ→ⅱ→ⅴ、运行分支3:ⅰ→ⅱ→ⅲ)的寄存器状态转移集合如表格2所示。表格2各运行分支的寄存器状态转移集合表表2中,“-”表示该分支各基本块中的汇编代码未使用对应寄存器。步骤s104:根据当前指令的寄存器使用情况,根据冗余指令检测规则判断当前指令是否为冗余指令,若当前指令为冗余指令,则对冗余指令进行删除。所述根据当前指令的操作符和指令集数据表得出寄存器读写模式具体指:根据当前指令的操作符采用字符串匹配的方法,在指令集数据表中查询操作符对应的寄存器读写模式。所述冗余指令检测规则为:如果寄存器在使用时连续出现两条写指令,则认为第一条写指令为冗余指令;如果寄存器在使用时运行分支的最后一条指令为写指令,则认为该指令为冗余指令。所述根据冗余指令检测规则对冗余指令进行删除具体指:根据上述规则标记各运行分支的冗余指令,若某指令在所有运行分支中都被标记为冗余,则认为该指令冗余,删除该指令。具体地,表格2中各运行分支的寄存器状态转移集合,如果出现011或110,则标记第一次出现的1为冗余,则其对应的指令标记为冗余指令;或者,如果二进制串的最后一位为1,则将其标记为冗余,其对应的指令标记为冗余指令(除某些特殊寄存器外,如$f0、$0,二者为返回寄存器,对其的写入操作并非冗余)。标记的运行分支的寄存器状态转移集合如表格3中加粗部分所示。最后,综合各分支的冗余情况,发现t3寄存器的第一条指令,“andt0,t1,t3”在所有运行分支中都被标记为冗余指令,因而认为该指令冗余,将其剔除。表格3标记的运行分支的寄存器状态转移集合表实施例二:如图3所示,一种汇编冗余指令的检测装置,包括:预处理模块301,用于设定指令集数据表,所述指令集数据表包括汇编代码对应的所有指令的操作符及对应的寄存器读写模式,根据指令集数据表对汇编代码进行预处理;匹配模块302,用于逐行遍历预处理后的汇编代码,利用正则表达式匹配每行汇编代码的首单词,匹配成功则认为该行汇编代码是标号,否则认为该行汇编代码是指令;若该行汇编代码是指令,则该行汇编代码的首单词为当前指令的操作符,通过当前指令的操作符和指令集数据表得出当前指令的类型,标记预处理后的汇编代码中的转移指令,并通过指令集数据表得出非转移指令的寄存器读写模式;获取模块303,用于依据所述寄存器读写模式,获取当前指令的寄存器使用情况;删除模块304,用于根据当前指令的寄存器使用情况,根据冗余指令检测规则判断当前指令是否为冗余指令,若当前指令为冗余指令,则对冗余指令进行删除。所述获取模块303还包括:划分模块,用于以汇编代码中的标号和转移指令为间隔,将汇编代码划分为若干基本块,利用转移指令得出各基本块间的跳转关系,从而获得汇编代码的控制流图及所有运行分支。以上所示仅是本发明的优选实施方式,应当指出,对于本
技术领域
的普通技术人员来说,在不脱离本发明原理的前提下,还可以做出若干改进和润饰,这些改进和润饰也应视为本发明的保护范围。当前第1页12
当前第1页1 2 
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1