18#define ENUM_NAME_ROOT L"Root"
84 for (NextEntry = DeviceExtension->DeviceListHead.
Flink;
85 NextEntry != &DeviceExtension->DeviceListHead;
86 NextEntry = NextEntry->
Flink)
147 InstancePath[0] =
L'\\';
192 WCHAR InstancePath[5];
197 HANDLE EnumHandle, DeviceKeyHandle =
NULL, InstanceKeyHandle;
213 DPRINT1(
"ExAllocatePoolWithTag() failed\n");
224 DPRINT(
"ExAllocatePoolWithTag() failed\n");
229 Device->DeviceID = DevicePath;
230 RtlInitEmptyUnicodeString(&DevicePath,
NULL, 0);
246 DPRINT1(
"Failed to open registry key\n");
257 (
PWSTR)DeviceKeyHandle,
261 for (NextInstance = 0; NextInstance <= 9999; NextInstance++)
263 _snwprintf(InstancePath,
sizeof(InstancePath) /
sizeof(
WCHAR),
L"%04lu", NextInstance);
269 if (NextInstance > 9999)
276 _snwprintf(InstancePath,
sizeof(InstancePath) /
sizeof(
WCHAR),
L"%04lu", NextInstance);
280 DPRINT1(
"NextInstance value is corrupt! (%lu)\n", NextInstance);
282 (
PWSTR)DeviceKeyHandle,
289 (
PWSTR)DeviceKeyHandle,
293 sizeof(NextInstance));
296 DPRINT1(
"Failed to write new NextInstance value! (0x%x)\n",
Status);
324 FullInstancePath->MaximumLength =
Device->DeviceID.Length +
sizeof(
L'\\') +
Device->InstanceID.Length;
325 FullInstancePath->Length = 0;
327 if (!FullInstancePath->Buffer)
341 DPRINT(
"IoCreateDevice() failed with status 0x%08lx\n",
Status);
351 Device->Pdo->Flags &= ~DO_DEVICE_INITIALIZING;
374 if (DeviceKeyHandle !=
NULL)
424 if (BinaryValue ==
NULL)
427 *
Buffer->Data = BinaryValue;
457 DPRINT(
"ExAllocatePoolWithTag() failed\n");
464 Device->DeviceID = *DevicePath;
465 RtlInitEmptyUnicodeString(DevicePath,
NULL, 0);
468 DPRINT1(
"RtlCreateUnicodeString() failed\n");
478 DPRINT1(
"IopOpenRegistryKeyEx() failed for '%wZ' with status 0x%lx\n",
524 DeviceExtension->DeviceListCount++;
528 if (DeviceKeyHandle !=
NULL)
551 HANDLE InstanceKey, ControlKey;
558 if (!pKeyValueFullInformation)
568 Status = ZwOpenKey(&InstanceKey,
583 DPRINT(
"No 'DeviceReported' value\n");
592 if (pKeyValueFullInformation->
Type !=
REG_DWORD || pKeyValueFullInformation->
DataLength !=
sizeof(DeviceReported))
600 ASSERT(DeviceReported == 1);
608 Status = ZwOpenKey(&ControlKey,
614 DPRINT(
"No 'Control' key\n");
629 DPRINT(
"No 'DeviceReported' value\n");
637 if (pKeyValueFullInformation->
Type !=
REG_DWORD || pKeyValueFullInformation->
DataLength !=
sizeof(DeviceReported))
644 ASSERT(DeviceReported == 1);
662 ULONG KeyInfoSize, SubKeyInfoSize;
664 ULONG Index1, Index2;
679 DPRINT(
"ExAllocatePoolWithTag() failed\n");
683 SubKeyInfoSize = KeyInfoSize;
689 DPRINT(
"ExAllocatePoolWithTag() failed\n");
723 ASSERT(KeyInfoSize < ResultSize);
724 KeyInfoSize = ResultSize;
731 DPRINT1(
"ExAllocatePoolWithTag(%lu) failed\n", KeyInfoSize);
739 DPRINT(
"ZwEnumerateKey() failed with status 0x%08lx\n",
Status);
759 DPRINT(
"IopOpenRegistryKeyEx() failed for '%wZ' with status 0x%lx\n",
782 ASSERT(SubKeyInfoSize < ResultSize);
783 SubKeyInfoSize = ResultSize;
790 DPRINT1(
"ExAllocatePoolWithTag(%lu) failed\n", SubKeyInfoSize);
798 DPRINT(
"ZwEnumerateKey() failed with status 0x%08lx\n",
Status);
803 SubKeyInfo->Name[SubKeyInfo->NameLength /
sizeof(
WCHAR)] = 0;
813 DPRINT1(
"ExAllocatePoolWithTag() failed\n");
820 DPRINT(
"Found device %wZ\\%S!\n", &DevicePath, SubKeyInfo->Name);
842 DPRINT(
"Skipping device %wZ\\%S (not reported yet)\n", &DevicePath, SubKeyInfo->Name);
895 DPRINT(
"EnumerateDevices() failed with status 0x%08lx\n",
Status);
912 DPRINT(
"ExAllocatePoolWithTag() failed\n");
919 Relations->
Count = OtherRelations->Count;
928 NextEntry = NextEntry->
Flink)
940 DPRINT(
"IoCreateDevice() failed with status 0x%08lx\n",
Status);
949 Device->Pdo->Flags &= ~DO_DEVICE_INITIALIZING;
1001 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_DEVICE_RELATIONS\n");
1033 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_DEVICE_RELATIONS / TargetDeviceRelation\n");
1037 DPRINT(
"ExAllocatePoolWithTag() failed\n");
1043 Relations->
Count = 1;
1103 return Irp->IoStatus.Status;
1137 return Irp->IoStatus.Status;
1159 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_DEVICE_TEXT / DeviceTextDescription\n");
1173 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_DEVICE_TEXT / DeviceTextLocationInformation\n");
1179 DPRINT1(
"IRP_MJ_PNP / IRP_MN_QUERY_DEVICE_TEXT / unknown query id type 0x%lx\n", DeviceTextType);
1204 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_ID / BusQueryDeviceID\n");
1224 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_ID / BusQueryInstanceID\n");
1236 DPRINT1(
"IRP_MJ_PNP / IRP_MN_QUERY_ID / unknown query id type 0x%lx\n",
IdType);
1259 &GUID_BUS_TYPE_INTERNAL,
1297 DPRINT(
"IRP_MJ_PNP / IRP_MN_START_DEVICE\n");
1306 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_CAPABILITIES\n");
1311 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_RESOURCES\n");
1316 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_RESOURCE_REQUIREMENTS\n");
1321 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_RESOURCE_REQUIREMENTS\n");
1326 DPRINT(
"IRP_MJ_PNP / IRP_MN_FILTER_RESOURCE_REQUIREMENTS\n");
1364 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_PNP_DEVICE_STATE\n");
1368 DPRINT(
"IRP_MJ_PNP / IRP_MN_QUERY_BUS_INFORMATION\n");
1517 &IopPfnDumpDeviceObject);
1520 DPRINT1(
"Creating PFN Dump device failed with %lx\n",
Status);
1524 IopPfnDumpDeviceObject->
Flags &= ~DO_DEVICE_INITIALIZING;
static PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(PIRP Irp)
static WCHAR ServiceName[]
PDEVICE_OBJECT PhysicalDeviceObject
_In_ BUS_QUERY_ID_TYPE IdType
NTSYSAPI BOOLEAN NTAPI RtlCreateUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
#define NT_SUCCESS(StatCode)
static void cleanup(void)
_In_ PIO_STACK_LOCATION IrpSp
#define RemoveEntryList(Entry)
#define InsertTailList(ListHead, Entry)
UNICODE_STRING * PUNICODE_STRING
#define ExAllocatePoolWithTag(hernya, size, tag)
struct _DEVICE_OBJECT * PDEVICE_OBJECT
NTSTATUS RtlAppendUnicodeToString(IN PUNICODE_STRING Str1, IN PWSTR Str2)
#define InitializeListHead(ListHead)
#define ExAllocatePool(type, size)
_Must_inspect_result_ _In_opt_ PVOID _In_opt_ PVOID InstanceId
VOID FASTCALL KeInitializeGuardedMutex(OUT PKGUARDED_MUTEX GuardedMutex)
VOID FASTCALL KeReleaseGuardedMutex(IN OUT PKGUARDED_MUTEX GuardedMutex)
VOID FASTCALL KeAcquireGuardedMutex(IN PKGUARDED_MUTEX GuardedMutex)
#define RTL_DUPLICATE_UNICODE_STRING_NULL_TERMINATE
_In_ GUID _In_ PVOID ValueData
#define OBJ_KERNEL_HANDLE
#define OBJ_CASE_INSENSITIVE
NTSYSAPI NTSTATUS WINAPI RtlDeleteRegistryValue(ULONG, PCWSTR, PCWSTR)
NTSYSAPI NTSTATUS WINAPI RtlWriteRegistryValue(ULONG, PCWSTR, PCWSTR, ULONG, PVOID, ULONG)
NTSYSAPI NTSTATUS WINAPI RtlQueryRegistryValues(ULONG, PCWSTR, PRTL_QUERY_REGISTRY_TABLE, PVOID, PVOID)
NTSYSAPI NTSTATUS WINAPI RtlDuplicateUnicodeString(int, const UNICODE_STRING *, UNICODE_STRING *)
#define ExFreePoolWithTag(_P, _T)
int _snwprintf(wchar_t *buffer, size_t count, const wchar_t *format,...)
#define InitializeObjectAttributes(p, n, a, r, s)
_Must_inspect_result_ _Out_ PNDIS_STATUS _In_ NDIS_HANDLE _In_ PNDIS_STRING SubKeyName
_In_ UINT _In_ UINT _In_ PNDIS_PACKET Source
_Must_inspect_result_ _Out_ PNDIS_STATUS _In_ NDIS_HANDLE _In_ PNDIS_STRING _Out_ PNDIS_HANDLE SubKeyHandle
_Must_inspect_result_ _Out_ PNDIS_STATUS _In_ NDIS_HANDLE _In_ ULONG _Out_ PNDIS_STRING _Out_ PNDIS_HANDLE KeyHandle
#define FILE_AUTOGENERATED_DEVICE_NAME
NTSYSAPI NTSTATUS NTAPI ZwClose(_In_ HANDLE Handle)
_In_ PCWSTR _Inout_ _At_ QueryTable EntryContext
_In_ PCWSTR _Inout_ _At_ QueryTable _Pre_unknown_ PRTL_QUERY_REGISTRY_TABLE QueryTable
_In_ PUNICODE_STRING _Inout_ PUNICODE_STRING Destination
#define RTL_QUERY_REGISTRY_SUBKEY
@ KeyValueFullInformation
NTSYSAPI NTSTATUS NTAPI RtlAppendUnicodeStringToString(PUNICODE_STRING Destination, PUNICODE_STRING Source)
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
NTSYSAPI BOOLEAN NTAPI RtlEqualUnicodeString(PUNICODE_STRING String1, PUNICODE_STRING String2, BOOLEAN CaseInSensitive)
#define REG_OPTION_NON_VOLATILE
#define RTL_QUERY_REGISTRY_REQUIRED
#define RTL_QUERY_REGISTRY_DIRECT
#define KEY_ENUMERATE_SUB_KEYS
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
NTSYSAPI BOOLEAN NTAPI RtlPrefixUnicodeString(IN PUNICODE_STRING String1, IN PUNICODE_STRING String2, IN BOOLEAN CaseInSensitive)
#define RTL_REGISTRY_HANDLE
NTSTATUS NTAPI IopOpenRegistryKeyEx(PHANDLE KeyHandle, HANDLE ParentKey, PUNICODE_STRING Name, ACCESS_MASK DesiredAccess)
PDEVICE_NODE FASTCALL IopGetDeviceNode(IN PDEVICE_OBJECT DeviceObject)
PDRIVER_OBJECT IopRootDriverObject
PDEVICE_NODE IopRootDeviceNode
VOID NTAPI MmDumpArmPfnDatabase(IN BOOLEAN StatusOnly)
NTSTATUS NTAPI IoCreateDevice(IN PDRIVER_OBJECT DriverObject, IN ULONG DeviceExtensionSize, IN PUNICODE_STRING DeviceName, IN DEVICE_TYPE DeviceType, IN ULONG DeviceCharacteristics, IN BOOLEAN Exclusive, OUT PDEVICE_OBJECT *DeviceObject)
VOID NTAPI IoDeleteDevice(IN PDEVICE_OBJECT DeviceObject)
#define IoCompleteRequest
VOID NTAPI PoStartNextPowerIrp(IN PIRP Irp)
#define STATUS_NO_MORE_ENTRIES
#define STATUS_REVISION_MISMATCH
NTSTATUS NTAPI ObCloseHandle(IN HANDLE Handle, IN KPROCESSOR_MODE AccessMode)
struct _PNPROOT_FDO_DEVICE_EXTENSION * PPNPROOT_FDO_DEVICE_EXTENSION
static NTSTATUS PdoQueryResources(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
struct _PNPROOT_PDO_DEVICE_EXTENSION PNPROOT_PDO_DEVICE_EXTENSION
VOID PnpRootInitializeDevExtension(VOID)
static NTSTATUS NTAPI PnpRootPowerControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
static NTSTATUS PdoQueryCapabilities(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
static NTSTATUS NTAPI PnpRootPnpControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
static NTSTATUS NTAPI QueryBinaryValueCallback(IN PWSTR ValueName, IN ULONG ValueType, IN PVOID ValueData, IN ULONG ValueLength, IN PVOID Context, IN PVOID EntryContext)
static NTSTATUS PdoQueryDeviceText(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
static NTSTATUS PdoQueryBusInformation(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
static PNPROOT_FDO_DEVICE_EXTENSION PnpRootDOExtension
static NTSTATUS PdoQueryResourceRequirements(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
NTSTATUS PnpRootRegisterDevice(IN PDEVICE_OBJECT DeviceObject)
static NTSTATUS CreateDeviceFromRegistry(_Inout_ PPNPROOT_FDO_DEVICE_EXTENSION DeviceExtension, _Inout_ PUNICODE_STRING DevicePath, _In_ PCWSTR InstanceId, _In_ HANDLE SubKeyHandle)
NTSTATUS PnpRootCreateDevice(IN PUNICODE_STRING ServiceName, OUT PDEVICE_OBJECT *PhysicalDeviceObject, OUT PUNICODE_STRING FullInstancePath)
static NTSTATUS NTAPI QueryStringCallback(IN PWSTR ValueName, IN ULONG ValueType, IN PVOID ValueData, IN ULONG ValueLength, IN PVOID Context, IN PVOID EntryContext)
static NTSTATUS PnpRootPdoPnpControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
NTSTATUS NTAPI PnpRootDriverEntry(IN PDRIVER_OBJECT DriverObject, IN PUNICODE_STRING RegistryPath)
static NTSTATUS PdoQueryId(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
NTSTATUS NTAPI PnpRootAddDevice(IN PDRIVER_OBJECT DriverObject, IN PDEVICE_OBJECT PhysicalDeviceObject)
struct _PNPROOT_DEVICE * PPNPROOT_DEVICE
struct _PNPROOT_PDO_DEVICE_EXTENSION * PPNPROOT_PDO_DEVICE_EXTENSION
static NTSTATUS PnpRootQueryDeviceRelations(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
static NTSTATUS PdoQueryDeviceRelations(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PIO_STACK_LOCATION IrpSp)
static NTSTATUS LocateChildDevice(IN PPNPROOT_FDO_DEVICE_EXTENSION DeviceExtension, IN PCUNICODE_STRING DeviceId, IN PCWSTR InstanceId, OUT PPNPROOT_DEVICE *ChildDevice OPTIONAL)
static NTSTATUS EnumerateDevices(IN PDEVICE_OBJECT DeviceObject)
struct _PNPROOT_DEVICE PNPROOT_DEVICE
static NTSTATUS IopShouldProcessDevice(IN HANDLE SubKey, IN PCWSTR InstanceID)
struct _PNPROOT_FDO_DEVICE_EXTENSION PNPROOT_FDO_DEVICE_EXTENSION
static NTSTATUS PnpRootFdoPnpControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
NTSTATUS PnpRootCreateDeviceObject(OUT PDEVICE_OBJECT *DeviceObject)
#define FILE_DEVICE_UNKNOWN
#define FILE_DEVICE_CONTROLLER
#define REGSTR_KEY_ROOTENUM
#define REGSTR_PATH_SYSTEMENUM
#define STATUS_BUFFER_TOO_SMALL
#define STATUS_BUFFER_OVERFLOW
PULONG MinorVersion OPTIONAL
PDEVICE_OBJECT Objects[1]
PDRIVER_ADD_DEVICE AddDevice
PDRIVER_EXTENSION DriverExtension
union _IO_STACK_LOCATION::@1581 Parameters
struct _IO_STACK_LOCATION::@3980::@4007 DeviceCapabilities
struct _IO_STACK_LOCATION::@3980::@4005 QueryDeviceRelations
struct _IO_STACK_LOCATION::@3980::@4012 QueryDeviceText
struct _IO_STACK_LOCATION::@3980::@4011 QueryId
struct _LIST_ENTRY * Flink
PCM_RESOURCE_LIST ResourceList
PIO_RESOURCE_REQUIREMENTS_LIST ResourceRequirementsList
UNICODE_STRING InstanceID
UNICODE_STRING DeviceDescription
KGUARDED_MUTEX DeviceListLock
LIST_ENTRY DeviceListHead
PPNPROOT_DEVICE DeviceInfo
PRTL_QUERY_REGISTRY_ROUTINE QueryRoutine
#define RTL_CONSTANT_STRING(s)
#define FIELD_OFFSET(t, f)
#define RtlCopyMemory(Destination, Source, Length)
#define RtlZeroMemory(Destination, Length)
#define CONTAINING_RECORD(address, type, field)
#define STATUS_INVALID_DEVICE_REQUEST
#define STATUS_NO_SUCH_DEVICE
#define STATUS_UNSUCCESSFUL
#define STATUS_INSUFFICIENT_RESOURCES
#define STATUS_OBJECT_NAME_NOT_FOUND
_Must_inspect_result_ _In_ WDFDEVICE Device
_In_ PDEVICE_OBJECT DeviceObject
_Must_inspect_result_ _In_ WDFDEVICE _In_ DEVICE_REGISTRY_PROPERTY _In_ ULONG _Out_ PULONG ResultLength
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ DEVPROPTYPE _In_ ULONG Size
_Must_inspect_result_ _In_ WDFDEVICE _In_ PCUNICODE_STRING KeyName
_Must_inspect_result_ _In_ WDFDEVICE _In_ WDFSTRING String
_Must_inspect_result_ _In_ PDRIVER_OBJECT _In_ PCUNICODE_STRING RegistryPath
_Must_inspect_result_ _In_ PDRIVER_OBJECT DriverObject
_Must_inspect_result_ _In_ PWDFDEVICE_INIT _In_ PCUNICODE_STRING InstanceID
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING _In_ ULONG _Out_opt_ PULONG _Out_opt_ PULONG ValueType
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING ValueName
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING _In_ ULONG ValueLength
_Must_inspect_result_ _In_ WDFIORESREQLIST _In_opt_ PWDF_OBJECT_ATTRIBUTES _Out_ WDFIORESLIST * ResourceList
_In_ WDF_WMI_PROVIDER_CONTROL Control
#define DeviceCapabilities
struct _PNP_BUS_INFORMATION * PPNP_BUS_INFORMATION
#define IRP_MN_QUERY_PNP_DEVICE_STATE
enum _BUS_QUERY_ID_TYPE BUS_QUERY_ID_TYPE
#define DO_BUS_ENUMERATED_DEVICE
#define IRP_MN_START_DEVICE
#define IRP_MN_QUERY_RESOURCE_REQUIREMENTS
#define IRP_MN_REMOVE_DEVICE
#define IRP_MN_FILTER_RESOURCE_REQUIREMENTS
struct _DEVICE_RELATIONS * PDEVICE_RELATIONS
#define IRP_MN_QUERY_DEVICE_RELATIONS
#define IRP_MN_QUERY_DEVICE_TEXT
#define IRP_MN_QUERY_CAPABILITIES
#define IRP_MN_QUERY_RESOURCES
@ DeviceTextLocationInformation
enum _DEVICE_TEXT_TYPE DEVICE_TEXT_TYPE
#define IRP_MN_QUERY_POWER
#define IRP_MN_QUERY_BUS_INFORMATION
#define ObReferenceObject