PHP安全编程:阻止文件名被操纵

文件名与目录的操纵攻击
服务器君一共花费了752.951 ms进行了5次数据库查询,努力地为您提供了这个页面。
试试阅读模式?希望听取您的建议

在很多情形下会使用动态包含,此时目录名或文件名中的部分会保存在一个变量中。例如,你可以缓存你的部分动态页来降低你的数据库服务器的负担。

<?php

include "/cache/{$_GET['username']}.html";

?>

为了让这个漏洞更明显,示例中使用了$_GET。如果你使用了受污染数据时,这个漏洞同样存在。使用$_GET['username']是一个极端的例子,通过它可以把问题看得更清楚。

虽然上面的流程有其优点,但它同时为攻击者提供了一个可以自由选择缓存页的良机。例如,一个用户可以方便地通过编辑URL中的username的值来察看其他用户的缓存文件。事实上,攻击者可以通过简单的更改username的值为相应的文件名(不加扩展名)来察看/cache目录下的所有扩展名为.html的文件。

http://example.org/index.php?username=filename

尽管该程序限制了攻击者所操作的目录和文件名,但变更文件名并不是唯一的手段。攻击者可以创造性地达到在文件系统中进行跨越的目的,而去察看其他目录中的.html文件以发现敏感信息。这是因为可以在字串使用父目录的方式进行目录跨越:

http://example.org/index.php?username=../admin/users

上面URL的运行结果如下:

<?php

include "/cache/../admin/users.html";

?>

此时,..意味着/cache的父目录,也就是根目录。这样上面的例子就等价于:

<?php

include "/admin/users.html";

?>

由于所有的文件都会在文件系统的根目录下,该流程就允许了一个攻击者能访问你服务器上所有的.html文件。

在某些平台上,攻击者还可以使用一个NULL来终止字符串,例如:http://example.org/index.php?username=../etc/passwd%00

这样就成功地绕开了.html文件扩展名的限制。当然,一味地去通过猜测攻击者的所有恶意攻击手段是不可能的,无论你在文件上加上多少控制,也不能排除风险。重要的是在动态包含时永远不要使用被污染数据。攻击手段不是一成不变的,但漏洞不会变化。只要通过过滤数据即可修复这个漏洞。

<?php

$clean = array();

/* $_GET['filename'] is filtered and stored in $clean['filename']. */

include "/path/to/{$clean['filename']}";

?>

如果你确认参数中只有文件名部分而没有路径信息时,另一个有效的技巧是通过使用basename()来进行数据的过滤:

<?php

$clean = array();

if (basename($_GET['filename'] == $_GET['filename'])
{
	$clean['filename'] = $_GET['filename'];
}

include "/path/to/{$clean['filename']}";

?>

如果你允许有路径信息但想要在检测前把它化简,你可以使用realpath()函数:

<?php

$filename = realpath("/path/to/{$_GET['filename']}");

?>

通过上面程序处理得到的结果($filename)可以被用来确认是否位于/path/to目录下:

<?php

$pathinfo = pathinfo($filename);

if ($pathinfo['dirname'] == '/path/to')
{
	/* $filename is within /path/to */.
}

?>

如果检测不通过,你就应该把这个请求记录到攻击日志以备后查。这个在你把这个流程作为深度防范措施时特别重要,因为你要确定其它的安全手段失效的原因。

延伸阅读

此文章所在专题列表如下:

  1. PHP安全编程:register_globals的安全性
  2. PHP安全编程:不要让不相关的人看到报错信息
  3. PHP安全编程:网站安全设计的一些原则
  4. PHP安全编程:可用性与数据跟踪
  5. PHP安全编程:过滤用户输入
  6. PHP安全编程:对输出要进行转义
  7. PHP安全编程:表单与数据安全
  8. PHP安全编程:从URL的语义进行攻击
  9. PHP安全编程:文件上传攻击的防御
  10. PHP安全编程:跨站脚本攻击的防御
  11. PHP安全编程:跨站请求伪造CSRF的防御
  12. PHP安全编程:关于表单欺骗提交
  13. PHP安全编程:HTTP请求欺骗
  14. PHP安全编程:不要暴露数据库访问权限
  15. PHP安全编程:防止SQL注入
  16. PHP安全编程:cookie暴露导致session被劫持
  17. PHP安全编程:session固定获取合法会话
  18. PHP安全编程:session劫持的防御
  19. PHP安全编程:防止源代码的暴露
  20. PHP安全编程:留心后门URL
  21. PHP安全编程:阻止文件名被操纵
  22. PHP安全编程:文件包含的代码注入攻击
  23. PHP安全编程:文件目录猜测漏洞
  24. PHP安全编程:打开远程文件的风险
  25. PHP安全编程:shell命令注入
  26. PHP安全编程:暴力破解攻击
  27. PHP安全编程:密码嗅探与重播攻击
  28. PHP安全编程:记住登录状态的安全做法
  29. PHP安全编程:共享主机的源码安全
  30. PHP安全编程:更优的会话数据安全
  31. PHP安全编程:会话数据注入
  32. PHP安全编程:主机文件目录浏览
  33. PHP安全编程:PHP的安全模式

本文地址:http://www.nowamagic.net/librarys/veda/detail/2047,欢迎访问原出处。

不打个分吗?

转载随意,但请带上本文地址:

http://www.nowamagic.net/librarys/veda/detail/2047

如果你认为这篇文章值得更多人阅读,欢迎使用下面的分享功能。
小提示:您可以按快捷键 Ctrl + D,或点此 加入收藏

大家都在看

阅读一百本计算机著作吧,少年

很多人觉得自己技术进步很慢,学习效率低,我觉得一个重要原因是看的书少了。多少是多呢?起码得看3、4、5、6米吧。给个具体的数量,那就100本书吧。很多人知识结构不好而且不系统,因为在特定领域有一个足够量的知识量+足够良好的知识结构,系统化以后就足以应对大量未曾遇到过的问题。

奉劝自学者:构建特定领域的知识结构体系的路径中再也没有比学习该专业的专业课程更好的了。如果我的知识结构体系足以囊括面试官的大部分甚至吞并他的知识结构体系的话,读到他言语中的一个词我们就已经知道他要表达什么,我们可以让他坐“上位”毕竟他是面试官,但是在知识结构体系以及心理上我们就居高临下。

所以,阅读一百本计算机著作吧,少年!

《代码大全(第2版)》 史蒂夫•迈克康奈尔 (Steve McConnell) (作者), 金戈 (译者)

代码大全(第2版)是著名IT畅销书作者、《IEEE Software》杂志前主编、具有20年编程与项目管理经验的Steve McConnell十余年前的经典著作的全新演绎:第2版做了全面的更新,增加了很多与时俱进的内容,包括对新语言、新的开发过程与方法论的讨论等等。这是一本百科全书式的软件构建手册,涵盖了软件构建活动的方方面面,尤其强调提高软件质量的种种实践方法。

更多计算机宝库...