Author: cgutman Date: Mon Jan 30 16:23:44 2012 New Revision: 55328
URL: http://svn.reactos.org/svn/reactos?rev=55328&view=rev Log: [HALACPI] - Create PDO earlier so ACPI can be loaded earlier in boot [HIVESYS] - Create critical device database with required devices for USB boot [NTOSKRNL] - Read the CDDB and install devices that are critical for boot - This implementation won't be 100% correct until a PnP manager rewrite but it should work well enough for our needs - Not complete and disabled atm
Modified: branches/usb-bringup-trunk/boot/bootdata/hivesys_i386.inf branches/usb-bringup-trunk/hal/halx86/acpi/halpnpdd.c branches/usb-bringup-trunk/ntoskrnl/io/pnpmgr/pnpmgr.c
Modified: branches/usb-bringup-trunk/boot/bootdata/hivesys_i386.inf URL: http://svn.reactos.org/svn/reactos/branches/usb-bringup-trunk/boot/bootdata/... ============================================================================== --- branches/usb-bringup-trunk/boot/bootdata/hivesys_i386.inf [iso-8859-1] (original) +++ branches/usb-bringup-trunk/boot/bootdata/hivesys_i386.inf [iso-8859-1] Mon Jan 30 16:23:44 2012 @@ -7,6 +7,44 @@ HKLM,"SYSTEM\CurrentControlSet\Control","WaitToKillServiceTimeout",2,"20000" HKLM,"SYSTEM\CurrentControlSet\Control\Biosinfo","InfName",2,"biosinfo.inf" HKLM,"SYSTEM\CurrentControlSet\Control\PnP",,0x00000012 + +; Critical Device Database + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\acpipic_up","ClassGUID",0x00000000,"{4D36E966-E325-11CE-BFC1-08002BE10318}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase*PNP0A03","Service",0x00000000,"pci" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase*PNP0A03","ClassGUID",0x00000000,"{4D36E97D-E325-11CE-BFC1-08002BE10318}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase*PNP0C08","Service",0x00000000,"acpi" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase*PNP0C08","ClassGUID",0x00000000,"{4D36E97D-E325-11CE-BFC1-08002BE10318}" + +;HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\PCI#CC_0C0300","Service",0x00000000,"usbuhci" +;HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\PCI#CC_0C0300","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\PCI#CC_0C0310","Service",0x00000000,"usbohci" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\PCI#CC_0C0310","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\PCI#CC_0C0320","Service",0x00000000,"usbehci" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\PCI#CC_0C0320","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#Class_08&SubClass_06&Prot_50","Service",0x00000000,"usbstor" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#Class_08&SubClass_06&Prot_50","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#COMPOSITE","Service",0x00000000,"usbccgp" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#COMPOSITE","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#CLASS_09","Service",0x00000000,"usbhub" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#CLASS_09","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#ROOT_HUB","Service",0x00000000,"usbhub" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#ROOT_HUB","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#ROOT_HUB20","Service",0x00000000,"usbhub" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\USB#ROOT_HUB20","ClassGUID",0x00000000,"{36FC9E60-C465-11CF-8056-444553540000}" + +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\GenDisk","Service",0x00000000,"disk" +HKLM,"SYSTEM\CurrentControlSet\Control\CriticalDeviceDatabase\GenDisk","ClassGUID",0x00000000,"{4D36E967-E325-11CE-BFC1-08002BE10318}" +
HKLM,"SYSTEM\CurrentControlSet\Control\SafeBoot","AlternateShell",2,"cmd.exe"
@@ -1413,10 +1451,61 @@ HKLM,"SYSTEM\CurrentControlSet\Services\Packet","Start",0x00010001,0x00000004 HKLM,"SYSTEM\CurrentControlSet\Services\Packet","Type",0x00010001,0x00000001
+; USB hub driver +HKLM,"SYSTEM\CurrentControlSet\Services\usbhub","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\usbhub","Group",0x00000000,"Boot Bus" +HKLM,"SYSTEM\CurrentControlSet\Services\usbhub","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\usbhub","ImagePath",0x00020000,"system32\drivers\usbhub.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\usbhub","Start",0x00010001,0x00000000 + +; EHCI controller driver +HKLM,"SYSTEM\CurrentControlSet\Services\usbehci","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\usbehci","Group",0x00000000,"Boot Bus" +HKLM,"SYSTEM\CurrentControlSet\Services\usbehci","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\usbehci","ImagePath",0x00020000,"system32\drivers\usbehci.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\usbehci","Start",0x00010001,0x00000000 + +; OHCI controller driver +HKLM,"SYSTEM\CurrentControlSet\Services\usbohci","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\usbohci","Group",0x00000000,"Boot Bus" +HKLM,"SYSTEM\CurrentControlSet\Services\usbohci","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\usbohci","ImagePath",0x00020000,"system32\drivers\usbohci.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\usbohci","Start",0x00010001,0x00000000 + +; UHCI controller driver +HKLM,"SYSTEM\CurrentControlSet\Services\usbuhci","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\usbuhci","Group",0x00000000,"Boot Bus" +HKLM,"SYSTEM\CurrentControlSet\Services\usbuhci","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\usbuhci","ImagePath",0x00020000,"system32\drivers\usbuhci.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\usbuhci","Start",0x00010001,0x00000000 + +; USB storage driver +HKLM,"SYSTEM\CurrentControlSet\Services\usbstor","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\usbstor","Group",0x00000000,"Primary Disk" +HKLM,"SYSTEM\CurrentControlSet\Services\usbstor","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\usbstor","ImagePath",0x00020000,"system32\drivers\usbstor.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\usbstor","Start",0x00010001,0x00000000 + +; USB composite generic parent +HKLM,"SYSTEM\CurrentControlSet\Services\usbccgp","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\usbccgp","Group",0x00000000,"Boot Bus" +HKLM,"SYSTEM\CurrentControlSet\Services\usbccgp","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\usbccgp","ImagePath",0x00020000,"system32\drivers\usbccgp.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\usbccgp","Start",0x00010001,0x00000000 + +; ACPI driver +HKLM,"SYSTEM\CurrentControlSet\Services\acpi","ErrorControl",0x00010001,0x00000001 +HKLM,"SYSTEM\CurrentControlSet\Services\acpi","Group",0x00000000,"Boot Bus" +HKLM,"SYSTEM\CurrentControlSet\Services\acpi","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\acpi","ImagePath",0x00020000,"system32\drivers\acpi.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\acpi","Start",0x00010001,0x00000000 + ; PCI Bus driver HKLM,"SYSTEM\CurrentControlSet\Services\Pci","ErrorControl",0x00010001,0x00000001 -HKLM,"SYSTEM\CurrentControlSet\Services\Pci","Group",0x00000000,"Boot Bus " +HKLM,"SYSTEM\CurrentControlSet\Services\Pci","Group",0x00000000,"Boot Bus" HKLM,"SYSTEM\CurrentControlSet\Services\Pci","Tag",0x00010001,0x00000002 +HKLM,"SYSTEM\CurrentControlSet\Services\Pci","ImagePath",0x00020000,"system32\drivers\pci.sys" +HKLM,"SYSTEM\CurrentControlSet\Services\Pci","Start",0x00010001,0x00000000 HKLM,"SYSTEM\CurrentControlSet\Services\Pci\Parameters","1045C621",0x00030003,04,00,00,00,00,00,00,00 HKLM,"SYSTEM\CurrentControlSet\Services\Pci\Parameters","10950640",0x00030003,04,00,00,00,00,00,00,00 HKLM,"SYSTEM\CurrentControlSet\Services\Pci\Parameters","80861230",0x00030003,04,00,00,00,00,00,00,00
Modified: branches/usb-bringup-trunk/hal/halx86/acpi/halpnpdd.c URL: http://svn.reactos.org/svn/reactos/branches/usb-bringup-trunk/hal/halx86/acp... ============================================================================== --- branches/usb-bringup-trunk/hal/halx86/acpi/halpnpdd.c [iso-8859-1] (original) +++ branches/usb-bringup-trunk/hal/halx86/acpi/halpnpdd.c [iso-8859-1] Mon Jan 30 16:23:44 2012 @@ -57,10 +57,61 @@ IN ULONG Count) { PFDO_EXTENSION FdoExtension = Context; + + /* Invalidate device relations since we added a new device */ + IoInvalidateDeviceRelations(FdoExtension->PhysicalDeviceObject, BusRelations); +} + +NTSTATUS +NTAPI +HalpAddDevice(IN PDRIVER_OBJECT DriverObject, + IN PDEVICE_OBJECT TargetDevice) +{ + NTSTATUS Status; + PFDO_EXTENSION FdoExtension; PPDO_EXTENSION PdoExtension; + PDEVICE_OBJECT DeviceObject, AttachedDevice; PDEVICE_OBJECT PdoDeviceObject; - NTSTATUS Status; PDESCRIPTION_HEADER Wdrt; + + DPRINT("HAL: PnP Driver ADD!\n"); + + /* Create the FDO */ + Status = IoCreateDevice(DriverObject, + sizeof(FDO_EXTENSION), + NULL, + FILE_DEVICE_BUS_EXTENDER, + 0, + FALSE, + &DeviceObject); + if (!NT_SUCCESS(Status)) + { + /* Should not happen */ + DbgBreakPoint(); + return Status; + } + + /* Setup the FDO extension */ + FdoExtension = DeviceObject->DeviceExtension; + FdoExtension->ExtensionType = FdoExtensionType; + FdoExtension->PhysicalDeviceObject = TargetDevice; + FdoExtension->FunctionalDeviceObject = DeviceObject; + FdoExtension->ChildPdoList = NULL; + + /* FDO is done initializing */ + DeviceObject->Flags &= ~DO_DEVICE_INITIALIZING; + + /* Attach to the physical device object (the bus) */ + AttachedDevice = IoAttachDeviceToDeviceStack(DeviceObject, TargetDevice); + if (!AttachedDevice) + { + /* Failed, undo everything */ + IoDeleteDevice(DeviceObject); + return STATUS_NO_SUCH_DEVICE; + } + + /* Save the attachment */ + FdoExtension->AttachedDeviceObject = AttachedDevice;
/* Create the PDO */ Status = IoCreateDevice(DriverObject, @@ -74,7 +125,7 @@ { /* Fail */ DPRINT1("HAL: Could not create ACPI device object status=0x%08x\n", Status); - return; + return Status; }
/* Setup the PDO device extension */ @@ -87,7 +138,7 @@ /* Add the PDO to the head of the list */ PdoExtension->Next = FdoExtension->ChildPdoList; FdoExtension->ChildPdoList = PdoExtension; - + /* Initialization is finished */ PdoDeviceObject->Flags &= ~DO_DEVICE_INITIALIZING;
@@ -99,61 +150,10 @@ DPRINT1("You have an ACPI Watchdog. That's great! You should be proud ;-)\n"); }
- /* Invalidate device relations since we added a new device */ - IoInvalidateDeviceRelations(FdoExtension->PhysicalDeviceObject, BusRelations); -} - -NTSTATUS -NTAPI -HalpAddDevice(IN PDRIVER_OBJECT DriverObject, - IN PDEVICE_OBJECT TargetDevice) -{ - NTSTATUS Status; - PFDO_EXTENSION FdoExtension; - PDEVICE_OBJECT DeviceObject, AttachedDevice; - DPRINT("HAL: PnP Driver ADD!\n"); - - /* Create the FDO */ - Status = IoCreateDevice(DriverObject, - sizeof(FDO_EXTENSION), - NULL, - FILE_DEVICE_BUS_EXTENDER, - 0, - FALSE, - &DeviceObject); - if (!NT_SUCCESS(Status)) - { - /* Should not happen */ - DbgBreakPoint(); - return Status; - } - - /* Setup the FDO extension */ - FdoExtension = DeviceObject->DeviceExtension; - FdoExtension->ExtensionType = FdoExtensionType; - FdoExtension->PhysicalDeviceObject = TargetDevice; - FdoExtension->FunctionalDeviceObject = DeviceObject; - FdoExtension->ChildPdoList = NULL; - - /* FDO is done initializing */ - DeviceObject->Flags &= ~DO_DEVICE_INITIALIZING; - - /* Attach to the physical device object (the bus) */ - AttachedDevice = IoAttachDeviceToDeviceStack(DeviceObject, TargetDevice); - if (!AttachedDevice) - { - /* Failed, undo everything */ - IoDeleteDevice(DeviceObject); - return STATUS_NO_SUCH_DEVICE; - } - - /* Save the attachment */ - FdoExtension->AttachedDeviceObject = AttachedDevice; - /* Register for reinitialization to report devices later */ - IoRegisterDriverReinitialization(DriverObject, - HalpReportDetectedDevices, - FdoExtension); + IoRegisterBootDriverReinitialization(DriverObject, + HalpReportDetectedDevices, + FdoExtension);
/* Return status */ DPRINT("Device added %lx\n", Status);
Modified: branches/usb-bringup-trunk/ntoskrnl/io/pnpmgr/pnpmgr.c URL: http://svn.reactos.org/svn/reactos/branches/usb-bringup-trunk/ntoskrnl/io/pn... ============================================================================== --- branches/usb-bringup-trunk/ntoskrnl/io/pnpmgr/pnpmgr.c [iso-8859-1] (original) +++ branches/usb-bringup-trunk/ntoskrnl/io/pnpmgr/pnpmgr.c [iso-8859-1] Mon Jan 30 16:23:44 2012 @@ -55,6 +55,370 @@ IopGetDeviceNode(PDEVICE_OBJECT DeviceObject) { return ((PEXTENDED_DEVOBJ_EXTENSION)DeviceObject->DeviceObjectExtension)->DeviceNode; +} + +VOID +IopFixupDeviceId(PWCHAR String) +{ + ULONG Length = wcslen(String), i; + + for (i = 0; i < Length; i++) + { + if (String[i] == L'\') + String[i] = L'#'; + } +} + +VOID +NTAPI +IopInstallCriticalDevice(PDEVICE_NODE DeviceNode) +{ + NTSTATUS Status; + HANDLE CriticalDeviceKey, InstanceKey; + OBJECT_ATTRIBUTES ObjectAttributes; + UNICODE_STRING CriticalDeviceKeyU = RTL_CONSTANT_STRING(L"\Registry\Machine\System\CurrentControlSet\Control\CriticalDeviceDatabase"); + UNICODE_STRING CompatibleIdU = RTL_CONSTANT_STRING(L"CompatibleIDs"); + UNICODE_STRING HardwareIdU = RTL_CONSTANT_STRING(L"HardwareID"); + UNICODE_STRING ServiceU = RTL_CONSTANT_STRING(L"Service"); + UNICODE_STRING ClassGuidU = RTL_CONSTANT_STRING(L"ClassGUID"); + PKEY_VALUE_PARTIAL_INFORMATION PartialInfo; + ULONG HidLength = 0, CidLength = 0, BufferLength; + PWCHAR IdBuffer, OriginalIdBuffer; + + /* Open the device instance key */ + Status = IopCreateDeviceKeyPath(&DeviceNode->InstancePath, 0, &InstanceKey); + if (Status != STATUS_SUCCESS) + return; + + Status = ZwQueryValueKey(InstanceKey, + &HardwareIdU, + KeyValuePartialInformation, + NULL, + 0, + &HidLength); + if (Status != STATUS_BUFFER_OVERFLOW && Status != STATUS_BUFFER_TOO_SMALL) + { + ZwClose(InstanceKey); + return; + } + + Status = ZwQueryValueKey(InstanceKey, + &CompatibleIdU, + KeyValuePartialInformation, + NULL, + 0, + &CidLength); + if (Status != STATUS_BUFFER_OVERFLOW && Status != STATUS_BUFFER_TOO_SMALL) + { + CidLength = 0; + } + + BufferLength = HidLength + CidLength; + BufferLength -= (((CidLength != 0) ? 2 : 1) * FIELD_OFFSET(KEY_VALUE_PARTIAL_INFORMATION, Data)); + + /* Allocate a buffer to hold data from both */ + OriginalIdBuffer = IdBuffer = ExAllocatePool(PagedPool, BufferLength); + if (!IdBuffer) + { + ZwClose(InstanceKey); + return; + } + + /* Compute the buffer size */ + if (HidLength > CidLength) + BufferLength = HidLength; + else + BufferLength = CidLength; + + PartialInfo = ExAllocatePool(PagedPool, BufferLength); + if (!PartialInfo) + { + ZwClose(InstanceKey); + ExFreePool(OriginalIdBuffer); + return; + } + + Status = ZwQueryValueKey(InstanceKey, + &HardwareIdU, + KeyValuePartialInformation, + PartialInfo, + HidLength, + &HidLength); + if (Status != STATUS_SUCCESS) + { + ExFreePool(PartialInfo); + ExFreePool(OriginalIdBuffer); + ZwClose(InstanceKey); + return; + } + + /* Copy in HID info first (without 2nd terminating NULL if CID is present) */ + HidLength = PartialInfo->DataLength - ((CidLength != 0) ? sizeof(WCHAR) : 0); + RtlCopyMemory(IdBuffer, PartialInfo->Data, HidLength); + + if (CidLength != 0) + { + Status = ZwQueryValueKey(InstanceKey, + &CompatibleIdU, + KeyValuePartialInformation, + PartialInfo, + CidLength, + &CidLength); + if (Status != STATUS_SUCCESS) + { + ExFreePool(PartialInfo); + ExFreePool(OriginalIdBuffer); + ZwClose(InstanceKey); + return; + } + + /* Copy CID next */ + CidLength = PartialInfo->DataLength; + RtlCopyMemory(((PUCHAR)IdBuffer) + HidLength, PartialInfo->Data, CidLength); + } + + /* Free our temp buffer */ + ExFreePool(PartialInfo); + + InitializeObjectAttributes(&ObjectAttributes, + &CriticalDeviceKeyU, + OBJ_KERNEL_HANDLE | OBJ_CASE_INSENSITIVE, + NULL, + NULL); + Status = ZwOpenKey(&CriticalDeviceKey, + KEY_ENUMERATE_SUB_KEYS, + &ObjectAttributes); + if (!NT_SUCCESS(Status)) + { + /* The critical device database doesn't exist because + * we're probably in 1st stage setup, but it's ok */ + ExFreePool(OriginalIdBuffer); + ZwClose(InstanceKey); + return; + } + + while (*IdBuffer) + { + ULONG StringLength = (ULONG)wcslen(IdBuffer) + 1, Index; + + IopFixupDeviceId(IdBuffer); + + /* Look through all subkeys for a match */ + for (Index = 0; TRUE; Index++) + { + ULONG NeededLength; + PKEY_BASIC_INFORMATION BasicInfo; + + Status = ZwEnumerateKey(CriticalDeviceKey, + Index, + KeyBasicInformation, + NULL, + 0, + &NeededLength); + if (Status == STATUS_NO_MORE_ENTRIES) + break; + else if (Status == STATUS_BUFFER_OVERFLOW || Status == STATUS_BUFFER_TOO_SMALL) + { + UNICODE_STRING ChildIdNameU, RegKeyNameU; + + BasicInfo = ExAllocatePool(PagedPool, NeededLength); + if (!BasicInfo) + { + /* No memory */ + ExFreePool(OriginalIdBuffer); + ZwClose(CriticalDeviceKey); + ZwClose(InstanceKey); + return; + } + + Status = ZwEnumerateKey(CriticalDeviceKey, + Index, + KeyBasicInformation, + BasicInfo, + NeededLength, + &NeededLength); + if (Status != STATUS_SUCCESS) + { + /* This shouldn't happen */ + ExFreePool(BasicInfo); + continue; + } + + ChildIdNameU.Buffer = IdBuffer; + ChildIdNameU.MaximumLength = ChildIdNameU.Length = (StringLength - 1) * sizeof(WCHAR); + RegKeyNameU.Buffer = BasicInfo->Name; + RegKeyNameU.MaximumLength = RegKeyNameU.Length = BasicInfo->NameLength; + + if (RtlEqualUnicodeString(&ChildIdNameU, &RegKeyNameU, TRUE)) + { + HANDLE ChildKeyHandle; + + InitializeObjectAttributes(&ObjectAttributes, + &ChildIdNameU, + OBJ_KERNEL_HANDLE | OBJ_CASE_INSENSITIVE, + CriticalDeviceKey, + NULL); + + Status = ZwOpenKey(&ChildKeyHandle, + KEY_QUERY_VALUE, + &ObjectAttributes); + if (Status != STATUS_SUCCESS) + { + ExFreePool(BasicInfo); + continue; + } + + /* Check if there's already a driver installed */ + Status = ZwQueryValueKey(InstanceKey, + &ClassGuidU, + KeyValuePartialInformation, + NULL, + 0, + &NeededLength); + if (Status == STATUS_BUFFER_OVERFLOW || Status == STATUS_BUFFER_TOO_SMALL) + { + ExFreePool(BasicInfo); + continue; + } + + Status = ZwQueryValueKey(ChildKeyHandle, + &ClassGuidU, + KeyValuePartialInformation, + NULL, + 0, + &NeededLength); + if (Status != STATUS_BUFFER_OVERFLOW && Status != STATUS_BUFFER_TOO_SMALL) + { + ExFreePool(BasicInfo); + continue; + } + + PartialInfo = ExAllocatePool(PagedPool, NeededLength); + if (!PartialInfo) + { + ExFreePool(OriginalIdBuffer); + ExFreePool(BasicInfo); + ZwClose(InstanceKey); + ZwClose(ChildKeyHandle); + ZwClose(CriticalDeviceKey); + return; + } + + /* Read ClassGUID entry in the CDDB */ + Status = ZwQueryValueKey(ChildKeyHandle, + &ClassGuidU, + KeyValuePartialInformation, + PartialInfo, + NeededLength, + &NeededLength); + if (Status != STATUS_SUCCESS) + { + ExFreePool(BasicInfo); + continue; + } + + /* Write it to the ENUM key */ + Status = ZwSetValueKey(InstanceKey, + &ClassGuidU, + 0, + REG_SZ, + PartialInfo->Data, + PartialInfo->DataLength); + if (Status != STATUS_SUCCESS) + { + ExFreePool(BasicInfo); + ExFreePool(PartialInfo); + ZwClose(ChildKeyHandle); + continue; + } + + Status = ZwQueryValueKey(ChildKeyHandle, + &ServiceU, + KeyValuePartialInformation, + NULL, + 0, + &NeededLength); + if (Status == STATUS_BUFFER_OVERFLOW || Status == STATUS_BUFFER_TOO_SMALL) + { + ExFreePool(PartialInfo); + PartialInfo = ExAllocatePool(PagedPool, NeededLength); + if (!PartialInfo) + { + ExFreePool(OriginalIdBuffer); + ExFreePool(BasicInfo); + ZwClose(InstanceKey); + ZwClose(ChildKeyHandle); + ZwClose(CriticalDeviceKey); + return; + } + + /* Read the service entry from the CDDB */ + Status = ZwQueryValueKey(ChildKeyHandle, + &ServiceU, + KeyValuePartialInformation, + PartialInfo, + NeededLength, + &NeededLength); + if (Status != STATUS_SUCCESS) + { + ExFreePool(BasicInfo); + ExFreePool(PartialInfo); + ZwClose(ChildKeyHandle); + continue; + } + + /* Write it to the ENUM key */ + Status = ZwSetValueKey(InstanceKey, + &ServiceU, + 0, + REG_SZ, + PartialInfo->Data, + PartialInfo->DataLength); + if (Status != STATUS_SUCCESS) + { + ExFreePool(BasicInfo); + ExFreePool(PartialInfo); + ZwClose(ChildKeyHandle); + continue; + } + + DPRINT1("Installed service '%S' for critical device '%wZ'\n", PartialInfo->Data, &ChildIdNameU); + } + else + { + DPRINT1("Installed NULL service for critical device '%wZ'\n", &ChildIdNameU); + } + + /* We need to enumerate children */ + DeviceNode->Flags |= DNF_NEED_TO_ENUM; + + ExFreePool(OriginalIdBuffer); + ExFreePool(PartialInfo); + ExFreePool(BasicInfo); + ZwClose(InstanceKey); + ZwClose(ChildKeyHandle); + ZwClose(CriticalDeviceKey); + + /* That's it */ + return; + } + + ExFreePool(BasicInfo); + } + else + { + /* Umm, not sure what happened here */ + continue; + } + } + + /* Advance to the next ID */ + IdBuffer += StringLength; + } + + ExFreePool(OriginalIdBuffer); + ZwClose(InstanceKey); + ZwClose(CriticalDeviceKey); }
NTSTATUS @@ -1869,6 +2233,8 @@ &DeviceNode->InstancePath); }
+ DeviceNode->Flags &= ~DNF_NEED_TO_ENUM; + DPRINT("Sending IRP_MN_QUERY_DEVICE_RELATIONS to device stack\n");
Stack.Parameters.QueryDeviceRelations.Type = BusRelations; @@ -2052,6 +2418,9 @@ { WCHAR RegKeyBuffer[MAX_PATH]; UNICODE_STRING RegKey; + + /* Install the service for this if it's in the CDDB */ + //IopInstallCriticalDevice(DeviceNode);
RegKey.Length = 0; RegKey.MaximumLength = sizeof(RegKeyBuffer); @@ -2184,7 +2553,25 @@ if (IopDeviceNodeHasFlag(DeviceNode, DNF_STARTED) || IopDeviceNodeHasFlag(DeviceNode, DNF_ADDED) || IopDeviceNodeHasFlag(DeviceNode, DNF_DISABLED)) + { + if (DeviceNode->Flags & DNF_NEED_TO_ENUM) + { + Status = IopInitializeDevice(DeviceNode, NULL); + if (NT_SUCCESS(Status)) + { + /* HACK */ + DeviceNode->Flags &= ~DNF_STARTED; + Status = IopStartDevice(DeviceNode); + if (!NT_SUCCESS(Status)) + { + DPRINT1("IopStartDevice(%wZ) failed with status 0x%08x\n", + &DeviceNode->InstancePath, Status); + } + } + DeviceNode->Flags &= ~DNF_NEED_TO_ENUM; + } return STATUS_SUCCESS; + }
if (DeviceNode->ServiceName.Buffer == NULL) {