从本质上讲,HTTP协议没有状态。它基于一种简单的请求—响应模型,其中每对消息代表一个独立的事务。协议本身并无将某位用户提出的各种请求联系起来的机制,并将它们与Web服务器收到的所有其他请求区分开来。在Web发展的早期阶段,并没有必要建立这种机制:因为Web站点公布的是任何人都可以查阅的静态HTML页面。但如今,情况已经发生了巨大变化。
绝大多数的Web“站点”实际为Web应用程序。它们允许用户注册与登录;帮助用户购买及销售产品。它们能够在用户下次访问时记住他的喜好。它们可根据用户的单击和输入,通过动态建立的内容提供丰富、多媒体形式的使用体验。为执行这些功能,应用程序就需要使用会话。
支持登录是会话在应用程序中最主要的用途。输入用户名和密码后,可以用输入的证书所属的用户身份使用应用程序,直到退出会话或由于会话处于非活动状态而终止。用户不希望在每个应用程序页面重复输入密码。因此,一旦用户通过验证,应用程序就会为他建立一个会话,把所有属于这个会话的请求当做该用户提出的请求处理。
不具备登录功能的应用程序通常也需要使用会话。许多出售商品的站点并不要求顾客建立账户。但是,它们允许用户浏览目录、往购物篮中添加商品、提供交货信息并进行支付。在这种情形下,就没有必要验证用户的身份:应用程序并不知道或关心绝大多数用户的身份。但是,为了与他们进行交易,应用程序需要知道它收到的哪些请求来自同一名用户。
执行会话最简单、最常见的方法就是向每名用户发布一个唯一的会话令牌或标识符。用户在随后向应用程序提出的每一个请求中提交这个令牌,帮助应用程序在当前请求与前面提出的请求之间建立关联。
在大多数情况下,应用程序使用HTTP cookie作为在服务器与客户端间传送这些会话令牌的传输机制。服务器对新客户端的第一个响应中包含以下HTTP消息头:
客户端随后提出的请求中包含如下消息头:
这种标准的会话管理机制非常容易受到各种类型的攻击。当攻击会话机制时,攻击者的主要目标是以某种方式劫持一名合法用户的会话,由此伪装成这名用户。如果该用户已经通过应用程序的验证,攻击者就可以访问属于这名用户的私有数据,或者以他的身份执行未授权操作。如果该用户未能通过验证,攻击者仍然能够查看用户在会话过程中提交的敏感信息。
和前面示例中运行ASP.NET的Microsoft IIS服务器一样,许多商业Web服务器和Web应用程序平台执行它们自己的基于HTTP cookie的非定制会话管理解决方案。Web应用程序开发者可使用它们提供的API将会话依赖功能与这种解决方案整合起来。
事实证明,一些非定制会话管理解决方案易于受到各种攻击,导致用户的会话被攻破(这一问题将在本章后面讨论)。此外,一些开发者发现,他们需要比内置解决方案所提供的控制更加全面的会话行为控制,或者希望避免基于cookie的解决方案中存在的一些固有漏洞。鉴于这些原因,安全性至关重要的应用程序(如电子银行)通常使用定制或并非基于cookie的会话管理机制。
会话管理机制中存在的漏洞主要分为两类:
会话令牌生成过程中的薄弱环节;
在整个生命周期过程中处理会话令牌的薄弱环节。
我们将分别分析这些弱点,描述在现实世界的会话管理机制中常见的各种漏洞,以及发现和利用这些漏洞的实用技巧。最后将描述应用程序为防止这些攻击所应采取的防御措施。