header image

Null pointer dereference in win32k [OpenRCE import]

Totally forgot about this. Some time ago I’ve accidentally found an unhandled exception condition in kernel-mode GDI. Microsoft is aware of this but frankly they still didn’t fix it. Well, it may be not security issue, but who knows 😉

Offending function: win32k!NtUserGetDCEx or its user-mode wrapper, GetDCEx.
Crash condition: call it with all 0s before any desktops are created (I’m not 100% sure of this, but it seems to be the case).
Sample scenario: Create a DLL that calls GetDcEx(0,0,0) in DllMain. MessageBox works too (that’s how I first stumbled on it). Add the DLL to AppInit_DLLs registry key. Reboot. Upon next system start the DLL will be mapped into winlogon’s memory and the fatal function called before any windows are present. Boom, BSOD.

PROCESS_NAME:  winlogon.exe

 bf83c00f 8b4904          mov     ecx,dword ptr [ecx+4]

 EXCEPTION_RECORD:  ffffffff -- (.exr 0xffffffffffffffff)
 ExceptionAddress: bf83c00f (win32k!NtUserGetDCEx+0x00000029)
    ExceptionCode: c0000005 (Access violation)
   ExceptionFlags: 00000000
 NumberParameters: 2
    Parameter[0]: 00000000
    Parameter[1]: 00000004
 Attempt to read from address 00000004

 ERROR_CODE: (NTSTATUS) 0xc0000005 - The instruction at "0x%08lx" referenced memory at "0x%08lx". The memory could not be "%s".

 READ_ADDRESS:  00000004 



 LAST_CONTROL_TRANSFER:  from 8053ca28 to bf83c00f

 f88d9d50 8053ca28 00000000 00000000 00000003 win32k!NtUserGetDCEx+0x29
 f88d9d50 7c90eb94 00000000 00000000 00000003 nt!KiFastCallEntry+0xf8
 0006fb24 7e41e881 7e43a383 00000000 00000000 ntdll!KiFastSystemCallRet
 0006fddc 7e43a284 0006ff38 00000005 00000004 USER32!NtUserGetDCEx+0xc
 0006ff2c 7e4661d3 0006ff38 00000028 00000000 USER32!MessageBoxWorker+0x2ba
 0006ff84 7e4505f3 00000000 1000d9e8 1000b370 USER32!MessageBoxTimeoutW+0x7a
 0006ffa4 7e46634f 00000000 1000d9e8 1000b370 USER32!MessageBoxExW+0x1b
 0006ffc0 1000105f 00000000 1000d9e8 1000b370 USER32!MessageBoxW+0x45

Here’s the appropriate disassembly:

 bf83c003 a138a59abf      mov     eax,dword ptr [win32k!gptiCurrent (bf9aa538)]
 bf83c008 f6404b20        test    byte ptr [eax+4Bh],20h
 bf83c00c 8b483c          mov     ecx,dword ptr [eax+3Ch]
 bf83c00f 8b4904          mov     ecx,dword ptr [ecx+4] ds:0023:00000004=????????
 bf83c012 8b7108          mov     esi,dword ptr [ecx+8]

Interestingly, NtUserGetDC isn’t just a wrapper to the …Ex function. It has different code and isn’t vulnerable to this.

~ by omeg on November 24, 2007.

assembly, information security, reverse engineering, windows internals

Leave a Reply