📄 breakpointserv.c
字号:
///////////////////////////////////////////////////////////////////////////////
//
// FileName : BreakPointServ.c
// Version : 0.10
// Author : Luo Cong
// Date : 2004-09-02 (yyyy-mm-dd)
// Comment :
//
///////////////////////////////////////////////////////////////////////////////
#include <windows.h>
#include <stdio.h>
#include "Misc.h"
#include "BreakPointServ.h"
#include "PEServ.h"
#include "MemServ.h"
#include "StackServ.h"
#include "LogServ.h"
#include "disasm.h"
const FUNCTION_BREAKPOINT g_FuncBP[] =
{
{"CreateFileA", FN_CREATEFILEA},
{"DeleteFileA", FN_DELETEFILEA},
{"CopyFileA", FN_COPYFILEA},
{"RegCreateKeyA", FN_REGCREATEKEYA},
{"RegCreateKeyExA", FN_REGCREATEKEYEXA},
{"RegDeleteKeyA", FN_REGDELETEKEYA},
{"RegSetValueA", FN_REGSETVALUEA},
{"RegSetValueExA", FN_REGSETVALUEEXA},
};
const int g_nFuncBPCount = sizeof(g_FuncBP) / sizeof(FUNCTION_BREAKPOINT);
BPDATA g_bpData[MAXBREAKPOINTCOUNT] = { 0 };
static const int g_nBPDATACount = sizeof(g_bpData) / sizeof(BPDATA);
/**
* Attention: nNum must start from 1
*/
int SetBreakPoint(
/* [in] */ const HANDLE hProcess,
/* [in] */ const LPVOID lpAddr,
#ifdef _MY_DEBUG
/* [in] */ const char szFuncName[],
#endif
/* [in] */ const FUNCTION_NAME fnFuncName,
/* [in] */ const int nNum
)
{
int nRetResult = 0;
int nRetCode;
unsigned char byTemp;
unsigned long ulNewProt;
unsigned long ulOldProt;
if (nNum >= g_nBPDATACount)
goto Exit0;
nRetCode = VirtualProtectEx(
hProcess,
lpAddr,
1,
PAGE_EXECUTE_READWRITE,
&ulOldProt
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = ReadProcessMemory(hProcess, lpAddr, &byTemp, 1, NULL);
MY_PROCESS_ERROR(nRetCode);
g_bpData[nNum].lpAddr = lpAddr;
g_bpData[nNum].byData = byTemp;
g_bpData[nNum].fnFuncName = fnFuncName;
#ifdef _MY_DEBUG
strcpy(g_bpData[nNum].szFuncName, szFuncName);
#endif
byTemp = 0xcc;
nRetCode = WriteProcessMemory(hProcess, lpAddr, &byTemp, 1, NULL);
MY_PROCESS_ERROR(nRetCode);
nRetResult = 1;
Exit0:
VirtualProtectEx(hProcess, lpAddr, 1, ulOldProt, &ulNewProt);
return nRetResult;
}
/**
* Attention: nNum must start from 1
*/
int RemoveBreakPoint(
/* [in] */ const HANDLE hProcess,
/* [in] */ const int nNum
)
{
int nRetResult = 0;
int nRetCode;
unsigned char byTemp;
unsigned long ulNewProt;
unsigned long ulOldProt;
LPVOID lpAddr = g_bpData[nNum].lpAddr;
if (nNum >= g_nBPDATACount)
goto Exit0;
nRetCode = VirtualProtectEx(
hProcess,
lpAddr,
1,
PAGE_EXECUTE_READWRITE,
&ulOldProt
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = ReadProcessMemory(hProcess, lpAddr, &byTemp, 1, NULL);
MY_PROCESS_ERROR(nRetCode);
nRetCode = (byTemp == 0xcc);
MY_PROCESS_ERROR(nRetCode);
nRetCode = WriteProcessMemory(
hProcess,
lpAddr,
&g_bpData[nNum].byData,
1,
NULL
);
if (nRetCode)
ZeroMemory(&g_bpData[nNum], sizeof(BPDATA));
else
goto Exit0;
nRetResult = 1;
Exit0:
VirtualProtectEx(hProcess, lpAddr, 1, ulOldProt, &ulNewProt);
return nRetResult;
}
int GetBreakPointIndex(
/* [in] */ const LPVOID lpAddr
)
{
int nBPIndex = 0;
int i;
for (i = 1; i < g_nBPDATACount; ++i)
{
if (lpAddr == g_bpData[i].lpAddr)
{
nBPIndex = i;
break;
}
}
return nBPIndex;
}
int SetFunctionsBreakPoint(
/* [in] */ const HANDLE hProcess
)
{
int nRetResult = 0;
int nRetCode;
int i;
char cmd[MAXCMDSIZE];
unsigned long ulCmdSize;
t_disasm da;
unsigned long ulBase;
unsigned long ulSize;
unsigned long ulIndex = 0;
unsigned long ulCurEIP;
char szFuncName[FUNCTIONNAMELEN];
int nBPIndex = 1;
nRetCode = GetDisassemblerRange(&ulBase, &ulSize);
MY_PROCESS_ERROR(nRetCode);
while (ulIndex < ulSize)
{
ulCurEIP = ulBase + ulIndex;
nRetCode = ReadCommand(ulCurEIP, MAXCMDSIZE, cmd);
MY_PROCESS_ERROR(nRetCode);
ulCmdSize = Disasm(cmd, MAXCMDSIZE, ulCurEIP, &da, DISASM_CODE);
ulIndex += ulCmdSize;
nRetCode = GetImportFunctionName(ulCurEIP, szFuncName);
MY_PROCESS_ERROR(nRetCode);
if ('\0' != szFuncName[0])
{
for (i = 0; i < g_nFuncBPCount; ++i)
{
nRetCode = strcmp(g_FuncBP[i].szFuncName, szFuncName);
if (0 == nRetCode) // 0 == Found
{
nRetCode = SetBreakPoint(
hProcess,
(LPLONG)ulCurEIP,
#ifdef _MY_DEBUG
szFuncName,
#endif
g_FuncBP[i].fnFuncName,
nBPIndex++
);
MY_PROCESS_ERROR(nRetCode);
#ifdef _MY_DEBUG
printf(
"SetBreakPoint '%s' at 0x%08X\n",
g_FuncBP[i].szFuncName,
ulCurEIP
);
#endif
break;
}
}
}
}
nRetResult = 1;
Exit0:
return nRetResult;
}
int GetTextFromStack(
/* [in] */ const HANDLE hProcess,
/* [in] */ const unsigned long Esp,
/* [in] */ const int nNum, // Item's Number of stack, start from 1
/* [in] */ const unsigned int unBufSize,
/* [out] */ char *buf
)
{
int nRetResult = 0;
int nRetCode;
unsigned long ulTextAddress;
nRetCode = GetStackContents(
hProcess,
Esp + 4 * (nNum - 1),
&ulTextAddress
);
MY_PROCESS_ERROR(nRetCode);
if (0 == ulTextAddress)
{
buf[0] = '\0';
goto Exit1;
}
nRetCode = ReadProcessMemory(
hProcess,
(unsigned long *)ulTextAddress,
buf,
unBufSize,
NULL
);
MY_PROCESS_ERROR(nRetCode);
Exit1:
nRetResult = 1;
Exit0:
return nRetResult;
}
int GetULValueFromStack(
/* [in] */ const HANDLE hProcess,
/* [in] */ const unsigned long Esp,
/* [in] */ const int nNum, // Item's Number of stack, start from 1
/* [out] */ unsigned long *ulParamValue
)
{
int nRetResult = 0;
int nRetCode;
nRetCode = GetStackContents(
hProcess,
Esp + 4 * (nNum - 1),
ulParamValue
);
MY_PROCESS_ERROR(nRetCode);
nRetResult = 1;
Exit0:
return nRetResult;
}
int AnalyzeBreakPointAndWriteToLog(
/* [in] */ const HANDLE hProcess,
/* [in] */ const unsigned long Esp,
/* [in] */ const FUNCTION_NAME fnFuncName
)
{
int nRetResult = 0;
int nRetCode;
int nReady = 1;
int nLogLen = 0;
char buf1[MAX_PATH] = { 0 };
char buf2[MAX_PATH] = { 0 };
unsigned long ulParamValue;
char log[1024] = { 0 };
switch (fnFuncName)
{
case FN_CREATEFILEA:
nRetCode = GetTextFromStack(
hProcess,
Esp,
1,
MAX_PATH,
buf1
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = GetULValueFromStack(
hProcess,
Esp,
5, // DWORD dwCreationDisposition, // how to create
&ulParamValue
);
MY_PROCESS_ERROR(nRetCode);
if (
(ulParamValue == CREATE_NEW) ||
(ulParamValue == CREATE_ALWAYS)
)
{
sprintf(log, "创建文件 %s 。\n", buf1);
#ifdef _DEBUG
printf("CreateFile(): %s\n", buf1);
#endif
}
break;
case FN_DELETEFILEA:
nRetCode = GetTextFromStack(
hProcess,
Esp,
1,
MAX_PATH,
buf1
);
MY_PROCESS_ERROR(nRetCode);
sprintf(log, "删除文件 %s 。\n", buf1);
#ifdef _DEBUG
printf("DeleteFile(): %s\n", buf1);
#endif
break;
case FN_COPYFILEA:
nRetCode = GetTextFromStack(
hProcess,
Esp,
1,
MAX_PATH,
buf1
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = GetTextFromStack(
hProcess,
Esp,
2,
MAX_PATH,
buf2
);
MY_PROCESS_ERROR(nRetCode);
sprintf(log, "拷贝文件 %s 到 %s 。\n", buf1, buf2);
#ifdef _DEBUG
printf("CopyFile(): %s to %s\n", buf1, buf2);
#endif
break;
case FN_REGCREATEKEYEXA:
case FN_REGCREATEKEYA:
nRetCode = GetTextFromStack(
hProcess,
Esp,
2,
MAX_PATH,
buf1
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = GetULValueFromStack(
hProcess,
Esp,
1,
&ulParamValue
);
MY_PROCESS_ERROR(nRetCode);
switch (ulParamValue)
{
case HKEY_CLASSES_ROOT:
nLogLen = sprintf(log, "创建注册表主键 HKEY_CLASSES_ROOT");
break;
case HKEY_CURRENT_CONFIG:
nLogLen = sprintf(log, "创建注册表主键 HKEY_CURRENT_CONFIG");
break;
case HKEY_CURRENT_USER:
nLogLen = sprintf(log, "创建注册表主键 HKEY_CURRENT_USER");
break;
case HKEY_LOCAL_MACHINE:
nLogLen = sprintf(log, "创建注册表主键 HKEY_LOCAL_MACHINE");
break;
case HKEY_USERS:
nLogLen = sprintf(log, "创建注册表主键 HKEY_USERS");
break;
case HKEY_PERFORMANCE_DATA:
nLogLen = sprintf(log, "创建注册表主键 HKEY_PERFORMANCE_DATA");
break;
case HKEY_DYN_DATA:
nLogLen = sprintf(log, "创建注册表主键 HKEY_DYN_DATA");
break;
default:
nReady = 0;
nLogLen = 0;
break;
}
sprintf(log + nLogLen, "\\%s 。\n", buf1);
#ifdef _DEBUG
printf("RegCreateKey(Ex)(): %s\n", buf1);
#endif
break;
case FN_REGDELETEKEYA:
nRetCode = GetTextFromStack(
hProcess,
Esp,
2,
MAX_PATH,
buf1
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = GetULValueFromStack(
hProcess,
Esp,
1,
&ulParamValue
);
MY_PROCESS_ERROR(nRetCode);
switch (ulParamValue)
{
case HKEY_CLASSES_ROOT:
nLogLen = sprintf(log, "删除注册表主键 HKEY_CLASSES_ROOT");
break;
case HKEY_CURRENT_CONFIG:
nLogLen = sprintf(log, "删除注册表主键 HKEY_CURRENT_CONFIG");
break;
case HKEY_CURRENT_USER:
nLogLen = sprintf(log, "删除注册表主键 HKEY_CURRENT_USER");
break;
case HKEY_LOCAL_MACHINE:
nLogLen = sprintf(log, "删除注册表主键 HKEY_LOCAL_MACHINE");
break;
case HKEY_USERS:
nLogLen = sprintf(log, "删除注册表主键 HKEY_USERS");
break;
case HKEY_PERFORMANCE_DATA:
nLogLen = sprintf(log, "删除注册表主键 HKEY_PERFORMANCE_DATA");
break;
case HKEY_DYN_DATA:
nLogLen = sprintf(log, "删除注册表主键 HKEY_DYN_DATA");
break;
default:
nReady = 0;
nLogLen = 0;
break;
}
sprintf(log + nLogLen, "\\%s 。\n", buf1);
#ifdef _DEBUG
printf("RegDeleteKey(): %s\n", buf1);
#endif
break;
case FN_REGSETVALUEEXA:
case FN_REGSETVALUEA:
nRetCode = GetTextFromStack(
hProcess,
Esp,
2,
MAX_PATH,
buf1
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = GetTextFromStack(
hProcess,
Esp,
4,
MAX_PATH,
buf2
);
MY_PROCESS_ERROR(nRetCode);
nRetCode = GetULValueFromStack(
hProcess,
Esp,
1,
&ulParamValue
);
MY_PROCESS_ERROR(nRetCode);
switch (ulParamValue)
{
case HKEY_CLASSES_ROOT:
nLogLen = sprintf(log, "修改注册表键值 HKEY_CLASSES_ROOT");
break;
case HKEY_CURRENT_CONFIG:
nLogLen = sprintf(log, "修改注册表键值 HKEY_CURRENT_CONFIG");
break;
case HKEY_CURRENT_USER:
nLogLen = sprintf(log, "修改注册表键值 HKEY_CURRENT_USER");
break;
case HKEY_LOCAL_MACHINE:
nLogLen = sprintf(log, "修改注册表键值 HKEY_LOCAL_MACHINE");
break;
case HKEY_USERS:
nLogLen = sprintf(log, "修改注册表键值 HKEY_USERS");
break;
case HKEY_PERFORMANCE_DATA:
nLogLen = sprintf(log, "修改注册表键值 HKEY_PERFORMANCE_DATA");
break;
case HKEY_DYN_DATA:
nLogLen = sprintf(log, "修改注册表键值 HKEY_DYN_DATA");
break;
default:
nReady = 0;
nLogLen = 0;
break;
}
sprintf(log + nLogLen, "\\%s 为 %s 。\n", buf1, buf2);
#ifdef _DEBUG
printf("RegSetValue(Ex)(): %s : %s\n", buf1, buf2);
#endif
break;
}
if (nReady && ('\0' != log[0]))
AddToLogTail(log);
nRetResult = 1;
Exit0:
return nRetResult;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -