枚举尽可能多的应用程序内容只是解析过程的一个方面。分析应用程序的功能、行为及使用的技术,确定它暴露的关键受攻击面,并开始想出办法探查其中可供利用的漏洞,这项任务也同样重要。
值得研究的一些重要方面如下。
应用程序的核心功能:用于特定目的时可利用它执行的操作。
其他较为外围的应用程序行为,包括站外链接、错误消息、管理与日志功能、重定向使用等。
核心安全机制及其运作方式,特别是会话状态、访问控制以及验证机制与支持逻辑(用户注册、密码修改、账户恢复等)。
应用程序处理用户提交的输入的所有不同位置:每个URL、查询字符串参数、POST数据、cookie以及类似内容。
客户端使用的技术,包括表单、客户端脚本、厚客户端组件(Java applet、ActiveX控件和Flash)和cookie。
服务器端使用的技术,包括静态与动态页面、使用的请求参数类型、SSL使用、Web服务器软件、数据库交互、电子邮件系统和其他后端组件。
任何可收集到的、关于服务器端应用程序内部结构与功能的其他信息(客户端可见的功能和行为的后台传输机制)。
在检查枚举应用程序功能时生成的HTTP请求的过程中,可以确定应用程序获取用户输入(由服务器处理)的绝大部分位置。需要注意的关键位置包括以下几项。
每个URL字符串,包括查询字符串标记。
URL查询字符串中提交的每个参数。
POST请求主体中提交的每个参数。
每个cookie。
极少情况下可能包括由应用程序处理的其他所有HTTP消息头,特别是User-Agent、Referer、Accept、Accept-Language和Host消息头。
1.URL文件路径
通常,查询字符串之前的URL部分并不被视为是进入点,因为人们认为它们只是服务器文件系统上的目录和文件的名称。但是,在使用REST风格的URL的应用程序中,查询字符串之前的URL部分实际上可以作为数据参数,并且和进入点一样重要,因为用户输入就是查询字符串本身。
典型的REST风格的URL可以采用以下格式:
http://eis/shop/browse/electronics/iPhone3G/
在这个示例中,字符串electronics和iPhone3G应被视为存储搜索功能的参数。
同样,在下面这个URL中:
http://eis/updates/2010/12/25/my-new-iphone/
updates之后的每个URL组件都可以以REST方式进行处理。
根据URL结构和应用程序上下文,我们可以轻松确定使用REST风格的URL的应用程序。但是,在解析应用程序时,并不存在必须遵循的固有标准,因为用户与应用程序的交互方式通常由应用程序的开发者决定。
2.请求参数
多数情况下,在URL查询字符串、消息主体和HTTP cookie中提交的参数都是明显的用户输入进入点。但是,一些应用程序并不对这些参数使用标准的name=value格式,而是使用定制的方案。定制方案采用非标准查询字符串标记和字段分隔符,甚至可能在参数数据中嵌入其他数据方案(如XML)。
以下是笔者在现实世界中遇到的一些非标准参数格式实例:
/dir/file;foo=bar&foo2=bar2;
/dir/file/foo%3dbar%26foo2%3dbar2;
dir/foo.bar/file;
/dir/foo=bar/file;
/dir/file?param=foo:bar;
/dir/file?data=%3cfoo%3ebar%3c%2ffoo%3e%3cfoo2%3ebar2%3c%2ffoo2%3e。
如果应用程序使用非标准的查询字符串格式,那么在探查其中是否存在各种常见的漏洞时必须考虑到这种情况。例如,测试上面最后一个URL时,如果忽略定制格式,认为其仅包含一个名为data的参数,因而提交各种攻击有效载荷作为这个参数的值,对其进行简单处理,那么可能会遗漏处理查询字符串过程中存在的许多漏洞。相反,如果详细分析它使用的定制格式并将有效载荷提交到嵌入的XML数据字段中,立即就会发现严重缺陷,如SQL注入或路径遍历。
3.HTTP消息头
许多应用程序执行定制的日志功能,并可能会记录HTTP消息头(如Referer和User-Agent)的内容。应始终将这些消息头视为基于输入的攻击的可能进入点。
一些应用程序还对Referer消息头进行其他处理。例如,应用程序可能检测到用户已通过搜索引擎到达,并提供针对用户的搜索查询的定制响应。一些应用程序可能会回应搜索术语,或者尝试突出显示响应中的匹配表达式。一些应用程序则通过动态添加HTML关键字等内容,并包含搜索引擎中最近的访问者搜索的字符串,以提高它们在搜索引擎中的排名。这时,通过提出大量包含经过适当设计的Referer URL的请求,就可以不断在应用程序的响应中注入内容。
近年来出现了一个重要的趋势,即应用程序向通过不同设备(如笔记本电脑、移动电话、平板电脑)进行访问的用户呈现不同的内容。应用程序通过检查User-Agent消息头实现这一目的。除了能为直接在User-Agent消息头本身中实施的基于输入的攻击提供“便利”外,这种行为还可以揭示应用程序中的其他受攻击面。通过伪造流行移动设备的User-Agent消息头,攻击者可以访问其行为与主要界面不同的简化用户界面。由于这种界面通过服务器端应用程序中的不同代码路径生成,并且可能并未经过严格的安全测试,因此,攻击者就可以确定主要应用程序界面中并不存在的漏洞(如跨站点脚本)。
提示
Burp Intruder提供了一个内置的有效载荷列表,其中包含大量针对不同类型设备的用户代理字符串。攻击者可以执行一次简单的攻击,即向提供不同用户代理字符串的应用程序主页面提出一个GET请求,然后检查Burp Intruder返回的结果,从中确定表明使用了不同用户界面的反常现象。
除了针对浏览器默认发送或应用程序组件添加的HTTP请求消息头实施攻击外,有些时候,攻击者还可以通过添加应用程序可能会处理的其他消息头来实施成功的攻击。例如,许多应用程序会对客户的IP地址进行某种处理,以执行日志、访问控制或用户地理位置定位等功能。通常,应用程序通过平台API可以访问客户的网络连接IP地址。但是,如果应用程序位于负载均衡器或 代理服务器之后,应用程序可能会使用X-Forwarded-For请求消息头(如果存在)中指定的IP地址。然后,开发者可能误认为该IP地址是安全的,并以危险的方式处理该地址。在这种情况下,通过添加适当设计的X-Forwarded-For消息头,攻击者就可以实施SQL注入或持续的跨站点脚本等攻击。
4.带外通道
最后一类用户输入进入点是带外通道,应用程序通过它接收攻击者能够控制的数据。如果只是检查应用程序生成的HTTP流量,攻击者可能根本无法检测到其中一些进入点,发现它们往往需要全面了解应用程序所执行的各种功能。通过带外通道接收用户可控制的数据的Web应用程序包括:
处理并显示通过SMTP接收到的电子邮件消息的Web邮件应用程序;
具有通过HTTP从其他服务器获取内容功能的发布应用程序;
使用网络嗅探器收集数据并通过Web应用程序界面显示这些数据的入侵检测应用程序;
任何提供由非浏览器用户代理使用的API接口(如果通过此接口处理的数据与主Web应用程序共享)的应用程序,如移动电话应用程序。
通常,我们可以通过各种线索和指标确定服务器所采用的技术。
1.提取版本信息
许多Web服务器公开与Web服务器软件本身和所安装组件有关的详细版本信息。例如,HTTP Server消息头揭示大量与安装软件有关的信息:
除Server消息头外,下列位置也可能揭露有关软件类型和版本的信息:
建立HTML页面的模板;
定制的HTTP消息头;
URL查询字符串参数。
2.HTTP指纹识别
从理论上说,服务器返回的任何信息都可加以定制或进行有意伪造,Server消息头等内容也不例外。大多数应用程序服务器软件允许管理员配置在Server HTTP消息头中返回的旗标。尽管采取了这些防御措施,但通常而言,蓄意破坏的攻击者仍然可以利用Web服务器的其他行为确定其所使用的软件,或者至少缩小搜索范围。HTTP规范中包含许多可选或由执行者自行决定是否使用的内容。另外,许多Web服务器还以各种不同的方式违背或扩展该规范。因此,除通过Server消息头判断外,还可以使用大量迂回的方法来识别Web服务器。在图4-11中,Httprecon工具正对EIS应用程序进行扫描,并以不同的可信度报告各种可能的Web服务器。
3.文件扩展名
URL中使用的文件扩展名往往能够揭示应用程序执行相关功能所使用的平台或编程语言。例如:
asp——Microsoft Active Server Pages;
aspx——Microsoft ASP.NET;
jsp——Java Server Pages;
cfm——Cold Fusion;
php——PHP语言;
d2w——WebSphere;
pl——Perl语言;
py——Python语言;
dll——通常为编译型本地代码(C或C++);
nsf或ntf——Lotus Domino。
即使应用程序在它公布的内容中并不使用特定的文件扩展名,但我们一般还是能够确定服务器是否执行支持该扩展名的技术。例如,如果应用程序上安装有ASP.NET,请求一个不存在的.aspx文件将返回一个由ASP.NET框架生成的错误页面,如图4-12所示。但是,请求一个扩展名不同的不存在的文件将返回一个由Web服务器生成的常规错误消息,如图4-13所示。
图4-13 请求一个无法识别的文件扩展名时生成的常规错误消息
使用前面描述的自动化内容查找技巧,我们能够请求大量常见的文件扩展名,并迅速确定服务器是否执行了任何相关技术。
之所以出现上述不同的行为,是因为许多Web服务器将特殊的文件扩展名映射到特定的服务器端组件中。不同的组件处理错误的方式(包括请求不存在的内容)也各不相同。图4-14说明了默认安装IIS 5.0时将各种扩展名映射到不同处理程序DLL的情况。
图4-14 IIS5.0中的文件扩展名映射
分析请求文件扩展名时生成的各种错误消息可以确定该文件扩展名映射是否存在。在某些情况下,发现一个特殊的映射可能表示存在一个Web服务器漏洞。例如,过去,IIS中的.printer和.ida/.idq处理程序易于遭受缓冲区溢出攻击。
类似于下面的URL是另外一种值得注意的常用识别方法:
https://wahh-app/news/0,,2-421206,00.html
URL末尾用逗号分隔的数字通常由Vignette内容管理平台生成。
4.目录名称
一些子目录名称常常表示应用程序使用了相关技术。例如:
servlet ——Java servlet;
pls ——Oracle Application Server PL/SQL网关;
cfdocs或cfide —— Cold Fusion;
SilverStream —— SilverStream Web服务器;
WebObjects或{function}.woa—— Apple WebObjects;
rails—— Ruby on Rails。
5.会话令牌
许多Web服务器和Web应用程序平台默认生成的会话令牌名称也揭示其所使用技术的信息,例如:
JSESSIONID ——Java平台;
ASPSESSIONID ——Microsoft IIS服务器;
ASP.NET_SessionId —— Microsoft ASP.NET;
CFID/CFTOKEN ——Cold Fusion;
PHPSESSID —— PHP。
6.第三方代码组件
许多Web应用程序整合第三方代码组件执行常见的功能,如购物车、登录机制和公告牌。这些组件可能为开源代码,或者从外部软件开发者购买而来。如果是这样,那么相同的组件会出现在因特网上的大量其他Web应用程序中,可以根据这些组件了解应用程序的功能。通常,其他应用程序会利用相同组件的不同特性,确保攻击者能够确定目标应用程序的其他隐藏行为和功能。而且,软件中可能包含其他地方已经揭示的某些已知漏洞,攻击者也可以下载并安装该组件,对它的源代码进行分析或以受控的方式探查其中存在的缺陷。