суббота, 5 декабря 2015 г.

WNF identifiers

I have made a mistake in my previous article about WNF. It seems that WNF idenificators are not standard IID but pair of DWORDs, so struct my_wnf_item actually looks like:
// struct can be ripped from ntdll!RtlpCreateWnfNameSubscription
struct wnf_name
{
/*  0x0 */  DWORD tag; // 0x980912 under x64, 0x700912 under x86
/*  0x4 */  DWORD unk4;
/*  0x8 */  DWORD unk8;
/*  0xC */  DWORD unkC;
/* 0x10 */  DWORD id1;
/* 0x14 */  DWORD id2;
};
 

struct my_wnf_item
{
  LIST_ENTRY List; // linked list of my_wnf_item
  wnf_name *wnfId;
  PBYTE notify;
};


Sample from windows 10 build 10586:
CheckProcess PID 420 (csrss.exe):
PEB.NtGlobalFlag: 0
PEB.Ldr: 00007FF946ED5200
PEB.GdiSharedHandleTable: 000001EFD8BC0000
WnfRoot: 000001EFD8A05BF0
 Wnf[0] at 000001EFD8A08238: id1 A3BC4035 id2 96003D (WNF_PNPA_PORTS_CHANGED_SESSION) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[1] at 000001EFD8A080C8: id1 A3BC3875 id2 96003D (WNF_PNPA_PORTS_CHANGED) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[2] at 000001EFD8A07F58: id1 A3BC3035 id2 96003D (WNF_PNPA_HARDWAREPROFILES_CHANGED_SESSION) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[3] at 000001EFD8A07DE8: id1 A3BC2875 id2 96003D (WNF_PNPA_HARDWAREPROFILES_CHANGED) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[4] at 000001EFD8A07C78: id1 A3BC2035 id2 96003D (WNF_PNPA_VOLUMES_CHANGED_SESSION) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[5] at 000001EFD8A07B08: id1 A3BC1875 id2 96003D (WNF_PNPA_VOLUMES_CHANGED) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[6] at 000001EFD8A04EF8: id1 A3BC1035 id2 96003D (WNF_PNPA_DEVNODES_CHANGED_SESSION) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)
 Wnf[7] at 000001EFD8A05058: id1 A3BC0875 id2 96003D (WNF_PNPA_DEVNODES_CHANGED) - 00007FF943335410 (C:\Windows\system32\winsrv.DLL)


List of some WNF identifiers (sure is not completed):

пятница, 9 октября 2015 г.

using CFG on more old windows

As you may know support for CodeFlow Guard exists only since windows 10. But it seems that you still can gain some profit from CFG on more old versions of windows (for example in fuzzers/honeypots)

1) you need inject your code in target process
2) you must check if CFG presents in your target module. It seems that MS linker has a bug - DataDirectory[IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG].Size eq 0x40. but IMAGE_LOAD_CONFIG_DIRECTORY.Size contains right value
3) you must just patch pointer in *(IMAGE_LOAD_CONFIG_DIRECTORY.GuardCFCheckFunctionPointer) to your handler. Prototype of handler:
void __fastcall my_check_icall(PBYTE addr)
4) now you can check addr parameter. One possible check - just see if this addr located in some loaded module, so you can traverse on PEB_LDR_DATA

Have fun !