[WIN32SS] EnumDisplayDevices: Fill DeviceID field properly

- [VIDEOPRT] Return the real PhysicalDeviceObject in Win32k callbacks.

- [WIN32SS:ENG] Pass PhysDeviceObject into the GraphicsDevice structure
  and rename the destination field accordingly.

- [WIN32SS:NTUSER] Request hardware identifiers from device PDO and
  fill DISPLAY_DEVICE's DeviceID field with the first identifier.

Now it's correctly passed to the usermode, and Desktop Propertes applet
can open the video adapter device properties.

Thanks to Hervé Poussineau for the help.

CORE-18197 CORE-11715
This commit is contained in:
Stanislav Motylkov 2022-05-24 02:54:57 +03:00
parent ee613a18eb
commit 31827c43b6
No known key found for this signature in database
GPG key ID: AFE513258CBA9E92
4 changed files with 58 additions and 5 deletions

View file

@ -630,6 +630,8 @@ VideoPortInitWin32kCallbacks(
_In_ ULONG BufferLength,
_Out_ PULONG_PTR Information)
{
PVIDEO_PORT_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
*Information = sizeof(VIDEO_WIN32K_CALLBACKS);
if (BufferLength < sizeof(VIDEO_WIN32K_CALLBACKS))
{
@ -643,7 +645,7 @@ VideoPortInitWin32kCallbacks(
/* Return reasonable values to Win32k */
Win32kCallbacks->bACPI = FALSE;
Win32kCallbacks->pPhysDeviceObject = DeviceObject;
Win32kCallbacks->pPhysDeviceObject = DeviceExtension->PhysicalDeviceObject;
Win32kCallbacks->DualviewFlags = 0;
return STATUS_SUCCESS;

View file

@ -349,7 +349,7 @@ EngpRegisterGraphicsDevice(
// TODO: Set flags according to the results.
// if (Win32kCallbacks.bACPI)
// if (Win32kCallbacks.DualviewFlags & ???)
// Win32kCallbacks.pPhysDeviceObject;
pGraphicsDevice->PhysDeviceHandle = Win32kCallbacks.pPhysDeviceObject;
/* Copy the device name */
RtlStringCbCopyNW(pGraphicsDevice->szNtDeviceName,

View file

@ -61,7 +61,7 @@ typedef struct _GRAPHICS_DEVICE
struct _GRAPHICS_DEVICE * pNextGraphicsDevice;
struct _GRAPHICS_DEVICE * pVgaDevice;
PDEVICE_OBJECT DeviceObject;
PVOID pDeviceHandle;
PDEVICE_OBJECT PhysDeviceHandle;
DWORD hkClassDriverConfig;
DWORD StateFlags; /* See DISPLAY_DEVICE_* */
ULONG cbdevmodeInfo;

View file

@ -237,7 +237,8 @@ UserEnumDisplayDevices(
DWORD dwFlags)
{
PGRAPHICS_DEVICE pGraphicsDevice;
ULONG cbSize;
PWCHAR pHardwareId;
ULONG cbSize, dwLength;
HKEY hkey;
NTSTATUS Status;
@ -280,9 +281,59 @@ UserEnumDisplayDevices(
RtlStringCbCopyW(pdispdev->DeviceName, sizeof(pdispdev->DeviceName), pGraphicsDevice->szWinDeviceName);
RtlStringCbCopyW(pdispdev->DeviceString, sizeof(pdispdev->DeviceString), pGraphicsDevice->pwszDescription);
pdispdev->StateFlags = pGraphicsDevice->StateFlags;
// FIXME: fill in DEVICE ID
pdispdev->DeviceID[0] = UNICODE_NULL;
/* Fill in DeviceID */
if (pGraphicsDevice->PhysDeviceHandle != NULL)
{
Status = IoGetDeviceProperty(pGraphicsDevice->PhysDeviceHandle,
DevicePropertyHardwareID,
0,
NULL,
&dwLength);
if (Status == STATUS_BUFFER_TOO_SMALL)
{
pHardwareId = ExAllocatePoolWithTag(PagedPool,
dwLength,
USERTAG_DISPLAYINFO);
if (!pHardwareId)
{
EngSetLastError(ERROR_NOT_ENOUGH_MEMORY);
return STATUS_INSUFFICIENT_RESOURCES;
}
Status = IoGetDeviceProperty(pGraphicsDevice->PhysDeviceHandle,
DevicePropertyHardwareID,
dwLength,
pHardwareId,
&dwLength);
if (!NT_SUCCESS(Status))
{
ERR("IoGetDeviceProperty() failed with status 0x%08lx\n", Status);
}
else
{
/* For video adapters it should be the first Hardware ID
* which usually is the longest one and unique enough */
RtlStringCbCopyW(pdispdev->DeviceID, sizeof(pdispdev->DeviceID), pHardwareId);
/* For monitors it should be the first Hardware ID
* concatenated with the unique driver registry key */
/* FIXME: Handle monitors! */
TRACE("Hardware ID: %ls\n", pdispdev->DeviceID);
}
ExFreePoolWithTag(pHardwareId, USERTAG_DISPLAYINFO);
}
else
{
ERR("IoGetDeviceProperty() failed with status 0x%08lx\n", Status);
}
}
return STATUS_SUCCESS;
}