| 12 | } |
| 13 | |
| 14 | NTSTATUS DevMonManager::AddDevice(PCWSTR name) { |
| 15 | AutoLock locker(Lock); |
| 16 | if (MonitoredDeviceCount == MaxMonitoredDevices) |
| 17 | return STATUS_TOO_MANY_NAMES; |
| 18 | |
| 19 | for (int i = 0; i < MaxMonitoredDevices; i++) { |
| 20 | if (Devices[i].DeviceObject == nullptr) { |
| 21 | UNICODE_STRING targetName; |
| 22 | RtlInitUnicodeString(&targetName, name); |
| 23 | |
| 24 | PFILE_OBJECT FileObject; |
| 25 | PDEVICE_OBJECT LowerDeviceObject = nullptr; |
| 26 | // ���豸���� Usually FILE_READ_DATA Infrequently FILE_WRITE_DATA or FILE_ALL_ACCESS |
| 27 | auto status = IoGetDeviceObjectPointer(&targetName, FILE_ALL_ACCESS, |
| 28 | &FileObject, &LowerDeviceObject); |
| 29 | if (!NT_SUCCESS(status)) { |
| 30 | KdPrint(("Failed to get device object pointer (%ws) (0x%08X)\n", name, status)); |
| 31 | return status; |
| 32 | } |
| 33 | |
| 34 | PDEVICE_OBJECT DeviceObject = nullptr; |
| 35 | WCHAR* buffer = nullptr; |
| 36 | |
| 37 | // �����豸��Ȼ���֮ |
| 38 | do |
| 39 | { |
| 40 | // A name is not needed,because the target device is named and is the real target for IRPs. |
| 41 | status = IoCreateDevice(DriverObject, sizeof(DeviceExtension), nullptr, |
| 42 | LowerDeviceObject->DeviceType, 0, FALSE, &DeviceObject); |
| 43 | if (!NT_SUCCESS(status)) |
| 44 | break; |
| 45 | // allocate buffer to copy device name |
| 46 | buffer = (WCHAR*)ExAllocatePool(PagedPool, targetName.Length); |
| 47 | if (!buffer) { |
| 48 | status = STATUS_INSUFF_SERVER_RESOURCES; |
| 49 | break; |
| 50 | } |
| 51 | |
| 52 | auto ext = (DeviceExtension*)DeviceObject->DeviceExtension; |
| 53 | |
| 54 | // ��������ķ����� Ϊ 0 ��ʾ������ |
| 55 | // ���Ϊ��������� Ϊ 0 ��ʾ������ |
| 56 | IoInitializeRemoveLock(&ext->RemoveLock, 'kcol',0,0); |
| 57 | // ������Ҫ��λ |
| 58 | // We must prepare our new device object fully before actually attaching. |
| 59 | DeviceObject->Flags |= LowerDeviceObject->Flags & (DO_BUFFERED_IO | DO_DIRECT_IO); |
| 60 | DeviceObject->DeviceType = LowerDeviceObject->DeviceType; |
| 61 | DeviceObject->Characteristics |= LowerDeviceObject->Characteristics & (FILE_DEVICE_SECURE_OPEN); |
| 62 | |
| 63 | Devices[i].DeviceName.Buffer = buffer; |
| 64 | Devices[i].DeviceName.MaximumLength = targetName.Length; |
| 65 | RtlCopyUnicodeString(&Devices[i].DeviceName, &targetName); |
| 66 | Devices[i].DeviceObject = DeviceObject; |
| 67 | |
| 68 | // ��һ���豸����һ���豸�� |
| 69 | status = IoAttachDeviceToDeviceStackSafe( |
| 70 | DeviceObject, // filter device object |
| 71 | LowerDeviceObject, // target device object |
nothing calls this directly
no test coverage detected