1
0
mirror of https://github.com/UzixLS/KernelEx.git synced 2025-07-19 07:21:20 +03:00

import KernelEx-4.5.1

This commit is contained in:
UzixLS
2018-11-03 16:23:39 +03:00
parent 7571e3c60d
commit 2948e23961
77 changed files with 2603 additions and 883 deletions

41
ApiHook/ApiHook.dsw Executable file
View File

@ -0,0 +1,41 @@
Microsoft Developer Studio Workspace File, Format Version 6.00
# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
###############################################################################
Project: "ApiLog"=.\ApiLog\ApiLog.dsp - Package Owner=<4>
Package=<5>
{{{
}}}
Package=<4>
{{{
}}}
###############################################################################
Project: "DebugWindow"=.\DebugWindow\DebugWindow.dsp - Package Owner=<4>
Package=<5>
{{{
}}}
Package=<4>
{{{
}}}
###############################################################################
Global:
Package=<5>
{{{
}}}
Package=<3>
{{{
}}}
###############################################################################

133
ApiHook/ApiLog/ApiLog.dsp Executable file
View File

@ -0,0 +1,133 @@
# Microsoft Developer Studio Project File - Name="ApiLog" - Package Owner=<4>
# Microsoft Developer Studio Generated Build File, Format Version 6.00
# ** DO NOT EDIT **
# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102
CFG=ApiLog - Win32 Debug
!MESSAGE This is not a valid makefile. To build this project using NMAKE,
!MESSAGE use the Export Makefile command and run
!MESSAGE
!MESSAGE NMAKE /f "ApiLog.mak".
!MESSAGE
!MESSAGE You can specify a configuration when running NMAKE
!MESSAGE by defining the macro CFG on the command line. For example:
!MESSAGE
!MESSAGE NMAKE /f "ApiLog.mak" CFG="ApiLog - Win32 Debug"
!MESSAGE
!MESSAGE Possible choices for configuration are:
!MESSAGE
!MESSAGE "ApiLog - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library")
!MESSAGE "ApiLog - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library")
!MESSAGE
# Begin Project
# PROP AllowPerConfigDependencies 0
# PROP Scc_ProjName ""
# PROP Scc_LocalPath ""
CPP=cl.exe
MTL=midl.exe
RSC=rc.exe
!IF "$(CFG)" == "ApiLog - Win32 Release"
# PROP BASE Use_MFC 0
# PROP BASE Use_Debug_Libraries 0
# PROP BASE Output_Dir "Release"
# PROP BASE Intermediate_Dir "Release"
# PROP BASE Target_Dir ""
# PROP Use_MFC 0
# PROP Use_Debug_Libraries 0
# PROP Output_Dir "Release"
# PROP Intermediate_Dir "Release"
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "APILOG_EXPORTS" /YX /FD /c
# ADD CPP /nologo /MT /W3 /O2 /I "." /I "../../common" /FI"msvc_quirks.h" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "APILOG_EXPORTS" /YX /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x415 /d "NDEBUG"
# ADD RSC /l 0x415 /d "NDEBUG"
BSC32=bscmake.exe
# ADD BASE BSC32 /nologo
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386
# ADD LINK32 kernel32.lib user32.lib gdi32.lib ../../kexcrt/kexcrt.lib libc.lib /nologo /entry:"DllMain@12" /dll /machine:I386 /nodefaultlib /OPT:NOWIN98
# SUBTRACT LINK32 /pdb:none
!ELSEIF "$(CFG)" == "ApiLog - Win32 Debug"
# PROP BASE Use_MFC 0
# PROP BASE Use_Debug_Libraries 1
# PROP BASE Output_Dir "Debug"
# PROP BASE Intermediate_Dir "Debug"
# PROP BASE Target_Dir ""
# PROP Use_MFC 0
# PROP Use_Debug_Libraries 1
# PROP Output_Dir "Debug"
# PROP Intermediate_Dir "Debug"
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "APILOG_EXPORTS" /YX /FD /GZ /c
# ADD CPP /nologo /MTd /W3 /Gm /ZI /Od /I "." /I "../../common" /FI"msvc_quirks.h" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "APILOG_EXPORTS" /YX /FD /GZ /c
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x415 /d "_DEBUG"
# ADD RSC /l 0x415 /d "_DEBUG"
BSC32=bscmake.exe
# ADD BASE BSC32 /nologo
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept
# ADD LINK32 kernel32.lib user32.lib gdi32.lib ../../kexcrt/kexcrt.lib libc.lib /nologo /entry:"DllMain@12" /dll /debug /machine:I386 /nodefaultlib /OPT:NOWIN98
# SUBTRACT LINK32 /pdb:none
!ENDIF
# Begin Target
# Name "ApiLog - Win32 Release"
# Name "ApiLog - Win32 Debug"
# Begin Group "Source Files"
# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
# Begin Source File
SOURCE=.\apilog.cpp
# End Source File
# Begin Source File
SOURCE=.\apilog.def
# End Source File
# Begin Source File
SOURCE=.\apilog_params.cpp
# End Source File
# Begin Source File
SOURCE=.\writer.cpp
# End Source File
# End Group
# Begin Group "Header Files"
# PROP Default_Filter "h;hpp;hxx;hm;inl"
# Begin Source File
SOURCE=.\apilog.h
# End Source File
# Begin Source File
SOURCE=.\apilog_params.h
# End Source File
# Begin Source File
SOURCE=.\writer.h
# End Source File
# End Group
# Begin Group "Resource Files"
# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
# End Group
# End Target
# End Project

38
ApiHook/ApiLog/README.txt Executable file
View File

@ -0,0 +1,38 @@
API logging DLL for KernelEx Core API hook infrastructure
Make sure to disable API extensions for this module or else the DLL
will try to hooks its own imports.
By default you have to rename the DLL to kexApiHook.dll and place it either in C:\Windows\KernelEx or somewhere in DLL search path.
Alternatively you can set the 'ApiHookPath' value under 'HKEY_LOCAL_MACHINE\Software\KernelEx' to full path to the DLL.
Search path takes precedence over other methods.
The DLL can output logs using different methods, set 'KEXAPILOG_OUTPUT' environment variable to change:
file - API logs are written to a file named as module but with '.log' extension (default)
window - API logs are output to DebugWindow application
debug - API logs are output via OutputDebugString API to system debugger
The DLL will also try to load the file called 'signature.dat' in the directory where the DLL is located.
This file contains API function signatures for parameter logging.
Syntax of the file:
[MODULENAME.DLL]
ApiName=format
where format is a sequence of letters from printf format specifiers:
p - pointer in the form of: 0x1234abcd
d - decimal number
x - hexadecimal number
s - ansi string
S - unicode string
f - float
Example:
[KERNEL32.DLL]
GetProcAddress=ps
Errors related to API hook DLL loading are written to debug output.

334
ApiHook/ApiLog/apilog.cpp Executable file
View File

@ -0,0 +1,334 @@
/*
* KernelEx
* Copyright (C) 2011, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
/*
* API logging DLL for KernelEx Core API hook infrastructure
*
* Make sure to disable API extensions for this module or else the DLL
* will try to hooks its own imports.
*/
#include "apilog.h"
#include "apilog_params.h"
#include "writer.h"
extern "C" void * _AddressOfReturnAddress(void);
#pragma intrinsic(_AddressOfReturnAddress)
#define countof(x) (sizeof(x)/sizeof(x[0]))
#ifdef _DEBUG
#define DBGASSERT(e) ((e) ? 0 : DebugBreak())
#else
#define DBGASSERT(e) ((void)0)
#endif
extern "C"
int snprintf(char *buffer, size_t n, const char* format, ...);
int tlsindex = -1;
const bool apilog_enabled = true;
HINSTANCE hInst;
ThreadAddrStack::ThreadAddrStack()
{
pos = 0;
}
void __stdcall ThreadAddrStack::push_ret_addr(DWORD addr)
{
DBGASSERT(tlsindex != -1);
ThreadAddrStack* tas = (ThreadAddrStack*) TlsGetValue(tlsindex);
if (!tas)
{
tas = new ThreadAddrStack;
TlsSetValue(tlsindex, tas);
}
tas->stack[tas->pos++] = addr;
DBGASSERT(tas->pos < countof(tas->stack));
}
DWORD __stdcall ThreadAddrStack::pop_ret_addr()
{
DBGASSERT(tlsindex != -1);
ThreadAddrStack* tas = (ThreadAddrStack*) TlsGetValue(tlsindex);
DBGASSERT(tas->pos > 0);
return tas->stack[--tas->pos];
}
DWORD __stdcall ThreadAddrStack::get_level()
{
DBGASSERT(tlsindex != -1);
ThreadAddrStack* tas = (ThreadAddrStack*) TlsGetValue(tlsindex);
return tas->pos;
}
log_stub::log_stub(const char* source, const char* target, const char* name,
unsigned long proc)
: call_prelog(DWORD(pre_log)), call_postlog(DWORD(post_log)),
call_orig(proc)
{
c_pushad1 = c_pushad2 = 0x60;
c_popad1 = c_popad2 = 0x61;
c_ret = 0xc3;
c_push1 = c_push2 = 0x68;
v_lgd1 = &lgd;
v_lgd2 = &lgd;
c_push_eax = 0x50;
c_add_esp = 0xc483;
c_sub_esp = 0xec83;
c_byte_4 = c_byte_4_1 = 4;
lgd.source = source;
lgd.target = target;
lgd.api_name = name;
}
void __stdcall log_stub::pre_log(log_data* lgd)
{
DWORD last_err;
DWORD caller_addr;
caller_addr = *((DWORD*) _AddressOfReturnAddress() + 10);
last_err = GetLastError();
ThreadAddrStack::push_ret_addr(caller_addr);
if (apilog_enabled)
{
DWORD level;
char msg[DEBUGMSG_MAXLEN];
level = ThreadAddrStack::get_level();
int z = snprintf(msg, sizeof(msg)-1, "%-2d|%x|%*s[%s]%08x:<%s>%s",
level,
GetCurrentThreadId(),
(level-1) * 2, "",
lgd->source, caller_addr,
lgd->target, lgd->api_name);
va_list ap = va_list((DWORD*) &lgd + 10);
z += ApiLogParams::inst().decode_parameters(lgd->target, lgd->api_name, ap, msg + z, sizeof(msg)-1 - z);
strcpy(msg + z, "\n");
writer_fn(msg);
}
SetLastError(last_err);
}
void __stdcall log_stub::post_log(log_data* lgd, DWORD retval)
{
DWORD last_err;
DWORD& caller_addr = *((DWORD*) _AddressOfReturnAddress() + 11);
last_err = GetLastError();
caller_addr = ThreadAddrStack::pop_ret_addr();
if (apilog_enabled)
{
DWORD level;
char msg[DEBUGMSG_MAXLEN];
level = ThreadAddrStack::get_level() + 1;
snprintf(msg, sizeof(msg), "%-2d|%x|%*s[%s]%08x:<%s>%s|%x\n",
level,
GetCurrentThreadId(),
(level-1) * 2, "",
lgd->source, caller_addr,
lgd->target, lgd->api_name,
retval);
writer_fn(msg);
}
SetLastError(last_err);
}
HMODULE GetCurrentModule()
{
MEMORY_BASIC_INFORMATION mbi;
static int dummy;
VirtualQuery(&dummy, &mbi, sizeof(mbi));
return (HMODULE)mbi.AllocationBase;
}
void load_signature()
{
char signature_file[MAX_PATH];
GetModuleFileName(hInst, signature_file, MAX_PATH);
char* p = strrchr(signature_file, '\\');
if (!p) p = signature_file;
else p++;
*p = '\0';
strcat(signature_file, "signature.dat");
OutputDebugString("Loading apilog signatures... ");
bool res = ApiLogParams::inst().load_signatures(signature_file);
OutputDebugString(res ? "done.\n" : "error.\n");
}
bool filter_out(const char* target, const char* api)
{
static const char* filtered_apis[] =
{
"HeapAlloc",
"HeapFree",
"HeapReAlloc",
"HeapSize",
"GetProcessHeap",
"TlsGetValue",
"TlsSetValue",
"InitializeCriticalSection",
"ReinitializeCriticalSection",
"DeleteCriticalSection",
"EnterCriticalSection",
"LeaveCriticalSection",
"InterlockedIncrement",
"InterlockedDecrement",
"InterlockedExchange",
"InterlockedExchangeAdd",
"InterlockedCompareExchange",
};
if (HIWORD(api) && !strcmp(target, "KERNEL32.DLL"))
{
for (int i = 0 ; i < countof(filtered_apis) ; i++)
{
if (!strcmp(api, filtered_apis[i]))
return true;
}
}
return false;
}
/*
* This function is called before any call to _register and BEFORE DllMain
* in order to let you prepare your API hooks.
*
* Return:
* 1 for success
* 0 in case of error - this will trigger unloading of the DLL
*
* WARNING: This function is called inside Kernel32Lock
* so you have to be VERY careful what you call here if you don't want
* to crash the system.
*/
int kexApiHook_initonce(void)
{
hInst = GetCurrentModule();
DBGASSERT(hInst != NULL);
load_signature();
return 1;
}
/*
* This function is called by the resolver for each API imported by a module.
* This function is called before DllMain.
*
* Parameters:
* caller - the module which imports the API (full path)
* target - the module from which API is imported (full path)
* api - the name of the API or ordinal number of the API (if upper word is zero)
* orig - address of the API being hooked, can be NULL if resolver found no API
*
* Return:
* orig - if you don't want to hook the API
* address of the hook - if you want to intercept the API
* NULL - if you want to disable the API altogether
*
* WARNING: This function is called inside Kernel32Lock
* so you have to be VERY careful what you call here if you don't want
* to crash the system.
*/
PROC kexApiHook_register(const char* caller, const char* target, const char* api, PROC orig)
{
char* new_api;
if (orig == NULL)
return orig;
//extract DLL file names
char* p;
p = strrchr(caller, '\\');
if (p) caller = p + 1;
p = strrchr(target, '\\');
if (p) target = p + 1;
if (filter_out(target, api))
return orig;
if (HIWORD(api)) //named export
{
new_api = strdup(api);
}
else //ordinal export
{
char ord_name[32];
snprintf(ord_name, sizeof(ord_name), "Ordinal:%u", (unsigned) api);
new_api = strdup(ord_name);
}
return (PROC) new log_stub(caller, target, new_api, (unsigned long) orig);
}
void prologue()
{
char path[MAX_PATH];
GetModuleFileName(NULL, path, MAX_PATH);
char msg[DEBUGMSG_MAXLEN];
snprintf(msg, sizeof(msg) -1, "0 |KernelEx API Log start for %s\n", path);
writer_fn(msg);
}
void epilogue()
{
writer_fn("0 |End of API log\n");
}
/*
* Called at DLL initialization/unload time, outside of Kernel32Lock.
* All static variables are initialized at this point.
* Also all DLLs on which this DLL depends are initialized here.
* This DLL's module tree is initialized before DLLs belonging to the process
* so be careful what you do.
*/
BOOL APIENTRY DllMain(HINSTANCE hModule, DWORD dwReason, LPVOID lpReserved)
{
if (dwReason == DLL_PROCESS_ATTACH)
{
tlsindex = TlsAlloc();
if (tlsindex == -1)
return 0;
DisableThreadLibraryCalls(hModule);
if (!init_writer())
return FALSE;
prologue();
}
else if (dwReason == DLL_PROCESS_DETACH)
{
epilogue();
}
return TRUE;
}

4
ApiHook/ApiLog/apilog.def Executable file
View File

@ -0,0 +1,4 @@
LIBRARY ApiLog.dll BASE=0x77000000
EXPORTS
kexApiHook_initonce
kexApiHook_register

122
ApiHook/ApiLog/apilog.h Executable file
View File

@ -0,0 +1,122 @@
/*
* KernelEx
* Copyright (C) 2011, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#ifndef _APILOG_APILOG_H
#define _APILOG_APILOG_H
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
class ThreadAddrStack
{
public:
ThreadAddrStack();
static void __stdcall push_ret_addr(DWORD addr);
static DWORD __stdcall pop_ret_addr();
static DWORD __stdcall get_level();
private:
int pos;
DWORD stack[1023];
};
#pragma pack(push,1)
/* Creates a stub that calls address specified in the constructor. */
class redir_stub
{
public:
redir_stub(unsigned long target, bool make_call = true)
{
op = make_call ? 0xe8 : 0xe9;
addr = target - ((unsigned long)(this) + 5);
}
private:
unsigned char op;
unsigned long addr;
};
/* Creates a stub for api logging. */
class log_stub
{
public:
log_stub(const char* source, const char* target, const char* name,
unsigned long proc);
private:
struct log_data
{
const char* source;
const char* target;
const char* api_name;
};
static void __stdcall pre_log(log_data* lgd);
static void __stdcall post_log(log_data* lgd, DWORD retval);
/*
pushad
push lgd
call pre_log@4
popad
add esp, 4
call orig
sub esp, 4
pushad
push eax
push lgd
call post_log@8
popad
ret
*/
BYTE c_pushad1;
BYTE c_push1;
log_data* v_lgd1;
redir_stub call_prelog;
BYTE c_popad1;
WORD c_add_esp;
BYTE c_byte_4;
redir_stub call_orig;
WORD c_sub_esp;
BYTE c_byte_4_1;
BYTE c_pushad2;
BYTE c_push_eax;
BYTE c_push2;
log_data* v_lgd2;
redir_stub call_postlog;
BYTE c_popad2;
BYTE c_ret;
log_data lgd;
};
#pragma pack(pop)
#endif

172
ApiHook/ApiLog/apilog_params.cpp Executable file
View File

@ -0,0 +1,172 @@
/*
* KernelEx
* Copyright (C) 2010, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#include <malloc.h>
#include "apilog_params.h"
extern "C"
int vsnprintf(char *buffer, size_t n, const char *format, va_list ap);
//singleton instance
ApiLogParams* ApiLogParams::inst_;
ApiLogParams::ApiLogParams() : empty_signature("")
{
}
ApiLogParams::~ApiLogParams()
{
}
int ApiLogParams::decode_parameters(const char* lib, const char* fn, va_list ap,
char* buf, int len)
{
const sstring& sign = get_signature(lib, fn);
if (sign.empty())
return 0;
int slen = sign.length();
int extra = 0;
for (int i = 0 ; i < slen ; i++)
{
if (sign[i] == 's' || sign[i] == 'S') extra += 2;
}
char* format = (char*) alloca(slen * 3 + 3);
char* p = format;
*p++ = '(';
for (int i = 0 ; i < slen ; i++)
{
bool wide = false;
char fc = sign[i];
if (i != 0)
*p++ = ' ';
if (fc == 's' || fc == 'S') *p++ = '\"';
*p++ = '%';
*p++ = fc;
if (fc == 's' || fc == 'S') *p++ = '\"';
}
*p++ = ')';
*p++ = '\0';
__try
{
return vsnprintf(buf, len, format, ap);
}
__except(EXCEPTION_EXECUTE_HANDLER)
{
//better output nothing than crash
return 0;
}
}
size_t ApiLogParams::readline(HANDLE file, char* buf, size_t size)
{
char c;
DWORD nr;
size_t pos = 0;
bool cmt = false;
bool read_sth = false;
//fill buffer with a line, skipping comments, trimming line to buffer size
while (ReadFile(file, &c, 1, &nr, NULL) && nr == 1)
{
read_sth = true;
if (c == '\r')
continue;
if (c == '\n')
break;
if (c == ';' || cmt)
{
cmt = true;
continue;
}
if (pos < size-1)
buf[pos++] = c;
}
if (read_sth)
buf[pos++] = '\0';
return pos;
}
bool ApiLogParams::load_signatures(const char* file_name)
{
char buf[256];
sstring lib;
HANDLE file = CreateFile(file_name, GENERIC_READ, FILE_SHARE_READ,
NULL, OPEN_EXISTING, 0, NULL);
if (file == INVALID_HANDLE_VALUE)
return false;
while (readline(file, buf, sizeof(buf)) != 0)
{
char* p;
char* fun;
char* sig;
//library name
if (buf[0] == '[')
{
p = strchr(buf, ']');
if (!p) continue;
*p = '\0';
strupr(buf);
lib = buf + 1;
}
//function definition
else
{
fun = buf;
p = strchr(buf, '=');
if (!p) continue;
*p++ = '\0';
sig = p;
if (!lib.empty())
signatures[lib][fun] = sig;
}
}
CloseHandle(file);
return true;
}
const sstring& ApiLogParams::get_signature(const char* lib, const char* fn)
{
std::map<sstring, std::map<sstring, sstring> >::iterator outer;
std::map<sstring, sstring>::iterator inner;
outer = signatures.find(lib);
if (outer == signatures.end())
return empty_signature;
inner = outer->second.find(fn);
if (inner == outer->second.end())
return empty_signature;
return inner->second;
}

54
ApiHook/ApiLog/apilog_params.h Executable file
View File

@ -0,0 +1,54 @@
/*
* KernelEx
* Copyright (C) 2010, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#ifndef __APILOGPARAMS_H
#define __APILOGPARAMS_H
#include <map>
#include <stdarg.h>
#include <windows.h>
#include "sstring.hpp"
class ApiLogParams
{
public:
~ApiLogParams();
int decode_parameters(const char* lib, const char* fn, va_list ap, char* buf, int len);
bool load_signatures(const char* file_name);
static ApiLogParams& inst();
private:
ApiLogParams();
const sstring& get_signature(const char* lib, const char* fn);
size_t readline(HANDLE file, char* buf, size_t size);
static ApiLogParams* inst_;
const sstring empty_signature;
std::map<sstring, std::map<sstring, sstring> > signatures;
};
inline ApiLogParams& ApiLogParams::inst()
{
if (!inst_) inst_ = new ApiLogParams;
return *inst_;
}
#endif // __APILOGPARAMS_H

37
ApiHook/ApiLog/test.cpp Executable file
View File

@ -0,0 +1,37 @@
#include <windows.h>
#include <stdio.h>
typedef PROC (*al_register_t)(const char*, const char*, const char*, PROC);
typedef int (*init_once_t)(void);
typedef int (WINAPI *MessageBox_t)(HWND, LPCWSTR, LPCWSTR, UINT);
int main()
{
MessageBox_t msgbox;
HMODULE hUser32 = LoadLibrary("user32.dll");
msgbox = (MessageBox_t) GetProcAddress(hUser32, "MessageBoxW");
al_register_t al_register;
init_once_t init_once;
HMODULE hApiHookDll = LoadLibrary("ApiLog.dll");
init_once = (init_once_t) GetProcAddress(hApiHookDll, "kexApiHook_initonce");
al_register = (al_register_t) GetProcAddress(hApiHookDll, "kexApiHook_register");
if (!init_once || !al_register)
{
puts("Failed to load api hook dll");
return 1;
}
if (!init_once())
{
puts("Failed to init api hook dll");
return 1;
}
msgbox = (MessageBox_t) al_register("SOURCE", "TARGET", "TestApi", (PROC) msgbox);
msgbox(NULL, L"This is a test message", L"Caption", MB_OK | MB_ICONINFORMATION);
FreeLibrary(hUser32);
FreeLibrary(hApiHookDll);
return 0;
}

121
ApiHook/ApiLog/writer.cpp Executable file
View File

@ -0,0 +1,121 @@
/*
* KernelEx
* Copyright (C) 2011, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include "writer.h"
#define VA_SHARED 0x8000000
const unsigned short WM_KEXAPPENDLOG = 0x6eef;
static HANDLE hFile;
static char* shbuf;
static HWND hwnd;
static CRITICAL_SECTION windows_cs;
typedef bool (*initfn_t)();
initfn_t init_fn;
writerfn_t writer_fn;
bool init_file()
{
char path[MAX_PATH];
char* p;
GetModuleFileName(NULL, path, sizeof(path));
p = strrchr(path, '.');
if (p) *p = '\0';
strcat(path, ".log");
hFile = CreateFile(path, GENERIC_WRITE, FILE_SHARE_READ, NULL,
CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if (hFile == INVALID_HANDLE_VALUE)
return false;
return true;
}
void write_file(const char* msg)
{
DWORD written;
WriteFile(hFile, msg, strlen(msg), &written, NULL);
}
bool init_window()
{
shbuf = (char*) VirtualAlloc(NULL, DEBUGMSG_MAXLEN,
VA_SHARED | MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE);
hwnd = FindWindow(NULL, "KernelEx Debug Console");
InitializeCriticalSection(&windows_cs);
if (hwnd == NULL)
return false;
return true;
}
void write_window(const char* msg)
{
EnterCriticalSection(&windows_cs);
strcpy(shbuf, msg);
int i = strlen(shbuf);
if (i > 0) shbuf[i-1] = 0;
SendMessage(hwnd, WM_KEXAPPENDLOG, 0, (LPARAM) shbuf);
LeaveCriticalSection(&windows_cs);
}
bool init_debug()
{
return true;
}
void write_debug(const char* msg)
{
OutputDebugString(msg);
}
bool init_writer()
{
char output[100];
output[0] = 0;
if (GetEnvironmentVariable("KEXAPILOG_OUTPUT", output, sizeof(output)))
{
if (!strcmp(output, "file"))
{
init_fn = init_file;
writer_fn = write_file;
}
else if (!strcmp(output, "window"))
{
init_fn = init_window;
writer_fn = write_window;
}
else if (!strcmp(output, "debug"))
{
init_fn = init_debug;
writer_fn = write_debug;
}
}
//default fallback
if (!writer_fn)
{
init_fn = init_file;
writer_fn = write_file;
}
return init_fn();
}

32
ApiHook/ApiLog/writer.h Executable file
View File

@ -0,0 +1,32 @@
/*
* KernelEx
* Copyright (C) 2011, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#ifndef _APILOG_WRITER_H
#define _APILOG_WRITER_H
#define DEBUGMSG_MAXLEN 256
typedef void (*writerfn_t)(const char* msg);
extern writerfn_t writer_fn;
bool init_writer();
#endif

View File

@ -0,0 +1,439 @@
/*
* KernelEx
* Copyright (C) 2009, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#include <windows.h>
#include <commctrl.h>
#include <malloc.h>
#include "DebugWindow.h"
#include "resource.h"
#define DEBUGMSG_MAXLEN 256
extern "C"
char* strtok_r(char* s, const char* delim, char** holder);
static bool apilog_enabled;
const unsigned short WM_KEXAPPENDLOG = 0x6eef;
HINSTANCE hInstance;
DebugWindow::DebugWindow()
{
hwnd = (HWND) -1;
//we're interested in everything
includes.push_back("*");
//these usually aren't interesting
excludes.push_back("Tls");
excludes.push_back("Heap");
excludes.push_back("CriticalSection");
excludes.push_back("Interlocked");
InitCommonControls();
}
DebugWindow::~DebugWindow()
{
}
BOOL CALLBACK DebugWindow::DebugDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
NMHDR* nmhdr;
DebugWindow* _this = (DebugWindow*) GetWindowLong(hwnd, GWL_USERDATA);
switch (msg)
{
case WM_INITDIALOG:
_this = (DebugWindow*) lParam;
SetWindowLong(hwnd, GWL_USERDATA, lParam);
_this->InitDialog(hwnd);
break;
case WM_SIZE:
MoveWindow(GetDlgItem(hwnd, IDC_LOG), 0, 0, LOWORD(lParam), HIWORD(lParam), TRUE);
SendDlgItemMessage(hwnd, IDC_LOG, WM_VSCROLL, SB_BOTTOM, 0);
break;
case WM_CLOSE:
DestroyWindow(hwnd);
break;
case WM_KEXAPPENDLOG:
_this->append((const char*) lParam);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
case WM_NOTIFY:
nmhdr = (NMHDR*) lParam;
if (nmhdr->idFrom == IDC_LOG)
if (nmhdr->code == NM_RCLICK)
{
_this->HandleMenu(hwnd);
break;
}
else if (nmhdr->code == LVN_KEYDOWN)
{
LPNMLVKEYDOWN nm = (LPNMLVKEYDOWN) lParam;
if (nm->wVKey == VK_DELETE)
{
_this->DeleteSelItems();
break;
}
}
default:
return FALSE;
}
return TRUE;
}
void DebugWindow::InitDialog(HWND hwnd)
{
hList = GetDlgItem(hwnd, IDC_LOG);
MoveWindow(hwnd, 0, 0, 480, 200, TRUE);
SendMessage(hList, LVM_SETEXTENDEDLISTVIEWSTYLE,
0, LVS_EX_FULLROWSELECT);
LV_COLUMN col;
memset(&col, 0, sizeof(col));
col.mask = LVCF_TEXT | LVCF_SUBITEM | LVCF_WIDTH | LVCF_FMT;
col.cx = 20;
col.pszText = "Depth";
col.fmt = LVCFMT_RIGHT;
ListView_InsertColumn(hList, 0, &col);
col.cx = 60;
col.fmt = LVCFMT_LEFT;
col.pszText = "Thread";
ListView_InsertColumn(hList, 1, &col);
col.cx = 310;
col.pszText = "Info";
ListView_InsertColumn(hList, 2, &col);
col.cx = 60;
col.fmt = LVCFMT_RIGHT;
col.pszText = "Return";
ListView_InsertColumn(hList, 3, &col);
#define NUM_COLS 4
menu = LoadMenu(hInstance, MAKEINTRESOURCE(IDR_LOGMENU));
menu = GetSubMenu(menu, 0);
}
void DebugWindow::HandleMenu(HWND hwnd)
{
POINT p;
GetCursorPos(&p);
int res = TrackPopupMenu(menu, TPM_LEFTALIGN | TPM_LEFTBUTTON | TPM_RETURNCMD,
p.x, p.y, 0, hwnd, NULL);
switch (res)
{
case IDM_ENABLE:
apilog_enabled = !apilog_enabled;
CheckMenuItem(menu, IDM_ENABLE, apilog_enabled ? MF_CHECKED : MF_UNCHECKED);
break;
case IDM_TOFILE:
WriteToFile();
break;
case IDM_CLEAR:
//FIXME: when there is a lot of entries it takes very long to clear the list
//how to improve this?
ListView_DeleteAllItems(hList);
break;
case IDM_FILTER:
DialogBoxParam(hInstance, MAKEINTRESOURCE(IDD_DEBUGFILTER),
hwnd, FilterDlgProc, (LPARAM) this);
break;
}
}
void DebugWindow::DeleteSelItems()
{
if (ListView_GetSelectedCount(hList) == 0)
return;
for (int i = ListView_GetItemCount(hList) - 1 ; i >= 0 ; i--)
{
if (ListView_GetItemState(hList, i, LVIS_SELECTED))
ListView_DeleteItem(hList, i);
}
}
void DebugWindow::ListView_Append(char* msg)
{
LV_ITEM item;
int idx;
HWND hList = GetDlgItem(hwnd, IDC_LOG);
char* p;
char* pch;
memset(&item, 0, sizeof(item));
pch = strtok_r(msg, "|", &p);
if (!pch)
return;
int items = ListView_GetItemCount(hList);
if (items >= 1000)
{
ListView_DeleteItem(hList, 0);
items--;
}
item.mask = LVIF_TEXT;
item.iItem = items;
item.iSubItem = 0;
item.pszText = pch;
idx = ListView_InsertItem(hList, &item);
while ((pch = strtok_r(NULL, "|", &p)) != NULL)
{
item.iSubItem++;
item.pszText = pch;
ListView_SetItem(hList, &item);
}
}
BOOL CALLBACK DebugWindow::FilterDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
DebugWindow* _this = (DebugWindow*) GetWindowLong(hwnd, GWL_USERDATA);
int len1, len2;
char* buf;
char* pch;
char* p;
list<sstring>::const_iterator it;
switch (msg)
{
case WM_INITDIALOG:
_this = (DebugWindow*) lParam;
SetWindowLong(hwnd, GWL_USERDATA, lParam);
len1 = 0;
len2 = 0;
for (it = _this->includes.begin() ; it != _this->includes.end() ; it++)
len1 += it->length() + 1;
for (it = _this->excludes.begin() ; it != _this->excludes.end() ; it++)
len2 += it->length() + 1;
buf = (char*) alloca(max(len1, len2));
buf[0] = '\0';
for (it = _this->includes.begin() ; it != _this->includes.end() ; it++)
{
if (it != _this->includes.begin())
strcat(buf, ";");
strcat(buf, *it);
}
SetDlgItemText(hwnd, IDC_DFINCLUDE, buf);
buf[0] = '\0';
for (it = _this->excludes.begin() ; it != _this->excludes.end() ; it++)
{
if (it != _this->excludes.begin())
strcat(buf, ";");
strcat(buf, *it);
}
SetDlgItemText(hwnd, IDC_DFEXCLUDE, buf);
break;
case WM_COMMAND:
switch (LOWORD(wParam))
{
case IDCANCEL:
EndDialog(hwnd, 0);
break;
case IDOK:
len1 = GetWindowTextLength(GetDlgItem(hwnd, IDC_DFINCLUDE)) + 1;
len2 = GetWindowTextLength(GetDlgItem(hwnd, IDC_DFEXCLUDE)) + 1;
buf = (char*) alloca(max(len1, len2));
GetDlgItemText(hwnd, IDC_DFINCLUDE, buf, len1);
_this->includes.clear();
pch = strtok_r(buf, ";", &p);
if (pch)
{
_this->includes.push_back(pch);
while ((pch = strtok_r(NULL, ";", &p)) != NULL)
_this->includes.push_back(pch);
}
GetDlgItemText(hwnd, IDC_DFEXCLUDE, buf, len2);
_this->excludes.clear();
pch = strtok_r(buf, ";", &p);
if (pch)
{
_this->excludes.push_back(pch);
while ((pch = strtok_r(NULL, ";", &p)) != NULL)
_this->excludes.push_back(pch);
}
EndDialog(hwnd, 0);
break;
}
break;
case WM_CLOSE:
EndDialog(hwnd, 0);
break;
default:
return FALSE;
}
return TRUE;
}
void DebugWindow::WriteToFile()
{
char buf[DEBUGMSG_MAXLEN];
OPENFILENAME ofn;
int rows;
LV_COLUMN col;
char filename[MAX_PATH];
HANDLE hFile;
HMODULE hComDlg32;
BOOL (WINAPI* pGetSaveFileName)(OPENFILENAME*);
hComDlg32 = GetModuleHandle("COMDLG32.DLL");
if (!hComDlg32)
hComDlg32 = LoadLibrary("COMDLG32.DLL");
if (!hComDlg32)
return;
pGetSaveFileName = (BOOL (WINAPI*)(OPENFILENAME*))
GetProcAddress(hComDlg32, "GetSaveFileNameA");
if (!pGetSaveFileName)
return;
filename[0] = '\0';
memset(&ofn, 0, sizeof(ofn));
ofn.lStructSize = sizeof(ofn);
ofn.hwndOwner = hwnd;
ofn.hInstance = hInstance;
ofn.lpstrFilter = "Text file\0*.txt\0";
ofn.lpstrDefExt = ".txt";
ofn.lpstrFile = filename;
ofn.nMaxFile = sizeof(filename);
ofn.Flags = OFN_EXPLORER | OFN_PATHMUSTEXIST | OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT;
if (!pGetSaveFileName(&ofn))
return;
hFile = CreateFile(filename, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if (hFile == INVALID_HANDLE_VALUE)
return;
//write column headers
col.mask = LVCF_TEXT;
col.pszText = buf;
col.cchTextMax = sizeof(buf);
DWORD wlen;
for (int j = 0 ; j < NUM_COLS ; j++)
{
DWORD len;
ListView_GetColumn(hList, j, &col);
len = strlen(buf);
if (j) WriteFile(hFile, " ", 1, &wlen, NULL);
WriteFile(hFile, buf, len, &wlen, NULL);
}
WriteFile(hFile, "\r\n", 2, &wlen, NULL);
//write rows
rows = ListView_GetItemCount(hList);
for (int i = 0 ; i < rows ; i++)
{
for (int j = 0 ; j < NUM_COLS ; j++)
{
DWORD len; DWORD wlen;
ListView_GetItemText(hList, i, j, buf, sizeof(buf));
len = strlen(buf);
if (j == 1 || j == 2) WriteFile(hFile, " ", 1, &wlen, NULL);
else if (j == 3 && len) WriteFile(hFile, " = ", 3, &wlen, NULL);
WriteFile(hFile, buf, len, &wlen, NULL);
}
WriteFile(hFile, "\r\n", 2, &wlen, NULL);
}
CloseHandle(hFile);
MessageBox(hwnd, "File written successfully", "Information", MB_ICONINFORMATION | MB_OK);
}
void DebugWindow::msgloop()
{
MSG msg;
hwnd = CreateDialogParam(hInstance, MAKEINTRESOURCE(IDD_DEBUG),
NULL, DebugDlgProc, (LPARAM) this);
ShowWindow(hwnd, SW_SHOW);
while (GetMessage(&msg, NULL, 0, 0))
DispatchMessage(&msg);
}
void DebugWindow::append(const char* str)
{
static char msg[DEBUGMSG_MAXLEN];
bool filter_out = true;
//filter out based on includes and excludes
if (includes.size() != 0)
{
if (includes.size() == 1 && strcmp(includes.front(), "*") == 0)
filter_out = false;
else
{
list<sstring>::const_iterator it;
for (it = includes.begin() ; it != includes.end() ; it++)
if (strstr(str, *it))
{
filter_out = false;
break;
}
}
}
if (!filter_out)
{
list<sstring>::const_iterator it;
for (it = excludes.begin() ; it != excludes.end() ; it++)
if (strstr(str, *it))
{
filter_out = true;
break;
}
}
if (filter_out)
return;
strncpy(msg, str, sizeof(msg));
msg[sizeof(msg) - 1] = '\0';
ListView_Append(msg);
SendMessage(hList, WM_VSCROLL, SB_BOTTOM, 0);
}
int WINAPI WinMain(HINSTANCE hinstance, HINSTANCE hPrevInstance,
LPSTR lpCmdLine, int nCmdShow)
{
hInstance = hinstance;
DebugWindow dw;
dw.msgloop();
return 0;
}

View File

@ -0,0 +1,120 @@
# Microsoft Developer Studio Project File - Name="DebugWindow" - Package Owner=<4>
# Microsoft Developer Studio Generated Build File, Format Version 6.00
# ** DO NOT EDIT **
# TARGTYPE "Win32 (x86) Application" 0x0101
CFG=DebugWindow - Win32 Debug
!MESSAGE This is not a valid makefile. To build this project using NMAKE,
!MESSAGE use the Export Makefile command and run
!MESSAGE
!MESSAGE NMAKE /f "DebugWindow.mak".
!MESSAGE
!MESSAGE You can specify a configuration when running NMAKE
!MESSAGE by defining the macro CFG on the command line. For example:
!MESSAGE
!MESSAGE NMAKE /f "DebugWindow.mak" CFG="DebugWindow - Win32 Debug"
!MESSAGE
!MESSAGE Possible choices for configuration are:
!MESSAGE
!MESSAGE "DebugWindow - Win32 Release" (based on "Win32 (x86) Application")
!MESSAGE "DebugWindow - Win32 Debug" (based on "Win32 (x86) Application")
!MESSAGE
# Begin Project
# PROP AllowPerConfigDependencies 0
# PROP Scc_ProjName ""
# PROP Scc_LocalPath ""
CPP=cl.exe
MTL=midl.exe
RSC=rc.exe
!IF "$(CFG)" == "DebugWindow - Win32 Release"
# PROP BASE Use_MFC 0
# PROP BASE Use_Debug_Libraries 0
# PROP BASE Output_Dir "Release"
# PROP BASE Intermediate_Dir "Release"
# PROP BASE Target_Dir ""
# PROP Use_MFC 0
# PROP Use_Debug_Libraries 0
# PROP Output_Dir "Release"
# PROP Intermediate_Dir "Release"
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /c
# ADD CPP /nologo /W3 /GX- /O2 /I "." /I "../../common" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x415 /d "NDEBUG"
# ADD RSC /l 0x415 /d "NDEBUG"
BSC32=bscmake.exe
# ADD BASE BSC32 /nologo
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /machine:I386
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib comctl32.lib ../../kexcrt/kexcrt.lib libc.lib /nologo /entry:"" /subsystem:windows /machine:I386 /nodefaultlib
!ELSEIF "$(CFG)" == "DebugWindow - Win32 Debug"
# PROP BASE Use_MFC 0
# PROP BASE Use_Debug_Libraries 1
# PROP BASE Output_Dir "Debug"
# PROP BASE Intermediate_Dir "Debug"
# PROP BASE Target_Dir ""
# PROP Use_MFC 0
# PROP Use_Debug_Libraries 1
# PROP Output_Dir "Debug"
# PROP Intermediate_Dir "Debug"
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /GZ /c
# ADD CPP /nologo /W3 /Gm /GX- /ZI /Od /I "." /I "../../common" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /GZ /c
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x415 /d "_DEBUG"
# ADD RSC /l 0x415 /d "_DEBUG"
BSC32=bscmake.exe
# ADD BASE BSC32 /nologo
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /debug /machine:I386 /pdbtype:sept
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib comctl32.lib ../../kexcrt/kexcrt.lib libc.lib /nologo /subsystem:windows /debug /machine:I386 /nodefaultlib
# SUBTRACT LINK32 /pdb:none
!ENDIF
# Begin Target
# Name "DebugWindow - Win32 Release"
# Name "DebugWindow - Win32 Debug"
# Begin Group "Source Files"
# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
# Begin Source File
SOURCE=.\DebugWindow.cpp
# End Source File
# End Group
# Begin Group "Header Files"
# PROP Default_Filter "h;hpp;hxx;hm;inl"
# Begin Source File
SOURCE=.\DebugWindow.h
# End Source File
# Begin Source File
SOURCE=.\resource.h
# End Source File
# End Group
# Begin Group "Resource Files"
# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
# Begin Source File
SOURCE=.\DebugWindow.rc
# End Source File
# End Group
# End Target
# End Project

View File

@ -0,0 +1,56 @@
/*
* KernelEx
* Copyright (C) 2009, Xeno86
*
* This file is part of KernelEx source code.
*
* KernelEx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published
* by the Free Software Foundation; version 2 of the License.
*
* KernelEx is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with GNU Make; see the file COPYING. If not, write to
* the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
*
*/
#ifndef __DEBUG_WINDOW_H
#define __DEBUG_WINDOW_H
#include "sstring.hpp"
#pragma warning(disable:4530) //we don't do exception handling
#include <list>
#pragma warning(default:4530)
using namespace std;
class DebugWindow
{
public:
DebugWindow();
~DebugWindow();
void msgloop();
void append(const char* str);
private:
HWND hwnd;
HWND hList;
HMENU menu;
list<sstring> includes;
list<sstring> excludes;
static BOOL CALLBACK DebugDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
static BOOL CALLBACK FilterDlgProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
void InitDialog(HWND hwnd);
void HandleMenu(HWND hwnd);
void DeleteSelItems();
void ListView_Append(char* msg);
void WriteToFile();
};
#endif

View File

@ -0,0 +1,141 @@
//Microsoft Developer Studio generated resource script.
//
#include "resource.h"
#define APSTUDIO_READONLY_SYMBOLS
/////////////////////////////////////////////////////////////////////////////
//
// Generated from the TEXTINCLUDE 2 resource.
//
#include "afxres.h"
/////////////////////////////////////////////////////////////////////////////
#undef APSTUDIO_READONLY_SYMBOLS
/////////////////////////////////////////////////////////////////////////////
// Neutral resources
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_NEU)
#ifdef _WIN32
LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL
#pragma code_page(1250)
#endif //_WIN32
/////////////////////////////////////////////////////////////////////////////
//
// Dialog
//
IDD_DEBUG DIALOG DISCARDABLE 0, 0, 186, 100
STYLE WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU |
WS_THICKFRAME
CAPTION "KernelEx Debug Console"
FONT 8, "MS Sans Serif"
BEGIN
CONTROL "",IDC_LOG,"SysListView32",LVS_REPORT | WS_TABSTOP,0,0,
185,100
END
IDD_DEBUGFILTER DIALOG DISCARDABLE 0, 0, 177, 90
STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "Filter settings"
FONT 8, "MS Sans Serif"
BEGIN
DEFPUSHBUTTON "OK",IDOK,65,70,50,14
PUSHBUTTON "Cancel",IDCANCEL,120,70,50,14
EDITTEXT IDC_DFINCLUDE,5,15,165,14,ES_AUTOHSCROLL
EDITTEXT IDC_DFEXCLUDE,5,45,165,14,ES_AUTOHSCROLL
LTEXT "Include:",IDC_STATIC,5,5,26,8
LTEXT "Exclude:",IDC_STATIC,5,35,28,8
END
/////////////////////////////////////////////////////////////////////////////
//
// Menu
//
IDR_LOGMENU MENU DISCARDABLE
BEGIN
POPUP ""
BEGIN
MENUITEM "Enabled", IDM_ENABLE, CHECKED
MENUITEM SEPARATOR
MENUITEM "Save to file", IDM_TOFILE
MENUITEM "Clear", IDM_CLEAR
MENUITEM "Filter", IDM_FILTER
END
END
/////////////////////////////////////////////////////////////////////////////
//
// DESIGNINFO
//
#ifdef APSTUDIO_INVOKED
GUIDELINES DESIGNINFO DISCARDABLE
BEGIN
IDD_DEBUGFILTER, DIALOG
BEGIN
LEFTMARGIN, 7
RIGHTMARGIN, 170
TOPMARGIN, 7
BOTTOMMARGIN, 83
END
END
#endif // APSTUDIO_INVOKED
#endif // Neutral resources
/////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////
// Polish resources
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_PLK)
#ifdef _WIN32
LANGUAGE LANG_POLISH, SUBLANG_DEFAULT
#pragma code_page(1250)
#endif //_WIN32
#ifdef APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// TEXTINCLUDE
//
1 TEXTINCLUDE DISCARDABLE
BEGIN
"resource.h\0"
END
2 TEXTINCLUDE DISCARDABLE
BEGIN
"#include ""afxres.h""\r\n"
"\0"
END
3 TEXTINCLUDE DISCARDABLE
BEGIN
"\r\n"
"\0"
END
#endif // APSTUDIO_INVOKED
#endif // Polish resources
/////////////////////////////////////////////////////////////////////////////
#ifndef APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// Generated from the TEXTINCLUDE 3 resource.
//
/////////////////////////////////////////////////////////////////////////////
#endif // not APSTUDIO_INVOKED

28
ApiHook/DebugWindow/resource.h Executable file
View File

@ -0,0 +1,28 @@
//{{NO_DEPENDENCIES}}
// Microsoft Developer Studio generated include file.
// Used by Core.rc
//
#define IDS_NOTREADY 1
#define IDS_STUBMISMATCH 2
#define IDS_OLDVER 3
#define IDD_DEBUG 101
#define IDR_LOGMENU 102
#define IDD_DEBUGFILTER 103
#define IDC_LOG 1003
#define IDC_DFINCLUDE 1004
#define IDC_DFEXCLUDE 1005
#define IDM_TOFILE 40001
#define IDM_CLEAR 40002
#define IDM_FILTER 40003
#define IDM_ENABLE 40004
// Next default values for new objects
//
#ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS
#define _APS_NEXT_RESOURCE_VALUE 104
#define _APS_NEXT_COMMAND_VALUE 40005
#define _APS_NEXT_CONTROL_VALUE 1006
#define _APS_NEXT_SYMED_VALUE 101
#endif
#endif

5
ApiHook/README.txt Executable file
View File

@ -0,0 +1,5 @@
In order to use the projects in this folder, you need to compile KernelEx Core with _ENABLE_APIHOOK defined.
Contents:
ApiLog - API logging DLL for KernelEx Core API hook infrastructure
DebugWindow - message receiver in ApiLog output to window mode