EXE和SYS基于事件同步消息通知

#ifndef _HEADER_HEAD_FILE
#define _HEADER_HEAD_FILE
#pragma once
#include <ntifs.h>
#include <ntddk.h>

#ifndef MAX_PATH
#define MAX_PATH	260
#endif



NTKERNELAPI UCHAR * PsGetProcessImageFileName(__in PEPROCESS Process);



//驱动控制代码
#define IOCTL_START CTL_CODE(FILE_DEVICE_UNKNOWN, 0x810,METHOD_BUFFERED, FILE_ANY_ACCESS)
#define IOCTL_STOP CTL_CODE(FILE_DEVICE_UNKNOWN, 0x811,METHOD_BUFFERED, FILE_ANY_ACCESS)
#define IOCTL_GET_DATA CTL_CODE(FILE_DEVICE_UNKNOWN, 0x812,METHOD_BUFFERED, FILE_ANY_ACCESS)

#endif


#include "Header.h"





//同步事件对象
PRKEVENT g_pEventObject = NULL;
//句柄信息
OBJECT_HANDLE_INFORMATION g_ObjectHandleInfo;

char g_szOutBuf[MAX_PATH] = { 0 };



//获取进程名
PCHAR GetProcessName16ByProcessId(HANDLE ProcessId)
{
	//定义变量
	NTSTATUS status = STATUS_UNSUCCESSFUL;
	PEPROCESS ProcessObj = NULL;
	PUCHAR ProcessName = NULL;

	//进程ID和返回一个引用指针的过程EPROCESS结构
	status = PsLookupProcessByProcessId(ProcessId, &ProcessObj);
	if (NT_SUCCESS(status))
	{
		// ImageFileName    : [16]  "SogouExplorer.e"
		//使用这个函数,只能获取进程名称是16的长度,后面的被截取了。。。
		ProcessName = PsGetProcessImageFileName(ProcessObj);
		ObfDereferenceObject(ProcessObj);
	}

	return ProcessName;
}



VOID CreateProcessNotifyFunction(IN HANDLE  ParentId, IN HANDLE  ProcessId, IN BOOLEAN  Create)
{
	if (Create)
	{
		char* pName=GetProcessName16ByProcessId(ProcessId);
		if (pName)
		{
			RtlZeroMemory(g_szOutBuf, sizeof(g_szOutBuf));
			RtlCopyMemory(g_szOutBuf, pName, strlen(pName)+1);

			//设置事件为有信号,通知应用层
			KeSetEvent(g_pEventObject, 0, FALSE);
		}

	}

	return;
}


VOID DriverUnload(DRIVER_OBJECT *DriverObject)
{
	PsSetCreateProcessNotifyRoutine(CreateProcessNotifyFunction, TRUE);
	UNICODE_STRING Win32Device;
	RtlInitUnicodeString(&Win32Device, L"\\DosDevices\\KernelHandle");
	IoDeleteSymbolicLink(&Win32Device);
	IoDeleteDevice(DriverObject->DeviceObject);
	return;
}

NTSTATUS KernelHandleCreate(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
	Irp->IoStatus.Status = STATUS_SUCCESS;
	Irp->IoStatus.Information = 0;
	IoCompleteRequest(Irp, IO_NO_INCREMENT);
	return STATUS_SUCCESS;
}

NTSTATUS KernelHandleClose(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
	Irp->IoStatus.Status = STATUS_NOT_SUPPORTED;
	Irp->IoStatus.Information = 0;
	IoCompleteRequest(Irp, IO_NO_INCREMENT);
	return Irp->IoStatus.Status;
}

NTSTATUS KernelHandleDefaultHandler(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
	NTSTATUS status = STATUS_SUCCESS;
	ULONG ulReturn = 0;
	PIO_STACK_LOCATION stack = IoGetCurrentIrpStackLocation(Irp);
	ULONG ulCtrlCode = stack->Parameters.DeviceIoControl.IoControlCode;
	PVOID InputBuffer = (PVOID)Irp->AssociatedIrp.SystemBuffer;
	PVOID OutputBuffer = (PVOID)Irp->AssociatedIrp.SystemBuffer;
	ULONG ulInputBufferSize = stack->Parameters.DeviceIoControl.InputBufferLength;
	ULONG ulOutputBufferSize = stack->Parameters.DeviceIoControl.OutputBufferLength;

	switch (ulCtrlCode)
	{
	case IOCTL_START:
	{
		//设置同步事件
		if (InputBuffer == NULL || ulInputBufferSize < sizeof(HANDLE))
		{
			KdPrint(("Set Event Error~!\n"));
			break;
		}

		//取得句柄对象
		HANDLE hEvent = *(HANDLE*)InputBuffer;
		status = ObReferenceObjectByHandle(hEvent, GENERIC_ALL, NULL, KernelMode, (PVOID*)&g_pEventObject, &g_ObjectHandleInfo);
		PsSetCreateProcessNotifyRoutine(CreateProcessNotifyFunction, FALSE);
		break;
	}
	case IOCTL_STOP:
	{
	
		//移除进程创建通知函数
		PsSetCreateProcessNotifyRoutine(CreateProcessNotifyFunction, TRUE);
		//释放对象引用
		if (g_pEventObject != NULL)
		{
			ObDereferenceObject(g_pEventObject);
			g_pEventObject = NULL;
		}

		break;
	}
	case IOCTL_GET_DATA:
	{
		int nLength = strlen(g_szOutBuf)+1;
		if (OutputBuffer == NULL && ulOutputBufferSize < nLength)
		{
			KdPrint(("OutputBufferSize is too small ~!\n"));
			break;
		}

		//复制进程到输出缓冲区
		RtlCopyBytes((PCHAR)OutputBuffer, g_szOutBuf, nLength);

		break;
	}
	default:
		break;
	}


	Irp->IoStatus.Status = STATUS_SUCCESS;
	Irp->IoStatus.Information = ulOutputBufferSize;
	IoCompleteRequest(Irp, IO_NO_INCREMENT);
	return Irp->IoStatus.Status;
}

NTSTATUS DriverEntry(_In_ PDRIVER_OBJECT DriverObject, _In_ PUNICODE_STRING RegistryPath)
{
	NTSTATUS status;
	PDEVICE_OBJECT DeviceObject = NULL;
	UNICODE_STRING DeviceName;
	UNICODE_STRING Win32Device;

	KdBreakPoint();
	DriverObject->DriverUnload = DriverUnload;
	RtlInitUnicodeString(&DeviceName, L"\\Device\\KernelHandle");
	RtlInitUnicodeString(&Win32Device, L"\\DosDevices\\KernelHandle");

	DriverObject->MajorFunction[IRP_MJ_CREATE] = KernelHandleCreate;
	DriverObject->MajorFunction[IRP_MJ_CLOSE] = KernelHandleClose;
	DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = KernelHandleDefaultHandler;



	status = IoCreateDevice(DriverObject,0,&DeviceName,FILE_DEVICE_UNKNOWN,0,FALSE,&DeviceObject);
	if (!NT_SUCCESS(status))
		return status;
	if (!DeviceObject)
		return STATUS_UNEXPECTED_IO_ERROR;
	DeviceObject->Flags |= DO_DIRECT_IO;
	DeviceObject->AlignmentRequirement = FILE_WORD_ALIGNMENT;
	status = IoCreateSymbolicLink(&Win32Device, &DeviceName);
	DeviceObject->Flags &= ~DO_DEVICE_INITIALIZING;

	return STATUS_SUCCESS;
}





#include <windows.h>
#include <tchar.h>
#include <stdio.h>


HANDLE hDevice;
HANDLE g_hKernelEvent = NULL;

//驱动控制代码
#define IOCTL_START CTL_CODE(FILE_DEVICE_UNKNOWN, 0x810,METHOD_BUFFERED, FILE_ANY_ACCESS)
#define IOCTL_STOP CTL_CODE(FILE_DEVICE_UNKNOWN, 0x811,METHOD_BUFFERED, FILE_ANY_ACCESS)
#define IOCTL_GET_DATA CTL_CODE(FILE_DEVICE_UNKNOWN, 0x812,METHOD_BUFFERED, FILE_ANY_ACCESS)


DWORD WINAPI ThreadProc(LPVOID lpParameter)
{
	printf("线程开始运行\n");

	DWORD dwRet;
	char szBuffer[MAX_PATH] = { 0 };

	while (WaitForSingleObject(g_hKernelEvent, INFINITE) == WAIT_OBJECT_0)
	{
		printf("收到状态\n");

		//等待完成,向驱动发送请求
		DeviceIoControl(hDevice,IOCTL_GET_DATA, NULL, 0, szBuffer, MAX_PATH, &dwRet,NULL);

		printf("从内核发来的信息是:%s\n", szBuffer);

		//设置同步事件为无信号,等待下一次通知
		ResetEvent(g_hKernelEvent);
	}

	printf("线程结束\n");
	return 0;
}





int main(void)
{

	//创建手动重置的事件
	g_hKernelEvent = CreateEvent(NULL, TRUE, FALSE, NULL);


	//打开驱动的符号链接
	hDevice = CreateFile(L"\\\\.\\KernelHandle", GENERIC_READ | GENERIC_WRITE, 0,NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);

	if (INVALID_HANDLE_VALUE == hDevice)
	{
		printf("CreateFile fail!\n");
		getchar();
		getchar();
		return FALSE;
	}
	DWORD dwRet;
	DeviceIoControl(hDevice, IOCTL_START, &g_hKernelEvent, sizeof(g_hKernelEvent), NULL, NULL, &dwRet, NULL);


	HANDLE hThread =CreateThread(NULL, NULL, ThreadProc, NULL, NULL, NULL);
	CloseHandle(hThread);


	getchar();
	getchar();

	DeviceIoControl(hDevice, IOCTL_STOP, NULL, 0, NULL, NULL, &dwRet, NULL);
	CloseHandle(hDevice);
	return 0;
}



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值