目录
文件包含:开发人员将相同函数写入单独文件中,需要使用某个时直接调用此文件,无需再次编写,这种文件调用的过程称文件包含
文件包含漏洞:在引入文件时,包含的文件名用户可控,并且传入的文件名没有经过合理的校验,或者校验被绕过。
类似于命令执行,函数调用的手法 没有错,错的是被黑客利用
php中常见的包含文件函数
- include():当使用该函数包含文件时,只有代码执行到include()函数时才将文件包含进来,发生错误时给出一个警告,继续向下执行
- include_once():功能与include() 相同,区别在于当重复调用同一文件时,程序只调用一次
- require():与include()的区别在于,require()执行如果发生错误,函数会输出错误信息,并停止运行脚本
- require_once():功能与require() 相同,区别在于当重复调用同一文件时,程序只调用一次
函数例子:
include() 找不到包含文件时,只会出现waring警告,而且还会继续执行include 下面的代码
而当require() 在包含不到文件时,就会发出错误信息,并停止运行脚本
include_once() require_once()
跟上边一样,,就是如果文件已被包含,就不会再次包含
实验前,打开相关配置文件
本地文件包含
<?php
if(isset($_GET['page'])) {
include $_GET['page'];
}else{
include 'home.php';
}
?>
访问上边这个脚本,,可以构造 url
?page=xxx.php
get到page的值,,不为空,,就会include包含该文件
但是若该文件不存在,,通常会出现以下警告,,从而爆出绝对路径
包含同目录的文件,虽然这里是 1.txt ,但是文件包含会优先执行代码,不看后缀,若不是代码,则输出其文件内容
还可以访问系统本地的敏感文件
一些常见路径
windows
c:/boot.ini //查看系统版本
c:/windows/php.ini //php配置信息
c:/windows/my.ini //MYSQL配置文件,记录管理员登陆过的MYSQL用户名和密码
linux
/etc/httpd/conf/httpd.conf // apache配置文件
/usr/local/app/php5/lib/php.ini //PHP相关设置
/etc/sysconfig/iptables 查看防火墙策略
除了跟绝对路径,还能通过相对路径读取
当有限制时(被包含的文件只能为 .html 文件)
$filename=$_GET['filename']
include ($filename.'.html')
可用长度截断来绕过,windows文件名最长256 , linux最长 4096
这时候用长度截断
? filename=1.txt/././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././.
远程文件包含
远程文件包含就是允许攻击者包含一个远程文件,一般是在远程服务器上预先设置好的脚本,可导致不同程度的信息泄露、拒绝服务、甚至在目标服务器执行代码
先在一个靶机服务器网站根目录写一个要被包含的文件
然后在有包含漏洞的服务器(实验是在本机)使用http:// 伪协议去远程包含
页面无回显,但是,代码已经执行
此时,去用蚁剑连接
连接成功,一句话木马写入成功
文件包含漏洞防御
设置白名单
代码在进行文件包含时,如果文件名可以确定,可以设置白名单对传入的参数进行比较。
过滤危险字符
由于Include/Require可以对PHP Wrapper形式的地址进行包含执行(需要配置php.ini),在Linux环境中可以通过”../../”的形式进行目录绕过,所以需要判断文件名称是否为合法的PHP文件。
设置文件目录
PHP配置文件中有open_basedir选项可以设置用户需要执行的文件目录,如果设置目录的话,PHP仅仅在该目录内搜索文件。
关闭危险配置
PHP配置中的allow_url_include选项如果打开,PHP会通过Include/Require进行远程文件包含,由于远程文件的不可信任性及不确定性,在开发中禁止打开此选项,PHP默认是关闭的。