PHP代码审计-伪协议
PHP代码审计-伪协议
什么是php伪协议
在 PHP 中,”伪协议”是一种特殊的语法,用于访问不同的资源或执行特定的操作。这些伪协议以 php:// 开头,后面跟着特定的指示符或参数,以实现不同的功能。这些伪协议提供了一种方便的方式来处理各种输入输出操作,而不必依赖于实际的文件或网络资源。
简单的理解就是,在URL中使用特殊的协议前缀来指示PHP执行特定的代码。
php.ini参数设置
在php.ini里有两个重要的参数allow_url_fopen、allow_url_include。
- allow_url_fopen:默认值是ON。允许url里的封装协议访问文件;
- allow_url_include:默认值是OFF。不允许包含url里的封装协议包含文件;
有哪些伪协议
1 | file:// — 访问本地文件系统 |
应用场景
文件包含
(关于文件包含的函数)
1 | include()、require()、include_once()、require_once()、highlight_file() |
伪协议详解
data://
数据流封装器,以传递相应格式的数据。可以让用户来控制输入流,当它与包含函数结合时,用户输入的data://流会被当作php文件执行。
allow_url_fopen和allow_url_include都需要开启。
example:
1 | 1、data://text/plain, |
file://
用于访问本地文件系统,并且不受allow_url_fopen,allow_url_include影响
file://协议主要用于访问文件(绝对路径、相对路径以及网络路径)
比如:www.xx.com?file=file:///etc/passwd
php://
不需要开启allow_url_fopen,仅php://input、php://stdin、php://memory和php://temp需要开启allow_url_include。
php://filter
一个中间件,在读入或写入数据的时候对数据进行处理后输出的过程。可以获取指定文件源码。当它与包含函数结合时,php://filter流会被当作php文件执行。所以我们一般对其进行base64编码,让其不执行,展现在页面上。从而导致任意文件读取。
ctf解题常用:变量=php://filter/read=convert.base64-encode/resource=文件名
使用的convert.base64-encode,是一种过滤器。

php://input
可以访问请求的原始数据的只读流, 将post请求中的数据作为PHP代码执行。在POST请求中访问POST的data部分,在enctype="multipart/form-data"的时候php://input 是无效的。
当传进去的参数作为文件名变量去打开文件时,可以将参数php://input,同时post方式传进去值作为文件内容,供php代码执行时当做文件内容读取。

其他
php://stdin、php://stdout 和 php://stderr 允许直接访问 PHP 进程相应的输入或者输出流。 数据流引用了复制的文件描述符,所以如果你打开 php://stdin 并在之后关了它, 仅是关闭了复制品,真正被引用的 STDIN 并不受影响。
注意 PHP 在这方面的行为有很多 BUG 直到 PHP 5.2.1。 推荐简单使用常量 STDIN、 STDOUT 和 STDERR 来代替手工打开这些封装器。
php://stdin 是只读的, php://stdout 和 php://stderr 是只写的。
zip://
可以访问压缩包里面的文件。当它与包含函数结合时,zip://流会被当作php文件执行。从而实现任意代码执行。相同类型的还有zlib://和bzip2://。
可以配合文件上传获取webshell,将shell.txt压缩成zip,再将后缀名改为jpg上传,通过zip伪协议访问压缩包里的文件,来连接木马
1 | ?url=zip://shell.jpg |
注意:此处只能传入绝对路径,要用#分隔压缩包和压缩包里的内容,并且#要用url编码%23。只要是zip的压缩包即可,后缀名可以任意更改。
phar://
与zip://类似,同样可以访问zip格式压缩包内容
1 | http://127.0.0.1/include.php?file=phar://E:/phpStudy/PHPTutorial/WWW/phpinfo.zip/phpinfo.txt |
http:// & https://
allow_url_fopen和allow_url_include都需要开启。
常规 URL 形式,允许通过 HTTP 1.0 的 GET方法,以只读访问文件或资源。CTF中通常用于远程包含。
1 | Copyhttp://127.0.0.1/include.php?file=http://127.0.0.1/phpinfo.txt |