用Visual studio2012在Windows8上开发内核驱动监视进程创建

               

在Windows NT中,80386保护模式的“保护”比Windows 95中更坚固,这个“镀金的笼子”更加结实,更加难以打破。在Windows 95中,至少应用程序I/O操作是不受限制的,而在Windows NT中,我们的应用程序连这点权限都被剥夺了。在NT中几乎不太可能进入真正的ring0层。 
在Windows NT中,存在三种Device Driver:

  1.“Virtual device Driver” (VDD)。通过VDD,16位应用程序,如DOS 和Win16应用程序可以访问特定的I/O端口(注意,不是直接访问,而是要通过VDD来实现访问)。

  2.“GDI Driver”,提供显示和打印所需的GDI函数。

  3.“Kernel Mode Driver”,实现对特定硬件的操作,比如说CreateFile, CloseHandle (对于文件对象而言), ReadFile, WriteFile, DeviceIoControl 等操作。“Kernel Mode Driver”还是Windows NT中唯一可以对硬件中断和DMA进行操作的Driver。SCSI 小端口驱动和 网卡NDIS 驱动都是Kernel Mode Driver的一种特殊形式。

Visual studio2012与Windows8带来格外不同的新体验

1.启动Vs2012


2.看见满目的驱动开发模板

3.选择一个驱动模式,有内核模式与用户模式两种的驱动

4.创建一个驱动程序,KMDF DriverMVP

5.我们选择的是内核模式的驱动程序,下面是创建成功后的界面,分别是驱动程序本身,与驱动安装包

6.按下F5,选择驱动编译,


插入下列代码实现内核的进程创建

#include "ProcMon.h"#include "../inc/ioctls.h"////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 全局变量//PDEVICE_OBJECT g_pDeviceObject;////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 函数实现//NTSTATUSDriverEntry( IN PDRIVER_OBJECT  DriverObject, IN PUNICODE_STRING  RegistryPath){ NTSTATUS   Status = STATUS_SUCCESS;     UNICODE_STRING  ntDeviceName; UNICODE_STRING  dosDeviceName; UNICODE_STRING  ProcessEventString; PDEVICE_EXTENSION deviceExtension; PDEVICE_OBJECT  deviceObject = NULL;  KdPrint(("[ProcMon] DriverEntry: %wZ\n", RegistryPath));  // // 创建设备对象 // RtlInitUnicodeString(&ntDeviceName, PROCMON_DEVICE_NAME_W);  Status = IoCreateDevice(      DriverObject,       sizeof(DEVICE_EXTENSION),  // DeviceExtensionSize      &ntDeviceName,     // DeviceName      FILE_DEVICE_PROCMON,   // DeviceType      0,        // DeviceCharacteristics      TRUE,       // Exclusive      &deviceObject     // [OUT]      ); if(!NT_SUCCESS(Status)) {  KdPrint(("[ProcMon] IoCreateDevice Error Code = 0x%X\n", Status));    return Status; }  // // 设置扩展结构 // deviceExtension = (PDEVICE_EXTENSION)deviceObject->DeviceExtension;  // // Set up synchronization objects, state info,, etc. // deviceObject->Flags |= DO_BUFFERED_IO;  // // 创建符号链接 // RtlInitUnicodeString(&dosDeviceName, PROCMON_DOS_DEVICE_NAME_W);  Status = IoCreateSymbolicLink(&dosDeviceName, &ntDeviceName);  if(!NT_SUCCESS(Status)) {  KdPrint(("[ProcMon] IoCreateSymbolicLink Error Code = 0x%X\n", Status));  IoDeleteDevice(deviceObject);    return Status; }  // // 分发IRP // DriverObject->MajorFunction[IRP_MJ_CREATE]   = ProcmonDispatchCreate; DriverObject->MajorFunction[IRP_MJ_CLOSE]   = ProcmonDispatchClose; DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = ProcmonDispatchDeviceControl; DriverObject->DriverUnload       = ProcmonUnload;  // // 保存设备对象指针 // g_pDeviceObject = deviceObject; // // 创建事件对象与应用层通信 // RtlInitUnicodeString(&ProcessEventString, EVENT_NAME);  deviceExtension->ProcessEvent = IoCreateNotificationEvent(&ProcessEventString, &deviceExtension->hProcessHandle); KeClearEvent(deviceExtension->ProcessEvent);   // 非受信状态 // // 设置回调例程 // Status = PsSetCreateProcessNotifyRoutine(ProcessCallback, FALSE); return Status;}NTSTATUSProcmonDispatchCreate( IN PDEVICE_OBJECT  DeviceObject, IN PIRP     Irp){ NTSTATUS Status = STATUS_SUCCESS;  Irp->IoStatus.Information = 0;  KdPrint(("[ProcMon] IRP_MJ_CREATE\n"));  Irp->IoStatus.Status = Status; IoCompleteRequest(Irp, IO_NO_INCREMENT);  return Status;}NTSTATUSProcmonDispatchClose( IN PDEVICE_OBJECT  DeviceObject, IN PIRP     Irp){ NTSTATUS Status = STATUS_SUCCESS;  Irp->IoStatus.Information = 0;  KdPrint(("[ProcMon] IRP_MJ_CLOSE\n"));  Irp->IoStatus.Status = Status; IoCompleteRequest(Irp, IO_NO_INCREMENT);  return Status;}NTSTATUSProcmonDispatchDeviceControl( IN PDEVICE_OBJECT  DeviceObject, IN PIRP     Irp){ NTSTATUS   Status = STATUS_SUCCESS; PIO_STACK_LOCATION irpStack; PDEVICE_EXTENSION deviceExtension; ULONG    inBufLength, outBufLength; ULONG    ioControlCode; PCALLBACK_INFO  pCallbackInfo;  // 获取当前设备栈 irpStack = IoGetCurrentIrpStackLocation(Irp); deviceExtension = (PDEVICE_EXTENSION)DeviceObject->DeviceExtension;  // 提取信息 pCallbackInfo = Irp->AssociatedIrp.SystemBuffer; inBufLength = irpStack->Parameters.DeviceIoControl.InputBufferLength; outBufLength = irpStack->Parameters.DeviceIoControl.OutputBufferLength; ioControlCode = irpStack->Parameters.DeviceIoControl.IoControlCode; // 处理不同的IOCTL switch (ioControlCode) { case IOCTL_PROC_MON:  {   KdPrint(("[ProcMon] IOCTL: 0x%X", ioControlCode));   if (outBufLength >= sizeof(PCALLBACK_INFO))   {    pCallbackInfo->hParentId = deviceExtension->hParentId;    pCallbackInfo->hProcessId = deviceExtension->hProcessId;    pCallbackInfo->bCreate = deviceExtension->bCreate;    Irp->IoStatus.Information = outBufLength;   }    break;  }   default:  {   Status = STATUS_INVALID_PARAMETER;   Irp->IoStatus.Information = 0;      KdPrint(("[ProcMon] Unknown IOCTL: 0x%X (%04X,%04X)", \     ioControlCode, DEVICE_TYPE_FROM_CTL_CODE(ioControlCode), \     IoGetFunctionCodeFromCtlCode(ioControlCode)));      break;  } }  Irp->IoStatus.Status = Status; IoCompleteRequest(Irp, IO_NO_INCREMENT);   return Status;}VOIDProcmonUnload( IN PDRIVER_OBJECT  DriverObject){ UNICODE_STRING dosDeviceName;  // // Free any resources // // 卸载回调例程 PsSetCreateProcessNotifyRoutine(ProcessCallback, TRUE);  // // Delete the symbolic link //  RtlInitUnicodeString(&dosDeviceName, PROCMON_DOS_DEVICE_NAME_W);  IoDeleteSymbolicLink(&dosDeviceName);  // // Delete the device object //  IoDeleteDevice(DriverObject->DeviceObject);  KdPrint(("[ProcMon] Unloaded"));}VOIDProcessCallback( IN HANDLE    ParentId,   // 父进程ID IN HANDLE    ProcessId,   // 发生事件的进程ID IN BOOLEAN    Create    // 进程是创建还是终止){ PDEVICE_EXTENSION deviceExtension = (PDEVICE_EXTENSION)g_pDeviceObject->DeviceExtension; deviceExtension->hParentId = ParentId; deviceExtension->hProcessId = ProcessId; deviceExtension->bCreate = Create; // 触发事件,通知应用程序 KeSetEvent(deviceExtension->ProcessEvent, 0, FALSE); KeClearEvent(deviceExtension->ProcessEvent);}////////////////////////////////////////////////////////////////////////////


ring3实现应用层的调用,搞定进程创建的监视


#include "windows.h"#include "winioctl.h"#include "stdio.h"#include "../inc/ioctls.h"#define SYMBOL_LINK "\\\\.\\ProcMon"//#define SYMBOL_LINK "\\\\.\\slNTProcDrv"int main(){ CALLBACK_INFO cbkinfo, cbktemp = {0}; // 打开驱动设备对象 HANDLE hDriver = ::CreateFile(       SYMBOL_LINK,       GENERIC_READ | GENERIC_WRITE,       0,       NULL,       OPEN_EXISTING,       FILE_ATTRIBUTE_NORMAL,       NULL); if (hDriver == INVALID_HANDLE_VALUE) {  printf("打开驱动设备对象失败!\n");  return -1; }  // 打开内核事件对象 HANDLE hProcessEvent = ::OpenEventW(SYNCHRONIZE, FALSE, EVENT_NAME); while (::WaitForSingleObject(hProcessEvent, INFINITE)) {  DWORD dwRet;  BOOL bRet;  bRet = ::DeviceIoControl(       hDriver,       IOCTL_PROC_MON,       NULL,       0,       &cbkinfo,       sizeof(cbkinfo),       &dwRet,       NULL);  if (bRet)  {   if (cbkinfo.hParentId != cbktemp.hParentId || \    cbkinfo.hProcessId != cbktemp.hProcessId || \    cbkinfo.bCreate != cbktemp.bCreate)   {    if (cbkinfo.bCreate)    {     printf("有进程被创建,PID = %d\n", cbkinfo.hProcessId);    }     else    {     printf("有进程被终止,PID = %d\n", cbkinfo.hProcessId);    }    cbktemp = cbkinfo;   }  }   else  {   printf("\n获取进程信息失败!\n");   break;  } } ::CloseHandle(hDriver); return 0;}



           

再分享一下我老师大神的人工智能教程吧。零基础!通俗易懂!风趣幽默!还带黄段子!希望你也加入到我们人工智能的队伍中来!https://blog.csdn.net/jiangjunshow

猜你喜欢

转载自blog.csdn.net/fdgugfv/article/details/87861940