https://git.reactos.org/?p=reactos.git;a=commitdiff;h=2674e26cbb0de1ea71c01…
commit 2674e26cbb0de1ea71c01348f46b1b937baae4d5
Author: Hermès Bélusca-Maïto <hermes.belusca-maito(a)reactos.org>
AuthorDate: Sat May 27 22:48:50 2023 +0200
Commit: Hermès Bélusca-Maïto <hermes.belusca-maito(a)reactos.org>
CommitDate: Sun Jun 4 21:40:07 2023 +0200
[NTOS:IO] Reformat iorsrce.c, no functional code changes.
- Fix whitespace; add SAL annotations, doxygen documentation...
- Deduplicate the array of description strings corresponding to
IO_QUERY_DEVICE_DATA_FORMAT.
- Unhardcode the "[3]" into 'IoQueryDeviceMaxData': the maximum
number
of device data queried.
---
ntoskrnl/include/internal/io.h | 16 +-
ntoskrnl/io/iomgr/iorsrce.c | 1703 +++++++++++++++++++++-------------------
sdk/include/xdk/iofuncs.h | 2 +-
3 files changed, 918 insertions(+), 803 deletions(-)
diff --git a/ntoskrnl/include/internal/io.h b/ntoskrnl/include/internal/io.h
index d877bd6fa97..13b0b6364ea 100644
--- a/ntoskrnl/include/internal/io.h
+++ b/ntoskrnl/include/internal/io.h
@@ -1330,17 +1330,17 @@ IopStartRamdisk(
// Configuration Routines
//
NTSTATUS
-NTAPI
-IopFetchConfigurationInformation(OUT PWSTR * SymbolicLinkList,
- IN GUID Guid,
- IN ULONG ExpectedInterfaces,
- IN PULONG Interfaces
+IopFetchConfigurationInformation(
+ _Out_ PWSTR* SymbolicLinkList,
+ _In_ GUID Guid,
+ _In_ ULONG ExpectedInterfaces,
+ _Out_ PULONG Interfaces
);
VOID
-NTAPI
-IopStoreSystemPartitionInformation(IN PUNICODE_STRING NtSystemPartitionDeviceName,
- IN PUNICODE_STRING OsLoaderPathName
+IopStoreSystemPartitionInformation(
+ _In_ PUNICODE_STRING NtSystemPartitionDeviceName,
+ _In_ PUNICODE_STRING OsLoaderPathName
);
//
diff --git a/ntoskrnl/io/iomgr/iorsrce.c b/ntoskrnl/io/iomgr/iorsrce.c
index d3e1abf3039..d5f40023728 100644
--- a/ntoskrnl/io/iomgr/iorsrce.c
+++ b/ntoskrnl/io/iomgr/iorsrce.c
@@ -1,12 +1,12 @@
/*
- * COPYRIGHT: See COPYING in the top level directory
- * PROJECT: ReactOS kernel
- * FILE: ntoskrnl/io/iomgr/iorsrce.c
- * PURPOSE: Hardware resource managment
- *
- * PROGRAMMERS: David Welch (welch(a)mcmail.com)
- * Alex Ionescu (alex(a)relsoft.net)
- * Pierre Schweitzer (pierre.schweitzer(a)reactos.org)
+ * PROJECT: ReactOS Kernel
+ * LICENSE: GPL-2.0-or-later (
https://spdx.org/licenses/GPL-2.0-or-later)
+ * PURPOSE: Hardware resource management
+ * COPYRIGHT: Copyright 1998 David Welch <welch(a)mcmail.com>
+ * Copyright 2001 Eric Kohl <eric.kohl(a)reactos.org>
+ * Copyright 2004-2013 Alex Ionescu <alex.ionescu(a)reactos.org>
+ * Copyright 2010 Cameron Gutman <cameron.gutman(a)reactos.org>
+ * Copyright 2010 Pierre Schweitzer <pierre(a)reactos.org>
*/
/* INCLUDES *****************************************************************/
@@ -19,19 +19,22 @@
static CONFIGURATION_INFORMATION
_SystemConfigurationInformation = { 0, 0, 0, 0, 0, 0, 0, FALSE, FALSE, 0, 0 };
-/* API Parameters to Pass in IopQueryBusDescription */
-typedef struct IO_QUERY {
- PINTERFACE_TYPE BusType;
- PULONG BusNumber;
- PCONFIGURATION_TYPE ControllerType;
- PULONG ControllerNumber;
- PCONFIGURATION_TYPE PeripheralType;
- PULONG PeripheralNumber;
- PIO_QUERY_DEVICE_ROUTINE CalloutRoutine;
- PVOID Context;
+/* API parameters to pass to IopQueryBusDescription() */
+typedef struct _IO_QUERY
+{
+ PINTERFACE_TYPE BusType;
+ PULONG BusNumber;
+ PCONFIGURATION_TYPE ControllerType;
+ PULONG ControllerNumber;
+ PCONFIGURATION_TYPE PeripheralType;
+ PULONG PeripheralNumber;
+ PIO_QUERY_DEVICE_ROUTINE CalloutRoutine;
+ PVOID Context;
} IO_QUERY, *PIO_QUERY;
-PWSTR ArcTypes[42] = {
+/* Strings corresponding to CONFIGURATION_TYPE */
+PCWSTR ArcTypes[MaximumType + 1] =
+{
L"System",
L"CentralProcessor",
L"FloatingPointProcessor",
@@ -76,626 +79,702 @@ PWSTR ArcTypes[42] = {
L"Undefined"
};
+/* Strings corresponding to IO_QUERY_DEVICE_DATA_FORMAT */
+PCWSTR IoDeviceInfoNames[IoQueryDeviceMaxData] =
+{
+ L"Identifier",
+ L"Configuration Data",
+ L"Component Information"
+};
+
/* PRIVATE FUNCTIONS **********************************************************/
-/*
- * IopQueryDeviceDescription
+/**
+ * @brief
+ * Reads and returns Hardware information from the appropriate hardware
+ * registry key. Helper stub of IopQueryBusDescription().
*
- * FUNCTION:
- * Reads and returns Hardware information from the appropriate hardware
- * registry key. Helper sub of IopQueryBusDescription.
+ * @param[in] Query
+ * What the parent function wants.
*
- * ARGUMENTS:
- * Query - What the parent function wants.
- * RootKey - Which key to look in
- * RootKeyHandle - Handle to the key
- * Bus - Bus Number.
- * BusInformation - The Configuration Information Sent
+ * @param[in] RootKey
+ * Which key to look in.
*
- * RETURNS:
- * Status
- */
-
-NTSTATUS NTAPI
+ * @param[in] RootKeyHandle
+ * Handle to the key.
+ *
+ * @param[in] Bus
+ * The bus number.
+ *
+ * @param[in] BusInformation
+ * The configuration information being sent.
+ *
+ * @return A status code.
+ **/
+static NTSTATUS
IopQueryDeviceDescription(
- PIO_QUERY Query,
- UNICODE_STRING RootKey,
- HANDLE RootKeyHandle,
- ULONG Bus,
- PKEY_VALUE_FULL_INFORMATION *BusInformation)
+ _In_ PIO_QUERY Query,
+ _In_ UNICODE_STRING RootKey,
+ _In_ HANDLE RootKeyHandle,
+ _In_ ULONG Bus,
+ _In_ PKEY_VALUE_FULL_INFORMATION* BusInformation)
{
- NTSTATUS Status = STATUS_SUCCESS;
-
- /* Controller Stuff */
- UNICODE_STRING ControllerString;
- UNICODE_STRING ControllerRootRegName = RootKey;
- UNICODE_STRING ControllerRegName;
- HANDLE ControllerKeyHandle;
- PKEY_FULL_INFORMATION ControllerFullInformation = NULL;
- PKEY_VALUE_FULL_INFORMATION ControllerInformation[3] = {NULL, NULL, NULL};
- ULONG ControllerNumber;
- ULONG ControllerLoop;
- ULONG MaximumControllerNumber;
-
- /* Peripheral Stuff */
- UNICODE_STRING PeripheralString;
- HANDLE PeripheralKeyHandle;
- PKEY_FULL_INFORMATION PeripheralFullInformation;
- PKEY_VALUE_FULL_INFORMATION PeripheralInformation[3] = {NULL, NULL, NULL};
- ULONG PeripheralNumber;
- ULONG PeripheralLoop;
- ULONG MaximumPeripheralNumber;
-
- /* Global Registry Stuff */
- OBJECT_ATTRIBUTES ObjectAttributes;
- ULONG LenFullInformation;
- ULONG LenKeyFullInformation;
- UNICODE_STRING TempString;
- WCHAR TempBuffer[14];
- PWSTR Strings[3] = {
- L"Identifier",
- L"Configuration Data",
- L"Component Information"
- };
-
- /* Temporary String */
- TempString.MaximumLength = sizeof(TempBuffer);
- TempString.Length = 0;
- TempString.Buffer = TempBuffer;
-
- /* Add Controller Name to String */
- RtlAppendUnicodeToString(&ControllerRootRegName, L"\\");
- RtlAppendUnicodeToString(&ControllerRootRegName,
ArcTypes[*Query->ControllerType]);
-
- /* Set the Controller Number if specified */
- if (Query->ControllerNumber && *(Query->ControllerNumber))
- {
- ControllerNumber = *Query->ControllerNumber;
- MaximumControllerNumber = ControllerNumber + 1;
- } else {
- /* Find out how many Controller Numbers there are */
- InitializeObjectAttributes(
- &ObjectAttributes,
- &ControllerRootRegName,
- OBJ_CASE_INSENSITIVE,
- NULL,
- NULL);
-
- Status = ZwOpenKey(&ControllerKeyHandle, KEY_READ, &ObjectAttributes);
- if (NT_SUCCESS(Status))
- {
- /* How much buffer space */
- ZwQueryKey(ControllerKeyHandle, KeyFullInformation, NULL, 0,
&LenFullInformation);
-
- /* Allocate it */
- ControllerFullInformation = ExAllocatePoolWithTag(PagedPool, LenFullInformation,
TAG_IO_RESOURCE);
-
- /* Get the Information */
- Status = ZwQueryKey(ControllerKeyHandle, KeyFullInformation,
ControllerFullInformation, LenFullInformation, &LenFullInformation);
- ZwClose(ControllerKeyHandle);
- ControllerKeyHandle = NULL;
- }
-
- /* No controller was found, go back to function. */
- if (!NT_SUCCESS(Status))
- {
- if (ControllerFullInformation != NULL)
- ExFreePoolWithTag(ControllerFullInformation, TAG_IO_RESOURCE);
- return Status;
- }
-
- /* Find out Controller Numbers */
- ControllerNumber = 0;
- MaximumControllerNumber = ControllerFullInformation->SubKeys;
-
- /* Free Memory */
- ExFreePoolWithTag(ControllerFullInformation, TAG_IO_RESOURCE);
- ControllerFullInformation = NULL;
- }
-
- /* Save String */
- ControllerRegName = ControllerRootRegName;
-
- /* Loop through controllers */
- for (; ControllerNumber < MaximumControllerNumber; ControllerNumber++)
- {
- /* Load String */
- ControllerRootRegName = ControllerRegName;
-
- /* Controller Number to Registry String */
- Status = RtlIntegerToUnicodeString(ControllerNumber, 10, &TempString);
-
- /* Create String */
- Status |= RtlAppendUnicodeToString(&ControllerRootRegName, L"\\");
- Status |= RtlAppendUnicodeStringToString(&ControllerRootRegName,
&TempString);
-
- /* Something messed up */
- if (!NT_SUCCESS(Status)) break;
-
- /* Open the Registry Key */
- InitializeObjectAttributes(
- &ObjectAttributes,
- &ControllerRootRegName,
- OBJ_CASE_INSENSITIVE,
- NULL,
- NULL);
-
- Status = ZwOpenKey(&ControllerKeyHandle, KEY_READ, &ObjectAttributes);
-
- /* Read the Configuration Data... */
- if (NT_SUCCESS(Status))
- {
- for (ControllerLoop = 0; ControllerLoop < 3; ControllerLoop++)
- {
- /* Identifier String First */
- RtlInitUnicodeString(&ControllerString, Strings[ControllerLoop]);
-
- /* How much buffer space */
- Status = ZwQueryValueKey(ControllerKeyHandle, &ControllerString,
KeyValueFullInformation, NULL, 0, &LenKeyFullInformation);
-
- if (!NT_SUCCESS(Status) && Status != STATUS_BUFFER_TOO_SMALL
&& Status != STATUS_BUFFER_OVERFLOW)
- continue;
+ NTSTATUS Status = STATUS_SUCCESS;
+
+ /* Controller data */
+ UNICODE_STRING ControllerString;
+ UNICODE_STRING ControllerRootRegName = RootKey;
+ UNICODE_STRING ControllerRegName;
+ HANDLE ControllerKeyHandle;
+ PKEY_FULL_INFORMATION ControllerFullInformation = NULL;
+ PKEY_VALUE_FULL_INFORMATION ControllerInformation[IoQueryDeviceMaxData] =
+ {NULL, NULL, NULL};
+ ULONG ControllerNumber;
+ ULONG ControllerLoop;
+ ULONG MaximumControllerNumber;
+
+ /* Peripheral data */
+ UNICODE_STRING PeripheralString;
+ HANDLE PeripheralKeyHandle;
+ PKEY_FULL_INFORMATION PeripheralFullInformation;
+ PKEY_VALUE_FULL_INFORMATION PeripheralInformation[IoQueryDeviceMaxData] =
+ {NULL, NULL, NULL};
+ ULONG PeripheralNumber;
+ ULONG PeripheralLoop;
+ ULONG MaximumPeripheralNumber;
+
+ /* Global Registry data */
+ OBJECT_ATTRIBUTES ObjectAttributes;
+ ULONG LenFullInformation;
+ ULONG LenKeyFullInformation;
+ UNICODE_STRING TempString;
+ WCHAR TempBuffer[14];
+
+ /* Temporary string */
+ TempString.MaximumLength = sizeof(TempBuffer);
+ TempString.Length = 0;
+ TempString.Buffer = TempBuffer;
+
+ /* Append controller name to string */
+ RtlAppendUnicodeToString(&ControllerRootRegName, L"\\");
+ RtlAppendUnicodeToString(&ControllerRootRegName,
ArcTypes[*Query->ControllerType]);
+
+ /* Set the controller number if specified */
+ if (Query->ControllerNumber && *(Query->ControllerNumber))
+ {
+ ControllerNumber = *Query->ControllerNumber;
+ MaximumControllerNumber = ControllerNumber + 1;
+ }
+ else
+ {
+ /* Find out how many controllers there are */
+ InitializeObjectAttributes(&ObjectAttributes,
+ &ControllerRootRegName,
+ OBJ_CASE_INSENSITIVE,
+ NULL,
+ NULL);
- /* Allocate it */
- ControllerInformation[ControllerLoop] = ExAllocatePoolWithTag(PagedPool,
LenKeyFullInformation, TAG_IO_RESOURCE);
-
- /* Get the Information */
- Status = ZwQueryValueKey(ControllerKeyHandle, &ControllerString,
KeyValueFullInformation, ControllerInformation[ControllerLoop], LenKeyFullInformation,
&LenKeyFullInformation);
- }
-
- /* Clean Up */
- ZwClose(ControllerKeyHandle);
- ControllerKeyHandle = NULL;
- }
-
- /* Something messed up */
- if (!NT_SUCCESS(Status))
- goto EndLoop;
-
- /* We now have Bus *AND* Controller Information.. is it enough? */
- if (!Query->PeripheralType || !(*Query->PeripheralType))
- {
- Status = Query->CalloutRoutine(
- Query->Context,
- &ControllerRootRegName,
- *Query->BusType,
- Bus,
- BusInformation,
- *Query->ControllerType,
- ControllerNumber,
- ControllerInformation,
- 0,
- 0,
- NULL);
- goto EndLoop;
- }
-
- /* Not enough...caller also wants peripheral name */
- Status = RtlAppendUnicodeToString(&ControllerRootRegName, L"\\");
- Status |= RtlAppendUnicodeToString(&ControllerRootRegName,
ArcTypes[*Query->PeripheralType]);
-
- /* Something messed up */
- if (!NT_SUCCESS(Status)) goto EndLoop;
-
- /* Set the Peripheral Number if specified */
- if (Query->PeripheralNumber && *Query->PeripheralNumber)
- {
- PeripheralNumber = *Query->PeripheralNumber;
- MaximumPeripheralNumber = PeripheralNumber + 1;
- } else {
- /* Find out how many Peripheral Numbers there are */
- InitializeObjectAttributes(
- &ObjectAttributes,
- &ControllerRootRegName,
- OBJ_CASE_INSENSITIVE,
- NULL,
- NULL);
-
- Status = ZwOpenKey(&PeripheralKeyHandle, KEY_READ, &ObjectAttributes);
-
- if (NT_SUCCESS(Status))
- {
- /* How much buffer space */
- ZwQueryKey(PeripheralKeyHandle, KeyFullInformation, NULL, 0,
&LenFullInformation);
+ Status = ZwOpenKey(&ControllerKeyHandle, KEY_READ, &ObjectAttributes);
+
+ if (NT_SUCCESS(Status))
+ {
+ /* Retrieve the necessary buffer space */
+ ZwQueryKey(ControllerKeyHandle,
+ KeyFullInformation,
+ NULL, 0,
+ &LenFullInformation);
/* Allocate it */
- PeripheralFullInformation = ExAllocatePoolWithTag(PagedPool,
LenFullInformation, TAG_IO_RESOURCE);
-
- /* Get the Information */
- Status = ZwQueryKey(PeripheralKeyHandle, KeyFullInformation,
PeripheralFullInformation, LenFullInformation, &LenFullInformation);
- ZwClose(PeripheralKeyHandle);
- PeripheralKeyHandle = NULL;
- }
-
- /* No controller was found, go back to function but clean up first */
- if (!NT_SUCCESS(Status))
- {
- Status = STATUS_SUCCESS;
- goto EndLoop;
- }
+ ControllerFullInformation = ExAllocatePoolWithTag(PagedPool,
LenFullInformation, TAG_IO_RESOURCE);
+
+ /* Get the information */
+ Status = ZwQueryKey(ControllerKeyHandle,
+ KeyFullInformation,
+ ControllerFullInformation,
+ LenFullInformation,
+ &LenFullInformation);
+ ZwClose(ControllerKeyHandle);
+ ControllerKeyHandle = NULL;
+ }
+
+ /* No controller was found, bail out */
+ if (!NT_SUCCESS(Status))
+ {
+ if (ControllerFullInformation != NULL)
+ ExFreePoolWithTag(ControllerFullInformation, TAG_IO_RESOURCE);
+ return Status;
+ }
- /* Find out Peripheral Number */
- PeripheralNumber = 0;
- MaximumPeripheralNumber = PeripheralFullInformation->SubKeys;
+ /* Find out the controllers */
+ ControllerNumber = 0;
+ MaximumControllerNumber = ControllerFullInformation->SubKeys;
- /* Free Memory */
- ExFreePoolWithTag(PeripheralFullInformation, TAG_IO_RESOURCE);
- PeripheralFullInformation = NULL;
- }
+ /* Cleanup */
+ ExFreePoolWithTag(ControllerFullInformation, TAG_IO_RESOURCE);
+ ControllerFullInformation = NULL;
+ }
- /* Save Name */
- ControllerRegName = ControllerRootRegName;
+ /* Save string */
+ ControllerRegName = ControllerRootRegName;
- /* Loop through Peripherals */
- for (; PeripheralNumber < MaximumPeripheralNumber; PeripheralNumber++)
- {
- /* Restore Name */
- ControllerRootRegName = ControllerRegName;
+ /* Loop through controllers */
+ for (; ControllerNumber < MaximumControllerNumber; ControllerNumber++)
+ {
+ /* Load string */
+ ControllerRootRegName = ControllerRegName;
- /* Peripheral Number to Registry String */
- Status = RtlIntegerToUnicodeString(PeripheralNumber, 10, &TempString);
+ /* Convert controller number to registry string */
+ Status = RtlIntegerToUnicodeString(ControllerNumber, 10, &TempString);
- /* Create String */
- Status |= RtlAppendUnicodeToString(&ControllerRootRegName,
L"\\");
- Status |= RtlAppendUnicodeStringToString(&ControllerRootRegName,
&TempString);
+ /* Create string */
+ Status |= RtlAppendUnicodeToString(&ControllerRootRegName,
L"\\");
+ Status |= RtlAppendUnicodeStringToString(&ControllerRootRegName,
&TempString);
- /* Something messed up */
- if (!NT_SUCCESS(Status)) break;
+ /* Something messed up */
+ if (!NT_SUCCESS(Status))
+ break;
- /* Open the Registry Key */
- InitializeObjectAttributes(
- &ObjectAttributes,
- &ControllerRootRegName,
- OBJ_CASE_INSENSITIVE,
- NULL,
- NULL);
+ /* Open the registry key */
+ InitializeObjectAttributes(&ObjectAttributes,
+ &ControllerRootRegName,
+ OBJ_CASE_INSENSITIVE,
+ NULL,
+ NULL);
- Status = ZwOpenKey(&PeripheralKeyHandle, KEY_READ, &ObjectAttributes);
+ Status = ZwOpenKey(&ControllerKeyHandle, KEY_READ, &ObjectAttributes);
- if (NT_SUCCESS(Status))
- {
- for (PeripheralLoop = 0; PeripheralLoop < 3; PeripheralLoop++)
+ /* Read the configuration data */
+ if (NT_SUCCESS(Status))
+ {
+ for (ControllerLoop = 0; ControllerLoop <
RTL_NUMBER_OF(IoDeviceInfoNames); ControllerLoop++)
{
- /* Identifier String First */
- RtlInitUnicodeString(&PeripheralString, Strings[PeripheralLoop]);
+ /* Identifier string first */
+ RtlInitUnicodeString(&ControllerString,
IoDeviceInfoNames[ControllerLoop]);
+
+ /* Retrieve the necessary buffer space */
+ Status = ZwQueryValueKey(ControllerKeyHandle,
+ &ControllerString,
+ KeyValueFullInformation,
+ NULL, 0,
+ &LenKeyFullInformation);
+
+ if (!NT_SUCCESS(Status) &&
+ (Status != STATUS_BUFFER_TOO_SMALL) &&
+ (Status != STATUS_BUFFER_OVERFLOW))
+ {
+ continue;
+ }
+
+ /* Allocate it */
+ ControllerInformation[ControllerLoop] = ExAllocatePoolWithTag(PagedPool,
LenKeyFullInformation, TAG_IO_RESOURCE);
+
+ /* Get the information */
+ Status = ZwQueryValueKey(ControllerKeyHandle,
+ &ControllerString,
+ KeyValueFullInformation,
+ ControllerInformation[ControllerLoop],
+ LenKeyFullInformation,
+ &LenKeyFullInformation);
+ }
- /* How much buffer space */
- Status = ZwQueryValueKey(PeripheralKeyHandle, &PeripheralString,
KeyValueFullInformation, NULL, 0, &LenKeyFullInformation);
+ /* Cleanup */
+ ZwClose(ControllerKeyHandle);
+ ControllerKeyHandle = NULL;
+ }
- if (!NT_SUCCESS(Status) && Status != STATUS_BUFFER_TOO_SMALL
&& Status != STATUS_BUFFER_OVERFLOW)
- {
- PeripheralInformation[PeripheralLoop] = NULL;
- continue;
- }
+ /* Something messed up */
+ if (!NT_SUCCESS(Status))
+ goto EndLoop;
- /* Allocate it */
- PeripheralInformation[PeripheralLoop] = ExAllocatePoolWithTag(PagedPool,
LenKeyFullInformation, TAG_IO_RESOURCE);
+ /* We now have bus *AND* controller information, is it enough? */
+ if (!Query->PeripheralType || !(*Query->PeripheralType))
+ {
+ Status = Query->CalloutRoutine(Query->Context,
+ &ControllerRootRegName,
+ *Query->BusType,
+ Bus,
+ BusInformation,
+ *Query->ControllerType,
+ ControllerNumber,
+ ControllerInformation,
+ 0,
+ 0,
+ NULL);
+ goto EndLoop;
+ }
- /* Get the Information */
- Status = ZwQueryValueKey(PeripheralKeyHandle, &PeripheralString,
KeyValueFullInformation, PeripheralInformation[PeripheralLoop], LenKeyFullInformation,
&LenKeyFullInformation);
- }
+ /* Not enough: the caller also wants peripheral name */
+ Status = RtlAppendUnicodeToString(&ControllerRootRegName, L"\\");
+ Status |= RtlAppendUnicodeToString(&ControllerRootRegName,
ArcTypes[*Query->PeripheralType]);
- /* Clean Up */
- ZwClose(PeripheralKeyHandle);
- PeripheralKeyHandle = NULL;
+ /* Something messed up */
+ if (!NT_SUCCESS(Status))
+ goto EndLoop;
+
+ /* Set the peripheral number if specified */
+ if (Query->PeripheralNumber && *Query->PeripheralNumber)
+ {
+ PeripheralNumber = *Query->PeripheralNumber;
+ MaximumPeripheralNumber = PeripheralNumber + 1;
+ }
+ else
+ {
+ /* Find out how many peripherals there are */
+ InitializeObjectAttributes(&ObjectAttributes,
+ &ControllerRootRegName,
+ OBJ_CASE_INSENSITIVE,
+ NULL,
+ NULL);
+
+ Status = ZwOpenKey(&PeripheralKeyHandle, KEY_READ,
&ObjectAttributes);
- /* We now have everything the caller could possibly want */
if (NT_SUCCESS(Status))
{
- Status = Query->CalloutRoutine(
- Query->Context,
- &ControllerRootRegName,
- *Query->BusType,
- Bus,
- BusInformation,
- *Query->ControllerType,
- ControllerNumber,
- ControllerInformation,
- *Query->PeripheralType,
- PeripheralNumber,
- PeripheralInformation);
+ /* Retrieve the necessary buffer space */
+ ZwQueryKey(PeripheralKeyHandle,
+ KeyFullInformation,
+ NULL, 0,
+ &LenFullInformation);
+
+ /* Allocate it */
+ PeripheralFullInformation = ExAllocatePoolWithTag(PagedPool,
LenFullInformation, TAG_IO_RESOURCE);
+
+ /* Get the information */
+ Status = ZwQueryKey(PeripheralKeyHandle,
+ KeyFullInformation,
+ PeripheralFullInformation,
+ LenFullInformation,
+ &LenFullInformation);
+ ZwClose(PeripheralKeyHandle);
+ PeripheralKeyHandle = NULL;
}
- /* Free the allocated memory */
- for (PeripheralLoop = 0; PeripheralLoop < 3; PeripheralLoop++)
+ /* No controller was found, cleanup and bail out */
+ if (!NT_SUCCESS(Status))
{
- if (PeripheralInformation[PeripheralLoop])
- {
- ExFreePoolWithTag(PeripheralInformation[PeripheralLoop],
TAG_IO_RESOURCE);
- PeripheralInformation[PeripheralLoop] = NULL;
- }
+ Status = STATUS_SUCCESS;
+ goto EndLoop;
}
- /* Something Messed up */
- if (!NT_SUCCESS(Status)) break;
- }
- }
+ /* Find out peripheral number */
+ PeripheralNumber = 0;
+ MaximumPeripheralNumber = PeripheralFullInformation->SubKeys;
+
+ /* Cleanup */
+ ExFreePoolWithTag(PeripheralFullInformation, TAG_IO_RESOURCE);
+ PeripheralFullInformation = NULL;
+ }
+
+ /* Save name */
+ ControllerRegName = ControllerRootRegName;
+
+ /* Loop through peripherals */
+ for (; PeripheralNumber < MaximumPeripheralNumber; PeripheralNumber++)
+ {
+ /* Restore name */
+ ControllerRootRegName = ControllerRegName;
+
+ /* Convert peripheral number to registry string */
+ Status = RtlIntegerToUnicodeString(PeripheralNumber, 10, &TempString);
+
+ /* Create string */
+ Status |= RtlAppendUnicodeToString(&ControllerRootRegName,
L"\\");
+ Status |= RtlAppendUnicodeStringToString(&ControllerRootRegName,
&TempString);
+
+ /* Something messed up */
+ if (!NT_SUCCESS(Status))
+ break;
+
+ /* Open the registry key */
+ InitializeObjectAttributes(&ObjectAttributes,
+ &ControllerRootRegName,
+ OBJ_CASE_INSENSITIVE,
+ NULL,
+ NULL);
+
+ Status = ZwOpenKey(&PeripheralKeyHandle, KEY_READ,
&ObjectAttributes);
+
+ if (NT_SUCCESS(Status))
+ {
+ for (PeripheralLoop = 0; PeripheralLoop <
RTL_NUMBER_OF(IoDeviceInfoNames); PeripheralLoop++)
+ {
+ /* Identifier string first */
+ RtlInitUnicodeString(&PeripheralString,
IoDeviceInfoNames[PeripheralLoop]);
+
+ /* Retrieve the necessary buffer space */
+ Status = ZwQueryValueKey(PeripheralKeyHandle,
+ &PeripheralString,
+ KeyValueFullInformation,
+ NULL, 0,
+ &LenKeyFullInformation);
+
+ if (!NT_SUCCESS(Status) &&
+ (Status != STATUS_BUFFER_TOO_SMALL) &&
+ (Status != STATUS_BUFFER_OVERFLOW))
+ {
+ PeripheralInformation[PeripheralLoop] = NULL;
+ continue;
+ }
+
+ /* Allocate it */
+ PeripheralInformation[PeripheralLoop] =
ExAllocatePoolWithTag(PagedPool, LenKeyFullInformation, TAG_IO_RESOURCE);
+
+ /* Get the information */
+ Status = ZwQueryValueKey(PeripheralKeyHandle,
+ &PeripheralString,
+ KeyValueFullInformation,
+ PeripheralInformation[PeripheralLoop],
+ LenKeyFullInformation,
+ &LenKeyFullInformation);
+ }
+
+ /* Cleanup */
+ ZwClose(PeripheralKeyHandle);
+ PeripheralKeyHandle = NULL;
+
+ /* We now have everything the caller could possibly want */
+ if (NT_SUCCESS(Status))
+ {
+ Status = Query->CalloutRoutine(Query->Context,
+ &ControllerRootRegName,
+ *Query->BusType,
+ Bus,
+ BusInformation,
+ *Query->ControllerType,
+ ControllerNumber,
+ ControllerInformation,
+ *Query->PeripheralType,
+ PeripheralNumber,
+ PeripheralInformation);
+ }
+
+ /* Free the allocated memory */
+ for (PeripheralLoop = 0; PeripheralLoop <
RTL_NUMBER_OF(IoDeviceInfoNames); PeripheralLoop++)
+ {
+ if (PeripheralInformation[PeripheralLoop])
+ {
+ ExFreePoolWithTag(PeripheralInformation[PeripheralLoop],
TAG_IO_RESOURCE);
+ PeripheralInformation[PeripheralLoop] = NULL;
+ }
+ }
+
+ /* Something messed up */
+ if (!NT_SUCCESS(Status))
+ break;
+ }
+ }
EndLoop:
- /* Free the allocated memory */
- for (ControllerLoop = 0; ControllerLoop < 3; ControllerLoop++)
- {
- if (ControllerInformation[ControllerLoop])
- {
- ExFreePoolWithTag(ControllerInformation[ControllerLoop], TAG_IO_RESOURCE);
- ControllerInformation[ControllerLoop] = NULL;
- }
- }
-
- /* Something Messed up */
- if (!NT_SUCCESS(Status)) break;
- }
-
- return Status;
+ /* Free the allocated memory */
+ for (ControllerLoop = 0; ControllerLoop < RTL_NUMBER_OF(IoDeviceInfoNames);
ControllerLoop++)
+ {
+ if (ControllerInformation[ControllerLoop])
+ {
+ ExFreePoolWithTag(ControllerInformation[ControllerLoop],
TAG_IO_RESOURCE);
+ ControllerInformation[ControllerLoop] = NULL;
+ }
+ }
+
+ /* Something messed up */
+ if (!NT_SUCCESS(Status))
+ break;
+ }
+
+ return Status;
}
-/*
- * IopQueryBusDescription
+/**
+ * @brief
+ * Reads and returns Hardware information from the appropriate hardware
+ * registry key. Helper stub of IoQueryDeviceDescription(). Has two modes
+ * of operation, either looking for root bus types or for sub-bus
+ * information.
*
- * FUNCTION:
- * Reads and returns Hardware information from the appropriate hardware
- * registry key. Helper sub of IoQueryDeviceDescription. Has two modes
- * of operation, either looking for Root Bus Types or for sub-Bus
- * information.
+ * @param[in] Query
+ * What the parent function wants.
*
- * ARGUMENTS:
- * Query - What the parent function wants.
- * RootKey - Which key to look in
- * RootKeyHandle - Handle to the key
- * Bus - Bus Number.
- * KeyIsRoot - Whether we are looking for Root Bus Types or
- * information under them.
+ * @param[in] RootKey
+ * Which key to look in.
*
- * RETURNS:
- * Status
- */
-
-NTSTATUS NTAPI
+ * @param[in] RootKeyHandle
+ * Handle to the key.
+ *
+ * @param[in,out] Bus
+ * Pointer to the current bus number.
+ *
+ * @param[in] KeyIsRoot
+ * Whether we are looking for root bus types or information under them.
+ *
+ * @return A status code.
+ **/
+static NTSTATUS
IopQueryBusDescription(
- PIO_QUERY Query,
- UNICODE_STRING RootKey,
- HANDLE RootKeyHandle,
- PULONG Bus,
- BOOLEAN KeyIsRoot)
+ _In_ PIO_QUERY Query,
+ _In_ UNICODE_STRING RootKey,
+ _In_ HANDLE RootKeyHandle,
+ _Inout_ PULONG Bus,
+ _In_ BOOLEAN KeyIsRoot)
{
- NTSTATUS Status;
- ULONG BusLoop;
- UNICODE_STRING SubRootRegName;
- UNICODE_STRING BusString;
- UNICODE_STRING SubBusString;
- ULONG LenBasicInformation = 0;
- ULONG LenFullInformation;
- ULONG LenKeyFullInformation;
- ULONG LenKey;
- HANDLE SubRootKeyHandle;
- PKEY_FULL_INFORMATION FullInformation;
- PKEY_BASIC_INFORMATION BasicInformation = NULL;
- OBJECT_ATTRIBUTES ObjectAttributes;
- PKEY_VALUE_FULL_INFORMATION BusInformation[3] = {NULL, NULL, NULL};
-
- /* How much buffer space */
- Status = ZwQueryKey(RootKeyHandle, KeyFullInformation, NULL, 0,
&LenFullInformation);
-
- if (!NT_SUCCESS(Status) && Status != STATUS_BUFFER_TOO_SMALL && Status
!= STATUS_BUFFER_OVERFLOW)
- return Status;
-
- /* Allocate it */
- FullInformation = ExAllocatePoolWithTag(PagedPool, LenFullInformation,
TAG_IO_RESOURCE);
-
- if (!FullInformation)
- return STATUS_NO_MEMORY;
-
- /* Get the Information */
- Status = ZwQueryKey(RootKeyHandle, KeyFullInformation, FullInformation,
LenFullInformation, &LenFullInformation);
-
- /* Everything was fine */
- if (NT_SUCCESS(Status))
- {
- /* Buffer needed for all the keys under this one */
- LenBasicInformation = FullInformation->MaxNameLen +
sizeof(KEY_BASIC_INFORMATION);
-
- /* Allocate it */
- BasicInformation = ExAllocatePoolWithTag(PagedPool, LenBasicInformation,
TAG_IO_RESOURCE);
- }
-
- /* Deallocate the old Buffer */
- ExFreePoolWithTag(FullInformation, TAG_IO_RESOURCE);
-
- /* Try to find a Bus */
- for (BusLoop = 0; NT_SUCCESS(Status); BusLoop++)
- {
- /* Bus parameter was passed and number was matched */
- if ((Query->BusNumber) && (*(Query->BusNumber)) == *Bus) break;
-
- /* Enumerate the Key */
- Status = ZwEnumerateKey(
- RootKeyHandle,
- BusLoop,
- KeyBasicInformation,
- BasicInformation,
- LenBasicInformation,
- &LenKey);
-
- /* Everything enumerated */
- if (!NT_SUCCESS(Status)) break;
-
- /* What Bus are we going to go down? (only check if this is a Root Key) */
- if (KeyIsRoot)
- {
- if (wcsncmp(BasicInformation->Name, L"MultifunctionAdapter",
BasicInformation->NameLength / 2) &&
- wcsncmp(BasicInformation->Name, L"EisaAdapter",
BasicInformation->NameLength / 2) &&
- wcsncmp(BasicInformation->Name, L"TcAdapter",
BasicInformation->NameLength / 2))
- {
- /* Nothing found, check next */
+ NTSTATUS Status;
+ ULONG BusLoop;
+ UNICODE_STRING SubRootRegName;
+ UNICODE_STRING BusString;
+ UNICODE_STRING SubBusString;
+ ULONG LenBasicInformation = 0;
+ ULONG LenFullInformation;
+ ULONG LenKeyFullInformation;
+ ULONG LenKey;
+ HANDLE SubRootKeyHandle;
+ PKEY_FULL_INFORMATION FullInformation;
+ PKEY_BASIC_INFORMATION BasicInformation = NULL;
+ OBJECT_ATTRIBUTES ObjectAttributes;
+ PKEY_VALUE_FULL_INFORMATION BusInformation[IoQueryDeviceMaxData] =
+ {NULL, NULL, NULL};
+
+ /* Retrieve the necessary buffer space */
+ Status = ZwQueryKey(RootKeyHandle,
+ KeyFullInformation,
+ NULL, 0,
+ &LenFullInformation);
+
+ if (!NT_SUCCESS(Status) &&
+ (Status != STATUS_BUFFER_TOO_SMALL) &&
+ (Status != STATUS_BUFFER_OVERFLOW))
+ {
+ return Status;
+ }
+
+ /* Allocate it */
+ FullInformation = ExAllocatePoolWithTag(PagedPool, LenFullInformation,
TAG_IO_RESOURCE);
+
+ if (!FullInformation)
+ return STATUS_NO_MEMORY;
+
+ /* Get the information */
+ Status = ZwQueryKey(RootKeyHandle,
+ KeyFullInformation,
+ FullInformation,
+ LenFullInformation,
+ &LenFullInformation);
+ if (NT_SUCCESS(Status))
+ {
+ /* Buffer needed for all the keys under this one */
+ LenBasicInformation = FullInformation->MaxNameLen +
sizeof(KEY_BASIC_INFORMATION);
+
+ /* Allocate it */
+ BasicInformation = ExAllocatePoolWithTag(PagedPool, LenBasicInformation,
TAG_IO_RESOURCE);
+ }
+
+ /* Deallocate the old buffer */
+ ExFreePoolWithTag(FullInformation, TAG_IO_RESOURCE);
+
+ /* Try to find a bus */
+ for (BusLoop = 0; NT_SUCCESS(Status); BusLoop++)
+ {
+ /* Bus parameter was passed and number was matched */
+ if (Query->BusNumber && (*(Query->BusNumber) == *Bus))
+ break;
+
+ /* Enumerate the Key */
+ Status = ZwEnumerateKey(RootKeyHandle,
+ BusLoop,
+ KeyBasicInformation,
+ BasicInformation,
+ LenBasicInformation,
+ &LenKey);
+
+ /* Stop if everything was enumerated */
+ if (!NT_SUCCESS(Status))
+ break;
+
+ /* What bus are we going to go down? (only check if this is a root key) */
+ if (KeyIsRoot)
+ {
+ if (wcsncmp(BasicInformation->Name, L"MultifunctionAdapter",
BasicInformation->NameLength / sizeof(WCHAR)) &&
+ wcsncmp(BasicInformation->Name, L"EisaAdapter",
BasicInformation->NameLength / sizeof(WCHAR)) &&
+ wcsncmp(BasicInformation->Name, L"TcAdapter",
BasicInformation->NameLength / sizeof(WCHAR)))
+ {
+ /* Nothing found, check next */
+ continue;
+ }
+ }
+
+ /* Enumerate the bus */
+ BusString.Buffer = BasicInformation->Name;
+ BusString.Length = (USHORT)BasicInformation->NameLength;
+ BusString.MaximumLength = (USHORT)BasicInformation->NameLength;
+
+ /* Open a handle to the root registry key */
+ InitializeObjectAttributes(&ObjectAttributes,
+ &BusString,
+ OBJ_CASE_INSENSITIVE,
+ RootKeyHandle,
+ NULL);
+
+ Status = ZwOpenKey(&SubRootKeyHandle, KEY_READ, &ObjectAttributes);
+
+ /* Go on if we failed */
+ if (!NT_SUCCESS(Status))
continue;
- }
- }
-
- /* Enumerate the Bus. */
- BusString.Buffer = BasicInformation->Name;
- BusString.Length = (USHORT)BasicInformation->NameLength;
- BusString.MaximumLength = (USHORT)BasicInformation->NameLength;
-
- /* Open a handle to the Root Registry Key */
- InitializeObjectAttributes(
- &ObjectAttributes,
- &BusString,
- OBJ_CASE_INSENSITIVE,
- RootKeyHandle,
- NULL);
-
- Status = ZwOpenKey(&SubRootKeyHandle, KEY_READ, &ObjectAttributes);
-
- /* Go on if we can't */
- if (!NT_SUCCESS(Status)) continue;
-
- /* Key opened. Create the path */
- SubRootRegName = RootKey;
- RtlAppendUnicodeToString(&SubRootRegName, L"\\");
- RtlAppendUnicodeStringToString(&SubRootRegName, &BusString);
-
- if (!KeyIsRoot)
- {
- /* Parsing a SubBus-key */
- int SubBusLoop;
- PWSTR Strings[3] = {
- L"Identifier",
- L"Configuration Data",
- L"Component Information"};
-
- for (SubBusLoop = 0; SubBusLoop < 3; SubBusLoop++)
- {
- /* Identifier String First */
- RtlInitUnicodeString(&SubBusString, Strings[SubBusLoop]);
-
- /* How much buffer space */
- ZwQueryValueKey(SubRootKeyHandle, &SubBusString, KeyValueFullInformation,
NULL, 0, &LenKeyFullInformation);
- /* Allocate it */
- BusInformation[SubBusLoop] = ExAllocatePoolWithTag(PagedPool,
LenKeyFullInformation, TAG_IO_RESOURCE);
-
- /* Get the Information */
- Status = ZwQueryValueKey(SubRootKeyHandle, &SubBusString,
KeyValueFullInformation, BusInformation[SubBusLoop], LenKeyFullInformation,
&LenKeyFullInformation);
- }
-
- if (NT_SUCCESS(Status))
- {
- /* Do we have something */
- if (BusInformation[1] != NULL &&
- BusInformation[1]->DataLength != 0 &&
- /* Does it match what we want? */
- (((PCM_FULL_RESOURCE_DESCRIPTOR)((ULONG_PTR)BusInformation[1] +
BusInformation[1]->DataOffset))->InterfaceType == *(Query->BusType)))
+ /* Key opened, create the path */
+ SubRootRegName = RootKey;
+ RtlAppendUnicodeToString(&SubRootRegName, L"\\");
+ RtlAppendUnicodeStringToString(&SubRootRegName, &BusString);
+
+ if (!KeyIsRoot)
+ {
+ /* Parsing a sub-bus key */
+ ULONG SubBusLoop;
+ for (SubBusLoop = 0; SubBusLoop < RTL_NUMBER_OF(IoDeviceInfoNames);
SubBusLoop++)
{
- /* Found a bus */
- (*Bus)++;
-
- /* Is it the bus we wanted */
- if (Query->BusNumber == NULL || *(Query->BusNumber) == *Bus)
- {
- /* If we don't want Controller Information, we're done... call
the callback */
- if (Query->ControllerType == NULL)
- {
- Status = Query->CalloutRoutine(
- Query->Context,
- &SubRootRegName,
- *(Query->BusType),
- *Bus,
- BusInformation,
- 0,
- 0,
- NULL,
- 0,
- 0,
- NULL);
- } else {
- /* We want Controller Info...get it */
- Status = IopQueryDeviceDescription(Query, SubRootRegName,
RootKeyHandle, *Bus, (PKEY_VALUE_FULL_INFORMATION*)BusInformation);
- }
- }
+ /* Identifier string first */
+ RtlInitUnicodeString(&SubBusString, IoDeviceInfoNames[SubBusLoop]);
+
+ /* Retrieve the necessary buffer space */
+ ZwQueryValueKey(SubRootKeyHandle,
+ &SubBusString,
+ KeyValueFullInformation,
+ NULL, 0,
+ &LenKeyFullInformation);
+
+ /* Allocate it */
+ BusInformation[SubBusLoop] = ExAllocatePoolWithTag(PagedPool,
LenKeyFullInformation, TAG_IO_RESOURCE);
+
+ /* Get the information */
+ Status = ZwQueryValueKey(SubRootKeyHandle,
+ &SubBusString,
+ KeyValueFullInformation,
+ BusInformation[SubBusLoop],
+ LenKeyFullInformation,
+ &LenKeyFullInformation);
}
- }
- /* Free the allocated memory */
- for (SubBusLoop = 0; SubBusLoop < 3; SubBusLoop++)
- {
- if (BusInformation[SubBusLoop])
+ if (NT_SUCCESS(Status))
{
- ExFreePoolWithTag(BusInformation[SubBusLoop], TAG_IO_RESOURCE);
- BusInformation[SubBusLoop] = NULL;
+ PKEY_VALUE_FULL_INFORMATION BusConfigData =
+ BusInformation[IoQueryDeviceConfigurationData];
+
+ /* Do we have something? */
+ if (BusConfigData != NULL &&
+ BusConfigData->DataLength != 0 &&
+ /* Does it match what we want? */
+ (((PCM_FULL_RESOURCE_DESCRIPTOR)((ULONG_PTR)BusConfigData +
+ BusConfigData->DataOffset))->InterfaceType ==
*(Query->BusType)))
+ {
+ /* Found a bus */
+ (*Bus)++;
+
+ /* Is it the bus we wanted? */
+ if (Query->BusNumber == NULL || *(Query->BusNumber) == *Bus)
+ {
+ if (Query->ControllerType == NULL)
+ {
+ /* We don't want controller information: call the
callback */
+ Status = Query->CalloutRoutine(Query->Context,
+ &SubRootRegName,
+ *(Query->BusType),
+ *Bus,
+ BusInformation,
+ 0,
+ 0,
+ NULL,
+ 0,
+ 0,
+ NULL);
+ }
+ else
+ {
+ /* We want controller information: get it */
+ Status = IopQueryDeviceDescription(Query,
+ SubRootRegName,
+ RootKeyHandle,
+ *Bus,
+
(PKEY_VALUE_FULL_INFORMATION*)BusInformation);
+ }
+ }
+ }
}
- }
- /* Exit the Loop if we found the bus */
- if (Query->BusNumber != NULL && *(Query->BusNumber) == *Bus)
- {
- ZwClose(SubRootKeyHandle);
- SubRootKeyHandle = NULL;
- continue;
- }
- }
+ /* Free the allocated memory */
+ for (SubBusLoop = 0; SubBusLoop < RTL_NUMBER_OF(IoDeviceInfoNames);
SubBusLoop++)
+ {
+ if (BusInformation[SubBusLoop])
+ {
+ ExFreePoolWithTag(BusInformation[SubBusLoop], TAG_IO_RESOURCE);
+ BusInformation[SubBusLoop] = NULL;
+ }
+ }
- /* Enumerate the buses below us recursively if we haven't found the bus yet
*/
- Status = IopQueryBusDescription(Query, SubRootRegName, SubRootKeyHandle, Bus,
!KeyIsRoot);
+ /* Exit the loop if we found the bus */
+ if (Query->BusNumber && (*(Query->BusNumber) == *Bus))
+ {
+ ZwClose(SubRootKeyHandle);
+ SubRootKeyHandle = NULL;
+ continue;
+ }
+ }
+
+ /* Enumerate the buses below us recursively if we haven't found the bus yet
*/
+ Status = IopQueryBusDescription(Query, SubRootRegName, SubRootKeyHandle, Bus,
!KeyIsRoot);
- /* Everything enumerated */
- if (Status == STATUS_NO_MORE_ENTRIES) Status = STATUS_SUCCESS;
+ /* Everything enumerated */
+ if (Status == STATUS_NO_MORE_ENTRIES) Status = STATUS_SUCCESS;
- ZwClose(SubRootKeyHandle);
- SubRootKeyHandle = NULL;
- }
+ ZwClose(SubRootKeyHandle);
+ SubRootKeyHandle = NULL;
+ }
- /* Free the last remaining Allocated Memory */
- if (BasicInformation)
- ExFreePoolWithTag(BasicInformation, TAG_IO_RESOURCE);
+ /* Free the last remaining allocated memory */
+ if (BasicInformation)
+ ExFreePoolWithTag(BasicInformation, TAG_IO_RESOURCE);
- return Status;
+ return Status;
}
NTSTATUS
-NTAPI
-IopFetchConfigurationInformation(OUT PWSTR * SymbolicLinkList,
- IN GUID Guid,
- IN ULONG ExpectedInterfaces,
- IN PULONG Interfaces)
+IopFetchConfigurationInformation(
+ _Out_ PWSTR* SymbolicLinkList,
+ _In_ GUID Guid,
+ _In_ ULONG ExpectedInterfaces,
+ _Out_ PULONG Interfaces)
{
NTSTATUS Status;
- ULONG IntInterfaces = 0;
- PWSTR IntSymbolicLinkList;
+ ULONG interfaces = 0;
+ PWSTR symbolicLinkList;
/* Get the associated enabled interfaces with the given GUID */
Status = IoGetDeviceInterfaces(&Guid, NULL, 0, SymbolicLinkList);
if (!NT_SUCCESS(Status))
{
/* Zero output and leave */
- if (SymbolicLinkList != 0)
- {
- *SymbolicLinkList = 0;
- }
+ if (SymbolicLinkList)
+ *SymbolicLinkList = NULL;
return STATUS_UNSUCCESSFUL;
}
- IntSymbolicLinkList = *SymbolicLinkList;
+ symbolicLinkList = *SymbolicLinkList;
/* Count the number of enabled interfaces by counting the number of symbolic links
*/
- while (*IntSymbolicLinkList != UNICODE_NULL)
+ while (*symbolicLinkList != UNICODE_NULL)
{
- IntInterfaces++;
- IntSymbolicLinkList += wcslen(IntSymbolicLinkList) + (sizeof(UNICODE_NULL) /
sizeof(WCHAR));
+ interfaces++;
+ symbolicLinkList += (wcslen(symbolicLinkList) + 1);
}
/* Matching result will define the result */
- Status = (IntInterfaces >= ExpectedInterfaces) ? STATUS_SUCCESS :
STATUS_UNSUCCESSFUL;
+ Status = (interfaces >= ExpectedInterfaces) ? STATUS_SUCCESS :
STATUS_UNSUCCESSFUL;
/* Finally, give back to the caller the number of found interfaces */
- *Interfaces = IntInterfaces;
+ *Interfaces = interfaces;
return Status;
}
VOID
-NTAPI
-IopStoreSystemPartitionInformation(IN PUNICODE_STRING NtSystemPartitionDeviceName,
- IN PUNICODE_STRING OsLoaderPathName)
+IopStoreSystemPartitionInformation(
+ _In_ PUNICODE_STRING NtSystemPartitionDeviceName,
+ _In_ PUNICODE_STRING OsLoaderPathName)
{
NTSTATUS Status;
UNICODE_STRING LinkTarget, KeyName;
@@ -733,9 +812,7 @@ IopStoreSystemPartitionInformation(IN PUNICODE_STRING
NtSystemPartitionDeviceNam
LinkTarget.Buffer = LinkTargetBuffer;
/* Query target */
- Status = ZwQuerySymbolicLinkObject(LinkHandle,
- &LinkTarget,
- NULL);
+ Status = ZwQuerySymbolicLinkObject(LinkHandle, &LinkTarget, NULL);
/* We are done with symbolic link */
ObCloseHandle(LinkHandle, KernelMode);
@@ -779,7 +856,7 @@ IopStoreSystemPartitionInformation(IN PUNICODE_STRING
NtSystemPartitionDeviceNam
return;
}
- /* Prepare first data writing... */
+ /* Prepare first data writing */
RtlInitUnicodeString(&KeyName, L"SystemPartition");
/* Write SystemPartition value which is the target of the symbolic link */
@@ -794,7 +871,7 @@ IopStoreSystemPartitionInformation(IN PUNICODE_STRING
NtSystemPartitionDeviceNam
DPRINT("Failed writing SystemPartition value, Status=%lx\n", Status);
}
- /* Prepare for second data writing... */
+ /* Prepare for second data writing */
RtlInitUnicodeString(&KeyName, L"OsLoaderPath");
/* Remove trailing slash if any (one slash only excepted) */
@@ -823,50 +900,70 @@ IopStoreSystemPartitionInformation(IN PUNICODE_STRING
NtSystemPartitionDeviceNam
/* PUBLIC FUNCTIONS ***********************************************************/
-/*
- * @implemented
- */
-PCONFIGURATION_INFORMATION NTAPI
+/**
+ * @brief
+ * Returns a pointer to the I/O manager's global configuration
+ * information structure.
+ *
+ * This structure contains the current values for how many physical storage
+ * media, SCSI HBA, serial, and parallel devices have device objects created
+ * to represent them by drivers as they are loaded.
+ **/
+PCONFIGURATION_INFORMATION
+NTAPI
IoGetConfigurationInformation(VOID)
{
- return(&_SystemConfigurationInformation);
+ return &_SystemConfigurationInformation;
}
-/*
+/**
* @halfplemented
- */
-NTSTATUS NTAPI
-IoReportResourceUsage(PUNICODE_STRING DriverClassName,
- PDRIVER_OBJECT DriverObject,
- PCM_RESOURCE_LIST DriverList,
- ULONG DriverListSize,
- PDEVICE_OBJECT DeviceObject,
- PCM_RESOURCE_LIST DeviceList,
- ULONG DeviceListSize,
- BOOLEAN OverrideConflict,
- PBOOLEAN ConflictDetected)
- /*
- * FUNCTION: Reports hardware resources in the
- * \Registry\Machine\Hardware\ResourceMap tree, so that a subsequently
- * loaded driver cannot attempt to use the same resources.
- * ARGUMENTS:
- * DriverClassName - The class of driver under which the resource
- * information should be stored.
- * DriverObject - The driver object that was input to the
- * DriverEntry.
- * DriverList - Resources that claimed for the driver rather than
- * per-device.
- * DriverListSize - Size in bytes of the DriverList.
- * DeviceObject - The device object for which resources should be
- * claimed.
- * DeviceList - List of resources which should be claimed for the
- * device.
- * DeviceListSize - Size of the per-device resource list in bytes.
- * OverrideConflict - True if the resources should be cliamed
- * even if a conflict is found.
- * ConflictDetected - Points to a variable that receives TRUE if
- * a conflict is detected with another driver.
- */
+ *
+ * @brief
+ * Reports hardware resources in the \Registry\Machine\Hardware\ResourceMap
+ * tree, so that a subsequently loaded driver cannot attempt to use the
+ * same resources.
+ *
+ * @param[in] DriverClassName
+ * The driver class under which the resource information should be stored.
+ *
+ * @param[in] DriverObject
+ * The driver object that was provided to the DriverEntry routine.
+ *
+ * @param[in] DriverList
+ * Resources claimed for the all the driver's devices, rather than per-device.
+ *
+ * @param[in] DriverListSize
+ * Size in bytes of the DriverList.
+ *
+ * @param[in] DeviceObject
+ * The device object for which resources should be claimed.
+ *
+ * @param[in] DeviceList
+ * List of resources that should be claimed for the device.
+ *
+ * @param[in] DeviceListSize
+ * Size of the per-device resource list in bytes.
+ *
+ * @param[in] OverrideConflict
+ * TRUE if the resources should be claimed even if a conflict is found.
+ *
+ * @param[out] ConflictDetected
+ * Points to a variable that receives TRUE if a conflict is detected
+ * with another driver.
+ **/
+NTSTATUS
+NTAPI
+IoReportResourceUsage(
+ _In_opt_ PUNICODE_STRING DriverClassName,
+ _In_ PDRIVER_OBJECT DriverObject,
+ _In_reads_bytes_opt_(DriverListSize) PCM_RESOURCE_LIST DriverList,
+ _In_opt_ ULONG DriverListSize,
+ _In_opt_ PDEVICE_OBJECT DeviceObject,
+ _In_reads_bytes_opt_(DeviceListSize) PCM_RESOURCE_LIST DeviceList,
+ _In_opt_ ULONG DeviceListSize,
+ _In_ BOOLEAN OverrideConflict,
+ _Out_ PBOOLEAN ConflictDetected)
{
NTSTATUS Status;
PCM_RESOURCE_LIST ResourceList;
@@ -908,13 +1005,13 @@ IoReportResourceUsage(PUNICODE_STRING DriverClassName,
return STATUS_SUCCESS;
}
-NTSTATUS
-NTAPI
-IopLegacyResourceAllocation(IN ARBITER_REQUEST_SOURCE AllocationType,
- IN PDRIVER_OBJECT DriverObject,
- IN PDEVICE_OBJECT DeviceObject OPTIONAL,
- IN PIO_RESOURCE_REQUIREMENTS_LIST ResourceRequirements,
- IN OUT PCM_RESOURCE_LIST *AllocatedResources)
+static NTSTATUS
+IopLegacyResourceAllocation(
+ _In_ ARBITER_REQUEST_SOURCE AllocationType,
+ _In_ PDRIVER_OBJECT DriverObject,
+ _In_opt_ PDEVICE_OBJECT DeviceObject,
+ _In_opt_ PIO_RESOURCE_REQUIREMENTS_LIST ResourceRequirements,
+ _Inout_ PCM_RESOURCE_LIST* AllocatedResources)
{
NTSTATUS Status;
@@ -924,7 +1021,7 @@ IopLegacyResourceAllocation(IN ARBITER_REQUEST_SOURCE
AllocationType,
{
/* We can get there by calling IoAssignResources() with RequestedResources =
NULL.
* TODO: not sure what we should do, but we shouldn't crash.
- * */
+ */
UNIMPLEMENTED;
return STATUS_NOT_IMPLEMENTED;
}
@@ -950,21 +1047,25 @@ IopLegacyResourceAllocation(IN ARBITER_REQUEST_SOURCE
AllocationType,
*/
NTSTATUS
NTAPI
-IoAssignResources(IN PUNICODE_STRING RegistryPath,
- IN PUNICODE_STRING DriverClassName,
- IN PDRIVER_OBJECT DriverObject,
- IN PDEVICE_OBJECT DeviceObject,
- IN PIO_RESOURCE_REQUIREMENTS_LIST RequestedResources,
- IN OUT PCM_RESOURCE_LIST* AllocatedResources)
+IoAssignResources(
+ _In_ PUNICODE_STRING RegistryPath,
+ _In_opt_ PUNICODE_STRING DriverClassName,
+ _In_ PDRIVER_OBJECT DriverObject,
+ _In_opt_ PDEVICE_OBJECT DeviceObject,
+ _In_opt_ PIO_RESOURCE_REQUIREMENTS_LIST RequestedResources,
+ _Inout_ PCM_RESOURCE_LIST* AllocatedResources)
{
PDEVICE_NODE DeviceNode;
+ UNREFERENCED_PARAMETER(RegistryPath);
+ UNREFERENCED_PARAMETER(DriverClassName);
+
/* Do we have a DO? */
if (DeviceObject)
{
/* Get its device node */
DeviceNode = IopGetDeviceNode(DeviceObject);
- if ((DeviceNode) && !(DeviceNode->Flags &
DNF_LEGACY_RESOURCE_DEVICENODE))
+ if (DeviceNode && !(DeviceNode->Flags &
DNF_LEGACY_RESOURCE_DEVICENODE))
{
/* New drivers should not call this API */
KeBugCheckEx(PNP_DETECTED_FATAL_ERROR,
@@ -987,7 +1088,8 @@ IoAssignResources(IN PUNICODE_STRING RegistryPath,
}
/* Initialize output if given */
- if (AllocatedResources) *AllocatedResources = NULL;
+ if (AllocatedResources)
+ *AllocatedResources = NULL;
/* Call internal helper function */
return IopLegacyResourceAllocation(ArbiterRequestLegacyAssigned,
@@ -997,194 +1099,207 @@ IoAssignResources(IN PUNICODE_STRING RegistryPath,
AllocatedResources);
}
-/*
- * FUNCTION:
- * Reads and returns Hardware information from the appropriate hardware registry
key.
+/**
+ * @brief
+ * Reads and returns Hardware information from the appropriate
+ * hardware registry key.
*
- * ARGUMENTS:
- * BusType - MCA, ISA, EISA...specifies the Bus Type
- * BusNumber - Which bus of above should be queried
- * ControllerType - Specifices the Controller Type
- * ControllerNumber - Which of the controllers to query.
- * CalloutRoutine - Which function to call for each valid query.
- * Context - Value to pass to the callback.
+ * @param[in] BusType
+ * Specifies the bus type, for example: MCA, ISA, EISA, etc.
*
- * RETURNS:
- * Status
+ * @param[in] BusNumber
+ * The number of the specified bus type to query.
*
- * STATUS:
- * @implemented
- */
-
-NTSTATUS NTAPI
-IoQueryDeviceDescription(PINTERFACE_TYPE BusType OPTIONAL,
- PULONG BusNumber OPTIONAL,
- PCONFIGURATION_TYPE ControllerType OPTIONAL,
- PULONG ControllerNumber OPTIONAL,
- PCONFIGURATION_TYPE PeripheralType OPTIONAL,
- PULONG PeripheralNumber OPTIONAL,
- PIO_QUERY_DEVICE_ROUTINE CalloutRoutine,
- PVOID Context)
+ * @param[in] ControllerType
+ * Specifies the controller type
+ *
+ * @param[in] ControllerNumber
+ * The number of the specified controller type to query.
+ *
+ * @param[in] CalloutRoutine
+ * A user-provided callback function to call for each valid query.
+ *
+ * @param[in] Context
+ * A callback-specific context value.
+ *
+ * @return A status code.
+ **/
+NTSTATUS
+NTAPI
+IoQueryDeviceDescription(
+ _In_opt_ PINTERFACE_TYPE BusType,
+ _In_opt_ PULONG BusNumber,
+ _In_opt_ PCONFIGURATION_TYPE ControllerType,
+ _In_opt_ PULONG ControllerNumber,
+ _In_opt_ PCONFIGURATION_TYPE PeripheralType,
+ _In_opt_ PULONG PeripheralNumber,
+ _In_ PIO_QUERY_DEVICE_ROUTINE CalloutRoutine,
+ _In_opt_ PVOID Context)
{
- NTSTATUS Status;
- ULONG BusLoopNumber = -1; /* Root Bus */
- OBJECT_ATTRIBUTES ObjectAttributes;
- UNICODE_STRING RootRegKey;
- HANDLE RootRegHandle;
- IO_QUERY Query;
-
- /* Set up the String */
- RootRegKey.Length = 0;
- RootRegKey.MaximumLength = 2048;
- RootRegKey.Buffer = ExAllocatePoolWithTag(PagedPool, RootRegKey.MaximumLength,
TAG_IO_RESOURCE);
- RtlAppendUnicodeToString(&RootRegKey,
L"\\REGISTRY\\MACHINE\\HARDWARE\\DESCRIPTION\\SYSTEM");
-
- /* Open a handle to the Root Registry Key */
- InitializeObjectAttributes(
- &ObjectAttributes,
- &RootRegKey,
- OBJ_CASE_INSENSITIVE,
- NULL,
- NULL);
-
- Status = ZwOpenKey(&RootRegHandle, KEY_READ, &ObjectAttributes);
-
- if (NT_SUCCESS(Status))
- {
- /* Use a helper function to loop though this key and get the info */
- Query.BusType = BusType;
- Query.BusNumber = BusNumber;
- Query.ControllerType = ControllerType;
- Query.ControllerNumber = ControllerNumber;
- Query.PeripheralType = PeripheralType;
- Query.PeripheralNumber = PeripheralNumber;
- Query.CalloutRoutine = CalloutRoutine;
- Query.Context = Context;
- Status = IopQueryBusDescription(&Query, RootRegKey, RootRegHandle,
&BusLoopNumber, TRUE);
-
- /* Close registry */
- ZwClose(RootRegHandle);
- }
-
- /* Free Memory */
- ExFreePoolWithTag(RootRegKey.Buffer, TAG_IO_RESOURCE);
-
- return Status;
+ NTSTATUS Status;
+ ULONG BusLoopNumber = -1; /* Root Bus */
+ OBJECT_ATTRIBUTES ObjectAttributes;
+ UNICODE_STRING RootRegKey;
+ HANDLE RootRegHandle;
+ IO_QUERY Query;
+
+ /* Set up the string */
+ RootRegKey.Length = 0;
+ RootRegKey.MaximumLength = 2048;
+ RootRegKey.Buffer = ExAllocatePoolWithTag(PagedPool, RootRegKey.MaximumLength,
TAG_IO_RESOURCE);
+ RtlAppendUnicodeToString(&RootRegKey,
L"\\REGISTRY\\MACHINE\\HARDWARE\\DESCRIPTION\\SYSTEM");
+
+ /* Open a handle to the Root Registry Key */
+ InitializeObjectAttributes(&ObjectAttributes,
+ &RootRegKey,
+ OBJ_CASE_INSENSITIVE,
+ NULL,
+ NULL);
+
+ Status = ZwOpenKey(&RootRegHandle, KEY_READ, &ObjectAttributes);
+
+ if (NT_SUCCESS(Status))
+ {
+ /* Use a helper function to loop though this key and get the information */
+ Query.BusType = BusType;
+ Query.BusNumber = BusNumber;
+ Query.ControllerType = ControllerType;
+ Query.ControllerNumber = ControllerNumber;
+ Query.PeripheralType = PeripheralType;
+ Query.PeripheralNumber = PeripheralNumber;
+ Query.CalloutRoutine = CalloutRoutine;
+ Query.Context = Context;
+ Status = IopQueryBusDescription(&Query,
+ RootRegKey,
+ RootRegHandle,
+ &BusLoopNumber,
+ TRUE);
+
+ /* Close registry key */
+ ZwClose(RootRegHandle);
+ }
+
+ /* Cleanup */
+ ExFreePoolWithTag(RootRegKey.Buffer, TAG_IO_RESOURCE);
+
+ return Status;
}
-/*
- * @implemented
- */
-NTSTATUS NTAPI
-IoReportHalResourceUsage(PUNICODE_STRING HalDescription,
- PCM_RESOURCE_LIST RawList,
- PCM_RESOURCE_LIST TranslatedList,
- ULONG ListSize)
-/*
- * FUNCTION:
- * Reports hardware resources of the HAL in the
- * \Registry\Machine\Hardware\ResourceMap tree.
- * ARGUMENTS:
- * HalDescription: Descriptive name of the HAL.
- * RawList: List of raw (bus specific) resources which should be
- * claimed for the HAL.
- * TranslatedList: List of translated (system wide) resources which
- * should be claimed for the HAL.
- * ListSize: Size in bytes of the raw and translated resource lists.
- * Both lists have the same size.
- * RETURNS:
- * Status.
- */
+/**
+ * @brief
+ * Reports hardware resources of the HAL in the
+ * \Registry\Machine\Hardware\ResourceMap tree.
+ *
+ * @param[in] HalName
+ * Descriptive name of the HAL.
+ *
+ * @param[in] RawResourceList
+ * List of raw (bus specific) resources which should be claimed
+ * for the HAL.
+ *
+ * @param[in] TranslatedResourceList
+ * List of translated (system wide) resources which should be claimed
+ * for the HAL.
+ *
+ * @param[in] ResourceListSize
+ * Size in bytes of the raw and translated resource lists.
+ * Both lists have the same size.
+ *
+ * @return A status code.
+ **/
+NTSTATUS
+NTAPI
+IoReportHalResourceUsage(
+ _In_ PUNICODE_STRING HalName,
+ _In_ PCM_RESOURCE_LIST RawResourceList,
+ _In_ PCM_RESOURCE_LIST TranslatedResourceList,
+ _In_ ULONG ResourceListSize)
{
- OBJECT_ATTRIBUTES ObjectAttributes;
- UNICODE_STRING Name;
- ULONG Disposition;
- NTSTATUS Status;
- HANDLE ResourcemapKey;
- HANDLE HalKey;
- HANDLE DescriptionKey;
-
- /* Open/Create 'RESOURCEMAP' key. */
- RtlInitUnicodeString(&Name,
- L"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP");
- InitializeObjectAttributes(&ObjectAttributes,
- &Name,
- OBJ_CASE_INSENSITIVE | OBJ_OPENIF,
- 0,
- NULL);
- Status = ZwCreateKey(&ResourcemapKey,
- KEY_ALL_ACCESS,
- &ObjectAttributes,
- 0,
- NULL,
- REG_OPTION_VOLATILE,
- &Disposition);
- if (!NT_SUCCESS(Status))
- return(Status);
-
- /* Open/Create 'Hardware Abstraction Layer' key */
- RtlInitUnicodeString(&Name,
- L"Hardware Abstraction Layer");
- InitializeObjectAttributes(&ObjectAttributes,
- &Name,
- OBJ_CASE_INSENSITIVE | OBJ_OPENIF,
- ResourcemapKey,
- NULL);
- Status = ZwCreateKey(&HalKey,
- KEY_ALL_ACCESS,
- &ObjectAttributes,
- 0,
- NULL,
- REG_OPTION_VOLATILE,
- &Disposition);
- ZwClose(ResourcemapKey);
- if (!NT_SUCCESS(Status))
- return(Status);
-
- /* Create 'HalDescription' key */
- InitializeObjectAttributes(&ObjectAttributes,
- HalDescription,
- OBJ_CASE_INSENSITIVE,
- HalKey,
- NULL);
- Status = ZwCreateKey(&DescriptionKey,
- KEY_ALL_ACCESS,
- &ObjectAttributes,
- 0,
- NULL,
- REG_OPTION_VOLATILE,
- &Disposition);
- ZwClose(HalKey);
- if (!NT_SUCCESS(Status))
- return(Status);
-
- /* Add '.Raw' value. */
- RtlInitUnicodeString(&Name,
- L".Raw");
- Status = ZwSetValueKey(DescriptionKey,
- &Name,
- 0,
- REG_RESOURCE_LIST,
- RawList,
- ListSize);
- if (!NT_SUCCESS(Status))
+ NTSTATUS Status;
+ OBJECT_ATTRIBUTES ObjectAttributes;
+ UNICODE_STRING Name;
+ ULONG Disposition;
+ HANDLE ResourceMapKey;
+ HANDLE HalKey;
+ HANDLE DescriptionKey;
+
+ /* Open/Create 'RESOURCEMAP' key */
+ RtlInitUnicodeString(&Name,
L"\\Registry\\Machine\\HARDWARE\\RESOURCEMAP");
+ InitializeObjectAttributes(&ObjectAttributes,
+ &Name,
+ OBJ_CASE_INSENSITIVE | OBJ_OPENIF,
+ 0,
+ NULL);
+ Status = ZwCreateKey(&ResourceMapKey,
+ KEY_ALL_ACCESS,
+ &ObjectAttributes,
+ 0,
+ NULL,
+ REG_OPTION_VOLATILE,
+ &Disposition);
+ if (!NT_SUCCESS(Status))
+ return Status;
+
+ /* Open/Create 'Hardware Abstraction Layer' key */
+ RtlInitUnicodeString(&Name, L"Hardware Abstraction Layer");
+ InitializeObjectAttributes(&ObjectAttributes,
+ &Name,
+ OBJ_CASE_INSENSITIVE | OBJ_OPENIF,
+ ResourceMapKey,
+ NULL);
+ Status = ZwCreateKey(&HalKey,
+ KEY_ALL_ACCESS,
+ &ObjectAttributes,
+ 0,
+ NULL,
+ REG_OPTION_VOLATILE,
+ &Disposition);
+ ZwClose(ResourceMapKey);
+ if (!NT_SUCCESS(Status))
+ return Status;
+
+ /* Create 'HalName' key */
+ InitializeObjectAttributes(&ObjectAttributes,
+ HalName,
+ OBJ_CASE_INSENSITIVE,
+ HalKey,
+ NULL);
+ Status = ZwCreateKey(&DescriptionKey,
+ KEY_ALL_ACCESS,
+ &ObjectAttributes,
+ 0,
+ NULL,
+ REG_OPTION_VOLATILE,
+ &Disposition);
+ ZwClose(HalKey);
+ if (!NT_SUCCESS(Status))
+ return Status;
+
+ /* Add '.Raw' value */
+ RtlInitUnicodeString(&Name, L".Raw");
+ Status = ZwSetValueKey(DescriptionKey,
+ &Name,
+ 0,
+ REG_RESOURCE_LIST,
+ RawResourceList,
+ ResourceListSize);
+ if (!NT_SUCCESS(Status))
{
- ZwClose(DescriptionKey);
- return(Status);
+ ZwClose(DescriptionKey);
+ return Status;
}
- /* Add '.Translated' value. */
- RtlInitUnicodeString(&Name,
- L".Translated");
- Status = ZwSetValueKey(DescriptionKey,
- &Name,
- 0,
- REG_RESOURCE_LIST,
- TranslatedList,
- ListSize);
- ZwClose(DescriptionKey);
-
- return(Status);
+ /* Add '.Translated' value */
+ RtlInitUnicodeString(&Name, L".Translated");
+ Status = ZwSetValueKey(DescriptionKey,
+ &Name,
+ 0,
+ REG_RESOURCE_LIST,
+ TranslatedResourceList,
+ ResourceListSize);
+ ZwClose(DescriptionKey);
+
+ return Status;
}
/* EOF */
diff --git a/sdk/include/xdk/iofuncs.h b/sdk/include/xdk/iofuncs.h
index 534edfd66b4..e6e431d26a7 100644
--- a/sdk/include/xdk/iofuncs.h
+++ b/sdk/include/xdk/iofuncs.h
@@ -1492,7 +1492,7 @@ IoQueryDeviceDescription(
_In_opt_ PCONFIGURATION_TYPE PeripheralType,
_In_opt_ PULONG PeripheralNumber,
_In_ PIO_QUERY_DEVICE_ROUTINE CalloutRoutine,
- _Inout_opt_ PVOID Context);
+ _In_opt_ PVOID Context);
_IRQL_requires_max_(APC_LEVEL)
NTKERNELAPI