文件包含
PHP常用的文件包含函数有四种,区别如下:
1 2 3 4
| require():找不到被包含的文件会产生致命错误,并停止脚本运行 include():找不到被包含的文件只会产生警告,脚本继续执行 require_once()与require()类似:唯一的区别是如果该文件的代码已经被包含,则不会再次包含 include_once()与include()类似:唯一的区别是如果该文件的代码已经被包含,则不会再次包含
|
以这四个函数包含文件时,不论文件什么类型都会直接作为php文件解析。
分类
能够打开并包含本地文件的漏洞,我们称为本地文件包含漏洞(LFI)
(1)使用绝对路径
(2)使用相对路径进行读取
(3)一些常见的敏感目录信息路径
Windows系统:
1 2 3 4 5 6
| C:\boot.ini //查看系统版本 C:\windows\system32\inetsrv\MetaBase.xml //IIS配置文件 C:\windows\repair\sam //存储Windows系统初次安装的密码 C:\ProgramFiles\mysql\my.ini //Mysql配置 C:\ProgramFiles\mysql\data\mysql\user.MYD //MySQL root密码 C:\windows\php.ini //php配置信息
|
Linux/Unix系统:
1 2 3 4 5 6 7 8
| /etc/password //账户信息 /etc/shadow //账户密码信息 /usr/local/app/apache2/conf/httpd.conf //Apache2默认配置文件 /usr/local/app/apache2/conf/extra/httpd-vhost.conf //虚拟网站配置 /usr/local/app/php5/lib/php.ini //PHP相关配置 /etc/httpd/conf/httpd.conf //Apache配置文件 /etc/my.conf //mysql配置文件
|
需要再php.ini中配置
1 2
| allow_url_fopen = On //一直默认 allow_url_include = On //php5.2之后默认
|
包含方式
1.file://协议
2.php://协议
1 2 3 4 5 6 7 8
| php://filter用于读取源码并进行base64编码输出 eg: ?file=php://filter/read=convert.base64-encode/resource=flag.php 如果不写可选参数2(read或write),那么网页会自动匹配一个合适的read或write 3是过滤器。主要有四种:字符串过滤器,转换过滤器,压缩过滤器,加密过滤器。filter里可以用一或多个过滤器(中间用|隔开) php://input用于执行php代码。 php代码写在POST
phar://路径 //php版本>=5.3.0
|
字符串过滤器
string.rot13
(对字符串执行ROT13
编码转换)
string.toupper
(将字符串转化为大写)
string.tolower
(将字符串转化为小写)
string.strip_tags
(自 PHP 7.3.0 起废弃,从字符串中去除 HTML 和 PHP 标记)
转换过滤器
注:转换过滤器是 PHP 5.0.0 添加的
convert.base64-encode
和 convert.base64-decode
(将字符串进行base64编码加解密)
3.ZIP://协议
和phar相似,但是只能加绝对路径,并将#编码成%23,之后填压缩包里的文件
4.data://协议
1 2
| eg: ?file=data:text/plain,<?php system();?> ?file=data:text/plain;base64,xxxxxx //xxxxxx的base解码为php代码
|
包含session
//session文件路径已知,且其中内容部分可控
1、包含日志
2、SSH log
//在user-agent中插入php代码,代码会写入environ中,之后再包含
//在temp目录下,在临时文件被删除前竞争时间包含
绕过方式
一、本地文件包含绕过
//存在PHP小于5.3.4版本,并且关闭PHP魔术引导。
//在Windows中目录长度不可以超过256字节,linux中目录长度不可以超过4096字节。超过的部分会被丢弃。
二、远程文件包含绕过
空字符绕过
超长字符绕过(远程文件包含好像只能使用”./“)
?绕过(query)
#绕过(用#的编码%23)
空格绕过(用空格的编码%20)