反病毒误报问题机理蓝皮书
来源:赛迪网 更新时间:2007-08-12

 作者:江海客/安天实验室  

     一、误报的成因分析

  首先需要澄清三个概念,即漏报、错报和误报。

  漏报:反病毒产品检测一个可确认是病毒的检测对象而没有报警。

  错报:反病毒产品检测一个可确认是某种病毒的检测对象,报警为另一种病毒。

  误报:反病毒产品检测一个可确认不是病毒的检测对象报警为病毒。

  一些用户将错报视为一种误报,实际上这是两个完全不同的概念,率先澄清这个概念有助于专心与我们今天的主题。

  反病毒作为信息安全领域一门严谨的工程技术,是以保证信息系统应用为前提的,由于误报会导致用户的心理恐慌,对被误杀产品不好的舆论影响,以及直接导致误杀,从而导致信息系统出现某种不可预期的后果,因此误报问题相对漏报和错报往往更加敏感。在某个非官方技术标准中,对反病毒的误报率作出了规定,即不能超过万分之零点五,即对十万个不同的检测对象,允许有五个误报,但对此无论是公众还是反病毒工作者自己依然觉得不可接受,而希望达到零误报的境界。

这也反映了工程化应用和学术化研究的不同视角,我们也经常看到从事反病毒理论方面的年轻研究者们经常兴奋不已,“看,只要建立这样一个简单的神经网络(如BP网络),并把若干样本和正常文件进行学习,再检测此前未经神经网络学习过的样本集合时,就会获得80%以上未知病毒检出率”。这种方法无论如何先进,只要误报了任何一个windows的系统文件或者program下面的正常程序文件,就都不能不加改动的应用到实际系统中。

  这就是为什么,在实际的反病毒产品中,如果有超过10%的未知病毒检出率,就可以视为很不错的结果,而反病毒的一些paper中则往往会出现令人鼓舞的比率。这是因为极低的误报率是商用反病毒技术的基础。过去关于未知检测就有这样的一个玩笑,100%检测未知病毒?很简单,只要对每个检测对象都报病毒就可以了,也就是说只有100%的误报率,才能造就100%的检出率。

  当然我们依然需要学术上对新的病毒检测理论方法的不懈探索,所谓大胆想象,小心求证。


连载:反病毒误报问题机理蓝皮书(一)

图 误报问题全图

二、误报的类型

  看待误报,可以有很多种角度,从技术角度,误报可能是一个bug,而从另外一些角度来看,误报则是一种争议,这种争议比较主要的在于什么是病毒或恶意代码这样的一个标准的不同认识。

  对某一个程序,在发生误报的争议后,反病毒厂商分析确认依然认为是病毒的情况。这种情况通常不是技术的问题,而是判定病毒或更广泛的恶意代码的标准。在现实生活中,其实这种情况要比从技术上的误报更普遍。

  比较常见的标准差异是广告件厂商与反病毒厂商经常发生的冲突和诉讼,由于装机量和广告件厂商的收入息息相关,因此广告件厂商往往采用一些比较极端的推广自己的方式、也包括页面注入和通过其他的广告件分发、甚至通过蠕虫或者僵尸网络分发。反病毒软件无疑成为了这种经济模式的天敌,一旦遭打反病毒软件的查杀,则它们的装机量就会骤然下降。因此,反病毒厂商最常见的误报投诉,往往来自这些厂商,伴随着误报投诉的则可能还包括律师函、直至法院的传票。

  一些广告件厂商,惯常的作法是开始极端推广,达到满意的装机量后,为了逃避查杀,则马上去掉所有不规范之处,再找公正机构公证自己没有危害,然后向反病毒厂商交涉。在他们眼中,既然反病毒厂商并不是执法机构,自然也没有道理去清算“原罪”。

  还有一种标准差异的情况在于对一些与安全攻防相关工具的定性,比如一些后门程序的作者,都坚称自己开发的不是后门或木马,而是网络远程管理工具。但对反病毒企业的基本技术标准来看,远程控制管理工具和后门的根本区别是前者对被控端至少是可见(如有托盘图标)的,并且是需要有安装确认过程的。

  此外,在部分安全工作者中还有这样的一种认识,即反病毒软件应该查杀对所运行主机有害的东西,而无须考虑运行结果是否危害其他主机。比较突出的观点就是在BO后门开始流行后,一些人认为反病毒厂商不应该查用于控制受害主机的Client端。

  被迫的误报:对反病毒工程师角度来说,还会有一些不得不添加规则去查杀一些并非病毒的东西,这往往是对市场压力的屈从。网上经常会流传一些垃圾样本集合,如所谓101种经典病毒、3000种经典病毒之类,但这其中不但所有的程序都没有主流操作系统的活性,而且有些根本就不是病毒,但往往很多普通用户则认为谁的检测率高,那种软件就好,因此反病毒工程师则在市场部门的压力下,违心的添加了这些垃圾规则。

  上述的情况虽然也可能被认为误报,但从反病毒厂商的技术流程角度,不能称为误报,因为反病毒软件报警了他们主观想要报警的东西,这个过程没有技术上的问题。

 我们需要分析的误报,则是一个检测对象被反病毒软件报警了,但经过反病毒厂商自身确认后,认定不是病毒的检测对象。

  通常来说可能带来误报的环节有四个:样本分析与判定环节、特征提取环节、引擎工作机理环节、未知判定环节。

  如果说的更明确一些,让我们来看一下误报构成的通路。

  情况一:样本判定环节厂商把一个入库的非病毒样本误判定为病毒,导致这个文件被误查。

  情况二:厂商把一个入库的非病毒样本误判定为病毒,导致这个文件以及这个文件同源的文件被误查。

  情况三:厂商在一个入库的病毒样本上提取病毒特征,但这个特征可能在其他正常程序上能够匹配到。

  情况四:厂商的未知病毒检测机制(如行为加权)判定一个可执行程序风险超过阈值,从而告警,而实际上这是一个正常程序。

  当然还有一种极端的情况,即构造者根据厂商的病毒特征构造出一个能被报警的无毒文件。


连载:反病毒误报问题机理蓝皮书(二)

图:误报的类型

 三、样本分析与判定环节

  在样本分析与判定环节,哪些会造成误报呢?

  1、被病毒和攻击者利用的第三方软件

  在没有BO这类远程控制工具之前,攻击者就已经学会了采用一些商用第三方软件作为后门使用,他们可能会对这些软件稍加改造。这种趋势比较明显的是自DIY蠕虫开始的,由于网络上的工具越来越普遍,一些病毒作者发现,其实并不需要编写代码,把一些工具组合起来,再用批处理或者脚本调度一下,就可以写成一个“DIY病毒”,DIY蠕虫可能包括扫描部分、投放部分、升级部分、后门部门、跳板部分等等,这些都可以在网上找到现成的工具。而其中利用的一些工具,很多也并非是专门的黑客工具,有很多本来是免费甚至是商用的正常软件。我们可以通过表一来看一看经常被病毒使用的。


  表一:病毒经常使用的第三方工具


反病毒误报问题机理技术蓝皮书(三)

  对上述软件来说,反病毒的处理要高度慎重,除对行命令工具,反病毒软件基本都会选择报警外,对其他几类,由于很难分辨相关程序,是用户的正常使用,还是病毒“种植”的结果,如果将这些代码加入到病毒库,很可能造成用户信息系统的异常。

2、公共控件和驱动

  广泛被使用的一些公共控件,为软件开发者提供了方便,但它也为病毒的作者提供了方便,他们也可以使用公共控件来实现自身的功能。毫无疑问,如果把公共控件当成病毒衍生物并提取特征,就会导致公共控件和其他使用该控件的正常程序被报警。

  例子:在win9x的时代,木马通过EXEBIND的方式,搭载一个winsock.ocx是比较常用的做法,由于winsock.ocx在病毒执行后同样被作为衍生物释放,因此很容易被当成病毒文件。这是一个我们自己曾经犯过的错误,而且这个错误险些重复过。彻底避免了这个问题的关键是,搜集齐了所有版本的winsock.ocx,放入了白名单。另外可以一题的是,其他一些正常应用程序虽然也使用winsock.ocx,但他们都是通过安装包把自己和winsock.ocx安装到系统中,而不会通过exebind的方式,因此我们当时采用过如果一个程序检测不到病毒,但发现exebind了winsock.ocx的情况下,就报警未知木马的方法,还是有不错的效果。

 3、开源软件

  开源软件比公共控件更利于应用,因此同样会导致误报的产生。开源软件的代码如果用来编写后门,就会导致开源软件本身被误报。

  例子:VNC是非常有名气的开源远程管理控制工具,其行为是非常规范的,运行后在右下角有托盘图标,用户可以设定密码验证,也可以正常关闭。但一些病毒作者,对VNC代码进行修改,使其不再被用户可见,这样就成为了一个后门。但对这个后门的特征提取,很难规避不报警正常的VNC程序。

 4、被修改的文件

  一些病毒希望通过修改某些系统文件或者其他程序文件达到自己的目的。如果反病毒软件不能识别这些文件的话,会导致病毒造成的隐患依然存在,但在这些文件体上提取特征,则也很容易导致原来未被修改的正常文件被误报。

  例子:著名的蠕虫HAPPY99会将系统正常wsock32.dll改名为 wsock32.ska,并生成一个与wsock32.dll文件大小一样的文件,新的文件修改了函数调用,从而达到调用病毒自身的另外一个链接库,获取用户发送邮件的收件人地址,然后发送一封把自身作为附件、被捕获得邮件地址为收件人的病毒邮件的作用。

  而如果在新的wsock32.dll上提取的特征位置不当的话,就会导致正常的wsock32.dll被误报,而一些厂商采用了取巧的方法,当他们发现Happy99的病毒体后,就在系统目录下寻找wsock32.ska,并覆盖回wsock32.dll。

 四、特征提取环节

  另外一些误报,不是对样本的认定过程出现了问题,而是在正确的病毒样本上所提取的特征会在正常程序上被匹配到。

  哪些环节引发特征提取导致的误报呢?最典型的是下面几种:

  1、感染

  对感染病毒特征的提取,取决于对病毒体位置的准确判定,病毒分析工程师必须能有效找到病毒代码和宿主程序之间的边界,否则如果误把特征提取到正常程序上,不但不能有效查杀病毒,反而导致了误报。这种事件并不常见,但确实发生过。

  2、壳

  如果一种壳,反病毒软件没有脱掉的能力,那么用这个壳处理过的有害程序,特征通常会提取在静态文件上,而如果特征的位置,正好在壳的代码,则有可能导致反病毒软件会误报所有的用这种壳压缩过的可执行程序。

 3、自解压文件

  广义自解压文件,不仅包括类似WINZIP、winrar生成的能够自动运行、自我解压的程序,也包括很多安装包制作工具制作的安装文件。自解压的机理也会被病毒作者利用,在很多木马作者构造社交工程的过程中,他们认为安装包制作工具比类似EXEBIND的机制更为好用,也更有欺骗性。因此他们用自解压包制作工具把正常程序和他们的木马打包放在一起,让用户误认为是在安装正常程序,但实际上木马被执行了。

  自解压文件误报是自大量DIY蠕虫开始的,在病毒作者拼凑完成一个DIY蠕虫后,如何让这些散兵游勇成为一个文件呢?他们想到了利用WINZIP之类的工具作个自解压包,并设定其中的某个程序被解压后自动执行。

  自解压导致的误报的原因与壳误报的原因很类似,就是特征被提取到了自解压的代码上,这样所有用该种工具制作的包裹可能都会被误报。

  但细致来看,自解压误报还分很多种情况,一种情况是病毒分析工程师没有识别出这是一个自解压包,而可能把这种包括当作某种EXE结合器来看待。还有一种情况是,虽然识别出了自解压包裹,但必须能够保证,反病毒软件需要能够识别,并删掉这个自解压包裹,比如DIY蠕虫,前者是判定上的错误,而后者是特征提取经验的不足。

  需要说明的是,由于反病毒软件通常对于自解压包的检测,与包裹文件检测是相类似的,即都需要解开察看内部的文件,因此反病毒软件和后段处置体系,是有常见自解压包裹的类型识别和处理能力的,因此对所能识别的自解压程序产生误报的原因,往往是因为病毒作者对DIY蠕虫或者木马的自解压包进行了2次修改,如通过PE_Patch修改了入口,导致分拣机制无法判定这是一个自解压样本,这样分拣机制就会把非包裹的属性送给反病毒工程师,反病毒工程师此时就有可能直接在代码段上提取特征了。

三、样本分析与判定环节

  在样本分析与判定环节,哪些会造成误报呢?

  1、被病毒和攻击者利用的第三方软件

  在没有BO这类远程控制工具之前,攻击者就已经学会了采用一些商用第三方软件作为后门使用,他们可能会对这些软件稍加改造。这种趋势比较明显的是自DIY蠕虫开始的,由于网络上的工具越来越普遍,一些病毒作者发现,其实并不需要编写代码,把一些工具组合起来,再用批处理或者脚本调度一下,就可以写成一个“DIY病毒”,DIY蠕虫可能包括扫描部分、投放部分、升级部分、后门部门、跳板部分等等,这些都可以在网上找到现成的工具。而其中利用的一些工具,很多也并非是专门的黑客工具,有很多本来是免费甚至是商用的正常软件。我们可以通过表一来看一看经常被病毒使用的。


  表一:病毒经常使用的第三方工具


反病毒误报问题机理技术蓝皮书(三)

  对上述软件来说,反病毒的处理要高度慎重,除对行命令工具,反病毒软件基本都会选择报警外,对其他几类,由于很难分辨相关程序,是用户的正常使用,还是病毒“种植”的结果,如果将这些代码加入到病毒库,很可能造成用户信息系统的异常。

4、编译器

  对于不加壳的样本,通常的病毒特征提取,为了保证质量,通常都会提取在代码段上,这就带来了一个隐含的问题,即编译器误报。不同的编译器生成的目标代码,会有不同的特性。有的编译器编译不同的程序,在入口处就会表现出明显不同的特性,但有的编译器则在入口之后,有一个相对长的相似部分。

  如果提取在这个相似部分上,可能会导致反病毒软件误报。通常对于主流编译器,反病毒厂商都会有一个基本的提取原则或者禁忌。但还有一些覆盖率不高、用户较少的边缘开发工具,反病毒厂商对此搜集的则未必齐全。

  在编译器这里需要说明的是,有时误报源于壳与编译器的组合,如果一种壳不能脱掉的话,对于壳的特征提取往往会有一些经验方法,但那些编译结果代码相似段较长的编译器编译出来的不同程序,用壳压缩过之后,可能还会出现大量的相似部分。如果提取在这个位置上依然会产生误报。

五、引擎机理环节

  有时特征提取本身并没有问题,但由于引擎的机理问题,也会导致误报。

  哈希碰撞:很多反病毒软件的特征库中并不存储特征码,而是用特征码的某种数学描述,比如CRC、MD5等等,这种方法的好处是显而易见的,首先他把病毒库变长的数据结构,变成一种等长结构,有利于优化和减少空间占用,同时也降低了病毒特征被抄袭的风险。但显然一个CRC32值的内容涵盖力,不如一个128字节的特征码。如果正好有一段其他的代码与病毒特征的CRC32值相同,则会导致误报。

  格式识别与预处理:早期病毒误报的重要原因,是反病毒引擎的格式识别与预处理机制,不够完备,比如一个病毒只感染DOS MZ可执行程序,那么对该病毒特征的匹配应该只针对同类型的文件进行。如果用来匹配一些图片、音乐文件,很难保证其中不会有特征碰撞,早期令人惊诧的“JPG病毒、BMP病毒”实际上并不是今天大家比较了解的格式化溢出,而是反病毒软件的误报。

  脚本:脚本带来的误报是屡见不鲜的,因为脚本不象2进制机制有严谨的结构。因此病毒脚本和正常脚本和网页之间的往往不容易划清边界。大家比较典型的就是看到一些关于批处理命令和注册表编辑的教程经常被反病毒软件误报。


连载:反病毒误报问题机理蓝皮书(五)

图:格式分支引擎

 六、未知检测环节

  未知检测机理的误报与前面的环节都是不同的,前面的环节是由一个从样本出发、到特征提取、到病毒库升级的链条过程产生的,而未知检测则完全是依靠反病毒软件自带的经验模型在客户端智能判定程序的有害性。

  未知检测的机理,很多文章都判定过,就是加权判定法,通过程序的行为或者一些静态特性设置标志,每个标志有不同的权值,通过根据程序标志取值的累加,就可以形成程序的风险值,如果超过了阈值,就会报警。这个机理说起来简单,但操作起来则是一个复杂的体系。其中重要原因之一就是因为未知病毒检测机制的误报指标与已知病毒检测技术的误报指标是完全相同的,而未知检测由于没有样本确认和提取过程,从而变得十分尴尬。

  例子:某硬盘保护程序曾被我们的VCS抓毒精灵机制误报,误报的原因很简单,就是他确实和太多的病毒行为标志重合了。确实这些系统底层的保护程序,往往难以回避一些与病毒相近的特性。