串口过滤驱动练习
2017-02-22 09:15
453 查看
一个简单的串口过滤驱动框架
参考《寒江独钓》完成用来对串口读写进行的过滤驱动。注意问题:
用来和应用层通信的buffer区域有三种方式。
完成的读写分发函数的方式特殊还未搞懂?
//以下为完整代码 #include <ntddk.h> #include <string.h> static PDEVICE_OBJECT m_fltobj; static PDEVICE_OBJECT m_topobj; //定义一个读的完成处理函数 NTSTATUS fengReadComplete(IN PDEVICE_OBJECT DeviectObject, IN PIRP Irp, IN PVOID Context) { PIO_STACK_LOCATION IrpSp; ULONG i; IrpSp = IoGetCurrentIrpStackLocation(Irp); if(NT_SUCCESS( Irp->IoStatus.Status)) { PUCHAR buf = (PUCHAR)Irp->AssociatedIrp.SystemBuffer; DbgPrint("Driver1 Read:"); for(i=0; i<Irp->IoStatus.Information; i++) { DbgPrint("%02X, ", buf[i]); } DbgPrint("\r\n"); } if( Irp->PendingReturned) IoMarkIrpPending( Irp); return Irp->IoStatus.Status; } NTSTATUS DRIVER1_DispatchDeviceControl(IN PDEVICE_OBJECT DeviceObject,IN PIRP Irp) { ULONG j; NTSTATUS status = STATUS_SUCCESS; PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation(Irp); DbgPrint(("收到IRP\r\n")); if(m_fltobj == DeviceObject) { if(irpSp->MajorFunction == IRP_MJ_POWER)//所有的电源操作,全部直接放过。 { //直接发送,然后返回说已经被处理了。 PoStartNextPowerIrp(Irp); IoSkipCurrentIrpStackLocation(Irp); return PoCallDriver(m_topobj, Irp); } else if(irpSp->MajorFunction == IRP_MJ_WRITE) { PUCHAR buf = NULL; if(Irp->MdlAddress != NULL) buf = (PUCHAR)MmGetSystemAddressForMdlSafe(Irp->MdlAddress, NormalPagePriority);//将数据放到MdkAddress中,映射关系。 else buf = (PUCHAR)Irp->UserBuffer; //直接读取用户控件内存。 if(buf == NULL) buf = (PUCHAR)Irp->AssociatedIrp.SystemBuffer; //将用户空间内存拷贝到内核空间。 DbgPrint("Driver1 Write:"); for(j =0; j< irpSp->Parameters.Write.Length; j++) { DbgPrint("%02X, ", buf[j]); } DbgPrint("\r\n"); } else if(irpSp->MajorFunction == IRP_MJ_READ) { IoCopyCurrentIrpStackLocationToNext(Irp); IoSetCompletionRoutine(Irp, fengReadComplete, DeviceObject, TRUE, TRUE, TRUE); return IoCallDriver(m_topobj, Irp); } //所有的读写请求直接下发执行即可,我们并不禁止或改变它。 IoSkipCurrentIrpStackLocation(Irp); return IoCallDriver(m_topobj, Irp); } //直接返回参数错误 Irp->IoStatus.Information = 0; Irp->IoStatus.Status = STATUS_INVALID_PARAMETER; IoCompleteRequest(Irp, IO_NO_INCREMENT); return status; } VOID DRIVER1_DriverUnload(IN PDRIVER_OBJECT DriverObject) { LARGE_INTEGER ilval; if(m_topobj != NULL) IoDetachDevice(m_topobj); ilval.QuadPart = 5 * 1000 * 1000 * (-10); //5秒 KeDelayExecutionThread(KernelMode, FALSE, &ilval); if(m_fltobj != NULL) IoDeleteDevice(m_fltobj); } #pragma code_seg("INIT") NTSTATUS DriverEntry(IN OUT PDRIVER_OBJECT DriverObject,IN PUNICODE_STRING RegistryPath) { size_t i; NTSTATUS status; UNICODE_STRING namestr; PFILE_OBJECT fileobj = NULL; PDEVICE_OBJECT devobj = NULL; DbgBreakPoint(); for(i = 0; i< IRP_MJ_MAXIMUM_FUNCTION; i++) { DriverObject->MajorFunction[i] = DRIVER1_DispatchDeviceControl; } DriverObject->DriverUnload = DRIVER1_DriverUnload; //打开一个端口设备 //根据id转换成串口的名字 RtlInitUnicodeString(&namestr, L"\\Device\\Serial0"); //打开设备 //从名字获取设备对象的指针。 status = IoGetDeviceObjectPointer( &namestr, FILE_ALL_ACCESS, //全部读写权限 &fileobj, //无用的文件对象指针 &devobj); //打开串口 //如果打开成功了,记得一定要把文件对象解除引用 if(status == STATUS_SUCCESS) ObDereferenceObject(fileobj); if(status == STATUS_SUCCESS) { NTSTATUS status; PDEVICE_OBJECT topdev = NULL; DbgPrint(("成功打开com1\r\n")); //生成设备然后绑定 status = IoCreateDevice(DriverObject, 0, NULL, devobj->DeviceType, 0, FALSE, &m_fltobj); if(status != STATUS_SUCCESS) return status; //拷贝重要标志位 没懂这个是干啥的? if(devobj->Flags & DO_BUFFERED_IO) m_fltobj->Flags |= DO_BUFFERED_IO; if(devobj->Flags & DO_DIRECT_IO) m_fltobj->Flags |= DO_DIRECT_IO; if(devobj->Characteristics & FILE_DEVICE_SECURE_OPEN) m_fltobj->Characteristics |= FILE_DEVICE_SECURE_OPEN; m_fltobj->Flags |= DO_POWER_PAGABLE; //将一个设备绑定到另一个设备 topdev = IoAttachDeviceToDeviceStack(m_fltobj, devobj); if(topdev == NULL) { //如果绑定失败了,销毁设备,返回错误 IoDeleteDevice(m_fltobj); m_fltobj = NULL; status = STATUS_UNSUCCESSFUL; return status; } DbgPrint(("driverentry 成功\r\n")); //设置这个设备已经启动 m_topobj= topdev; m_fltobj->Flags &= ~DO_DEVICE_INITIALIZING; return STATUS_SUCCESS; } return STATUS_SUCCESS; }
相关文章推荐
- 串口过滤驱动源码
- <读书笔记>Windows内核安全 ---串口过滤驱动(3) 相关知识总结
- 为串口过滤驱动加上显示串口收发内容的应用程序
- 一个串口输入过滤驱动
- 串口的过滤驱动例子
- 一个简单的串口过滤驱动
- 串口过滤驱动(过滤所有的串口)
- 一个简单的串口过滤驱动及一点体会
- CommMonitor8.0 串口过滤驱动 SDK DLL版本 C#/Delphi调用DEMO
- 一个可以过滤串口输入的过滤驱动
- windows驱动开发之过滤串口
- 【驱动】USB驱动实例・串口驱动・键盘驱动
- 25.3.1 USB串口驱动
- NVIDIA Tegra-TK1串口驱动代码初探
- Windows文件系统过滤驱动开发教程(4)
- 初尝windows内核编程-键盘过滤驱动
- 文件系统过滤驱动 重要系统调用总结--part1
- 键盘过滤驱动
- 引用 SAMSUNG_S3C2410串口驱动
- 6410的串口驱动