⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 hexview.c

📁 直接IRP操作文件的实现问题
💻 C
📖 第 1 页 / 共 3 页
字号:
#include <windows.h>
#include "hexview.h"

#define xmalloc(s)		HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (s))
#define xfree(p)		HeapFree(GetProcessHeap(), 0, (p))
#define MAX(a, b) ((a) > (b) ? (a) : (b))
#define MIN(a, b) ((a) < (b) ? (a) : (b))

#define EM_TEXT 0
#define EM_HEX_HIGH 1
#define EM_HEX_LOW 2
#define GWL_HEXINFO 0
#define WM_MOUSEWHEEL 0x020A

#define HV_COLOR_DEFAULT 0
#define HV_COLOR_RED 1
#define HV_COLOR_SBGRAY 2
#define HV_COLOR_GREEN 3
#define HV_COLOR_BLUE 4

typedef struct _HV_PRINTFMT
{
	BYTE x;
	BYTE y;
	BYTE color : 7;
	BYTE highlight : 1;
	BYTE len;
	BYTE data[];
} HV_PRINTFMT, *PHV_PRINTFMT;

typedef struct _HV_MODIFYLOG
{
	int nLog;
	int nBack;
	int nMaxUndoLog;
	int nMaxRedoLog;
	PBYTE pLog;
	PBYTE pLogBuf;
	DWORD nLogBufLen;
	DWORD nMaxLogBuf;
	PBYTE pOrgBuf;
	DWORD nOrgBufLen;
} HV_MODIFYLOG, *PHV_MODIFYLOG;

typedef struct _HEXVIEW
{
	BOOL TextOnly;
	BOOL ReadOnly;
	BOOL NoCursor;
	PBYTE Buffer;
	DWORD Length;
	DWORD BaseAddress;
	ULONG SelStart;
	ULONG SelEnd;
	DWORD PageOffset;
	DWORD PageLength;
	DWORD PageMaxLength;
	UINT LineWidth;
	UINT AddressWidth;
	UINT CharWidth;
	UINT CharHeight;
	DWORD EditMode;
	int Cursor;
	HV_MODIFYLOG hv_modl;
	DWORD color[10];
} HEXVIEW, *PHEXVIEW;

void *HV_MemSearchR(void *m1, size_t n1, void *m2, size_t n2)
{
	unsigned char *s1 = m1;
	unsigned char *s2 = m2;
	size_t i, index[256];

	if (n1 < n2)
		return NULL;

	if (n2 == 0)
		return m1;

	for (i = 0; i < 256; i++)
		index[i] = n2 + 1;

	for (i = 0; i < n2; i++)
		index[s2[i]] = n2 - i;

	do
	{
		for (i = 0; s1[i] == s2[i]; i++)
		{
			if (i == n2 - 1)
				return s1;
		}

		s1 += index[s1[n2]];
	} while (s1 + n2 <= (char *)m1 + n1);

	return NULL;
}

void *HV_MemSearchL(void *m1, size_t n1, void *m2, size_t n2)
{
	unsigned char *s1 = m1;
	unsigned char *s2 = m2;
	size_t i, index[256];

	if (n1 < n2)
		return NULL;

	if (n2 == 0)
		return m1;

	for (i = 0; i < 256; i++)
		index[i] = n2 + 1;

	for (i = n2 - 1; i >= 0; i--)
		index[s2[i]] = n2 - i;

	do
	{
		for (i = n2 - 1; s1[i] == s2[i]; i--)
		{
			if (i == 0)
				return s1;
		}

		s1 -= index[*(s1 - 1)];
	} while (s1 >= (char *)m1 + n2);

	return NULL;
}

int HV_InitModifyLog(PHV_MODIFYLOG hv_modl, PBYTE pOrgBuf, DWORD pOrgLen)
{
	hv_modl->nLog = 0;
	hv_modl->nBack = 0;
	hv_modl->nMaxUndoLog = 0;
	hv_modl->nMaxRedoLog = 0;
	hv_modl->pOrgBuf = pOrgBuf;
	hv_modl->nOrgBufLen = pOrgLen;
	hv_modl->nMaxLogBuf = 0x200000;
	hv_modl->nLogBufLen = 0x8000;
	hv_modl->pLogBuf = VirtualAlloc(NULL, hv_modl->nMaxLogBuf, MEM_RESERVE, PAGE_READWRITE);
	hv_modl->pLog = hv_modl->pLogBuf;

	if (hv_modl->pLogBuf == NULL)
		return -1;

	VirtualAlloc(hv_modl->pLogBuf, hv_modl->nLogBufLen, MEM_COMMIT, PAGE_READWRITE);

	return 0;
}

int HV_AddModifyLog(PHV_MODIFYLOG hv_modl, DWORD offset, DWORD length, PBYTE pData)
{//*
	int n;
	PBYTE p;
	DWORD l;

	if (hv_modl->nLog < 0)
	{
		hv_modl->nBack += -hv_modl->nLog;
		hv_modl->nMaxUndoLog -= -hv_modl->nLog;
		hv_modl->nLog = 0;
	}

	p = hv_modl->pLog;
	n = hv_modl->nLog;

	for (; n > 0; n--)
		p += *(PDWORD)p + sizeof(DWORD) + sizeof(DWORD);

	if (hv_modl->nLogBufLen - (p - hv_modl->pLogBuf) < length + sizeof(DWORD) + sizeof(DWORD))
	{
		l = MAX(0x8000, length + sizeof(DWORD) + sizeof(DWORD));
		l = (l + 0x7fff) & ~0x7fff;

		if (hv_modl->nLogBufLen + l > hv_modl->nMaxLogBuf)
			return -1;

		hv_modl->nLogBufLen += l;
		VirtualAlloc(hv_modl->pLogBuf, hv_modl->nLogBufLen, MEM_COMMIT, PAGE_READWRITE);
	}

	*((PDWORD)p)++ = length;
	*((PDWORD)p)++ = offset;
	memcpy(p, pData, length);

	hv_modl->nLog++;
	hv_modl->nMaxRedoLog = hv_modl->nLog;//*/

	return 0;
}

int HV_GetModifyData(PHV_MODIFYLOG hv_modl, DWORD nStart, PBYTE pBuffer, DWORD nSize)
{
	int n, x;
	PBYTE pUndoLog = hv_modl->pLog;
	PBYTE pRedoLog = hv_modl->pLog;
	DWORD off, len;
	DWORD nEnd = nStart + nSize;

	if (hv_modl->nLog > hv_modl->nMaxRedoLog || hv_modl->nLog < hv_modl->nMaxUndoLog)
		return -1;

	x = MIN(hv_modl->nOrgBufLen - nStart, nSize);
	memcpy(pBuffer, hv_modl->pOrgBuf + nStart, x);		//拷贝原始数据

	for (n = 0; n < hv_modl->nBack; n++)
	{
		len = *((PDWORD)pUndoLog - 1);
		off = *((PDWORD)pUndoLog - 2);
		pUndoLog -= len + sizeof(DWORD) + sizeof(DWORD);

		if (off >= nStart && off < nEnd)
		{
			int l = MIN(len, nSize - (off - nStart));
			memcpy(pBuffer + (off - nStart), pUndoLog, l);
		}
		else if (off >= nStart && off <= nEnd)
		{
			int l = MIN(nEnd - off, len);
			memcpy(pBuffer + off - nStart, pUndoLog, l);
		}
	}

	if (hv_modl->nLog >= 0)
	{
		for (n = 0; n < hv_modl->nLog; n++)
		{
			len = *((PDWORD)pRedoLog)++;
			off = *((PDWORD)pRedoLog)++;

			if (off >= nStart && off < nEnd)
			{
				int l = MIN(len, nSize - (off - nStart));
				memcpy(pBuffer + (off - nStart), pRedoLog, l);
			}
			else if (off >= nStart && off <= nEnd)
			{
				int l = MIN(nEnd - off, len);
				memcpy(pBuffer + off - nStart, pRedoLog, l);
			}

			pRedoLog += len;
		}
	}
	else
	{
		for (n = 0; n > hv_modl->nLog; n--)
		{
			len = *((PDWORD)pUndoLog - 1);
			off = *((PDWORD)pUndoLog - 2);
			pUndoLog -= len + sizeof(DWORD) + sizeof(DWORD);

			if (off >= nStart && off < nEnd)
			{
				int l = MIN(len, nSize - (off - nStart));
				memcpy(pBuffer + (off - nStart), pUndoLog, l);
			}
			else if (off >= nStart && off <= nEnd)
			{
				int l = MIN(nEnd - off, len);
				memcpy(pBuffer + off - nStart, pUndoLog, l);
			}
		}
	}

	return x;//*/
}

void HV_ApplyModifyLog(PHV_MODIFYLOG hv_modl, PBYTE pNewBuffer)
{
	int i, j;
	PBYTE pUndoLog = hv_modl->pLog;
	PBYTE pRedoLog = hv_modl->pLog;

	if (pNewBuffer)
	{
		memcpy(pNewBuffer, hv_modl->pOrgBuf, hv_modl->nOrgBufLen);
		hv_modl->pOrgBuf = pNewBuffer;
	}

	if (hv_modl->nLog == 0 && hv_modl->nBack == 0)
		return;

	for (i = 0; i < hv_modl->nBack; i++)
	{
		DWORD len = *((PDWORD)pUndoLog - 1);
		DWORD off = *((PDWORD)pUndoLog - 2);

		pUndoLog -= sizeof(DWORD) + sizeof(DWORD) + len;

		for (j = 0; (DWORD)j < len; j++)
			hv_modl->pOrgBuf[off + j] = pUndoLog[j];
	}

	if (hv_modl->nLog >= 0)
	{
		for (i = 0 ; i < hv_modl->nLog; i++)
		{
			DWORD len = *((PDWORD)pRedoLog)++;
			DWORD off = *((PDWORD)pRedoLog)++;

			for (j = 0; (DWORD)j < len; j++)
			{
				pUndoLog[j] = hv_modl->pOrgBuf[off + j];
				hv_modl->pOrgBuf[off + j] = pRedoLog[j];
			}

			pUndoLog += len;
			pRedoLog += len;
			*((PDWORD)pUndoLog)++ = off;
			*((PDWORD)pUndoLog)++ = len;
		}
	}
	else
	{
		for (i = 0 ; i > hv_modl->nLog; i--)
		{
			DWORD len = *--((PDWORD)pUndoLog);
			DWORD off = *--((PDWORD)pUndoLog);

			pUndoLog -= len;
			pRedoLog -= len;

			for (j = 0; (DWORD)j < len; j++)
			{
				pRedoLog[j] = hv_modl->pOrgBuf[off + j];
				hv_modl->pOrgBuf[off + j] = pUndoLog[j];
			}

			*--((PDWORD)pRedoLog) = off;
			*--((PDWORD)pRedoLog) = len;
		}
	}

	hv_modl->pLog = pUndoLog;
	hv_modl->nMaxRedoLog -= hv_modl->nLog;
	hv_modl->nMaxUndoLog += -hv_modl->nLog;
	hv_modl->nLog = 0;
	hv_modl->nBack = 0;
}

int HV_DelModifyLog(PHV_MODIFYLOG hv_modl)
{
	if (hv_modl->nLog < 0)
	{
		PBYTE p = hv_modl->pLog;
		int i, j;

		for (i = hv_modl->nLog; i < 0; i++)
		{
			DWORD len = *((PDWORD)p - 1);
			DWORD off = *((PDWORD)p - 2);

			p -= sizeof(DWORD) + sizeof(DWORD) + len;

			for (j = len; j > 0; j--)
				p[sizeof(DWORD) + sizeof(DWORD) + j] = p[j];

			*((PDWORD)p + 0) = len;
			*((PDWORD)p + 1) = off;
		}

		hv_modl->pLog = p;
		hv_modl->nMaxRedoLog = -hv_modl->nLog;
		hv_modl->nMaxUndoLog -= hv_modl->nLog;
		hv_modl->nLog = 0;
	}
	else
	{
		hv_modl->nMaxRedoLog = hv_modl->nLog;
	}

	return 0;
}

void HV_FreeModifyLog(PHV_MODIFYLOG hv_modl)
{
	hv_modl->nLog = 0;
	hv_modl->nBack = 0;
	hv_modl->nMaxUndoLog = 0;
	hv_modl->nMaxRedoLog = 0;
	hv_modl->pLog = NULL;
	hv_modl->pOrgBuf = NULL;
	hv_modl->nOrgBufLen = 0;
	hv_modl->nMaxLogBuf = 0;
	hv_modl->nLogBufLen = 0;
	VirtualFree(hv_modl->pLogBuf, 0, MEM_RELEASE);
	hv_modl->pLogBuf = NULL;
}

void HV_ResetModifyLog(PHV_MODIFYLOG hv_modl, PBYTE pOrgBuf, DWORD pOrgLen)
{
	hv_modl->nLog = 0;
	hv_modl->nBack = 0;
	hv_modl->nMaxUndoLog = 0;
	hv_modl->nMaxRedoLog = 0;
	hv_modl->pOrgBuf = pOrgBuf;
	hv_modl->nOrgBufLen = pOrgLen;
}

int HV_LogUndo(HWND hWnd, BOOL bTest)
{
	PHEXVIEW p = (PHEXVIEW)GetWindowLong(hWnd, GWL_HEXINFO);
	NMHDR n;

	if (p->hv_modl.nLog > p->hv_modl.nMaxUndoLog)
	{
		if (bTest == TRUE)
			return 1;
		else
		{
			p->hv_modl.nLog--;
			RedrawWindow(hWnd, NULL, 0, RDW_INVALIDATE);
			n.code = HV_EN_CHANGE;
			n.idFrom = GetDlgCtrlID(hWnd);
			n.hwndFrom = hWnd;
			SendMessage(GetParent(hWnd), WM_NOTIFY, GetDlgCtrlID(hWnd), (LPARAM)&n);
			return 1;
		}
	}

	return 0;
}

int HV_LogRedo(HWND hWnd, BOOL bTest)
{
	PHEXVIEW p = (PHEXVIEW)GetWindowLong(hWnd, GWL_HEXINFO);
	NMHDR n;

	if (p->hv_modl.nLog < p->hv_modl.nMaxRedoLog)
	{
		if (bTest == TRUE)
			return 1;
		else
		{
			p->hv_modl.nLog++;
			RedrawWindow(hWnd, NULL, 0, RDW_INVALIDATE);
			n.code = HV_EN_CHANGE;
			n.idFrom = GetDlgCtrlID(hWnd);
			n.hwndFrom = hWnd;
			SendMessage(GetParent(hWnd), WM_NOTIFY, GetDlgCtrlID(hWnd), (LPARAM)&n);
			return 1;
		}
	}

	return 0;
}

int HV_Compare(PBYTE s1, PBYTE s2, int n)
{
	int i = n;

	if (*s1 == *s2)
	{
		while (--n && *++s1 == *++s2);
		return i - n;
	}
	else
	{
		while (--n && *++s1 != *++s2);
		return n - i;
	}
}

void HV_FormatForPrint(int lineWidth, int maxLine, DWORD startAddr, PVOID allModify, PBYTE data,
					   DWORD selStart, DWORD selEnd, PBYTE output)
{
	PHV_PRINTFMT hv_pfmt;
	PBYTE buf = output;
	BYTE text[64 * 32];
	int i, j, k, l, w, dlen;
	BOOL bModify, bHighLight;

	lineWidth = MAX(lineWidth, 1);
	lineWidth = MIN(lineWidth, 32);
	maxLine = MAX(maxLine, 1);
	maxLine = MIN(maxLine, 64);

	dlen = HV_GetModifyData(allModify, startAddr, text, lineWidth * maxLine);

	maxLine = dlen / lineWidth;
	maxLine += (dlen % lineWidth) == 0 ? 0 : 1;
	w = lineWidth;

	for (i = 0; i < maxLine; i++)
	{
		hv_pfmt = (PHV_PRINTFMT)buf;				//输出地址
		hv_pfmt->x = 1;
		hv_pfmt->y = i;
		hv_pfmt->color = HV_COLOR_ADDR;
		hv_pfmt->highlight = 0;
		hv_pfmt->len = 8;
		buf += sizeof(HV_PRINTFMT);

		for (l = 3; l >= 0; l--)
		{
			*buf++ = "0123456789ABCDEF"[(startAddr >> (l * 8 + 4)) & 15];
			*buf++ = "0123456789ABCDEF"[(startAddr >> (l * 8 + 0)) & 15];
		}

		if (i == maxLine - 1)
		{
			if (dlen % lineWidth)
				w = dlen % lineWidth;
		}

		for (j = 0; j < w; j += k)
		{
			k = HV_Compare(data + startAddr + j, text + i * lineWidth + j, w - j);

			if (k > 0)
			{
				bModify = FALSE;
			}
			else
			{
				bModify = TRUE;
				k = -k;
			}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -