CORE-17932
[ENG] Implement DirectDraw management in switch display mode functions
(e.g. resolution change, color depth, display frequency etc.):
- Switch DirectDraw instances between the two PDEVs (the current one and
the new one allocated by ourselves) by calling dxg!DxDdDynamicModeChange
function.
- Suspend them before and resume after the display mode switch, by calling
dxg!DxDdsuspendDirectDraw and dxg!DxDdResumeDirectDraw appropriately.
We currently don't have these functions implemented, but MS DXG has, so
it allows to properly manage DirectDraw PDEVs using this driver, similarly
to Windows.
My analysis confirms that these functions are always called in XP/2k3 on
display mode switch, even when there is no any DirectX app running at the
moment. Analyzing their prototypes show that my guesses are correct.
- Initialize hDev and dhpdev members for EDD_DIRECTDRAW_GLOBAL for newly
created surfaces, switch them during mode change and re-initialize after
it also. They are commonly used by DirectDraw stack.
In addition, enable DirectDraw for old and new PDEVs, by calling
dxg!DxDdEnableDirectDraw function.
[NTDDRAW] Additionally, fix usage of DirectDraw lock count in the PDEVOBJ
structure.
- Enable cDirectDrawDisableLocks member for storing its value, instead of
DxDd_nCount, which is marked as ROS-specific.
- Use it in win32k!DxEngGet/SetHdevData for getting/setting DirectDraw
count appropriately.
My analysis also shows that in Windows, the PDEVOBJ::cDirectDrawDisableLocks
method calls DxEngGetHdevData with type 8, which corresponds to our DxDd_nCount.
So there are no doubts that this member is used there.
- Rename DxEngGetHdevData_dd_count alias of type 8 to DxEngGetHdevData_dd_locks,
to match more accurately an actual member name. Update the enumeration
and fix all code parts appropriately.
All these changes allow to properly change display mode during executing
DirectDraw applications, when they try to switch in full-screen mode.
At least a bugcheck that happened before my changes, does no longer appear.
There are still some games that don't run correctly, as if there is no
3D acceleration (which actually exists). This requires further investigations.
- [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
- store the acceleration level in PDEVOBJ
- when searching a pdev, search a pdev with required acceleration level
- disable some functions when not at full acceleration level
(levels 3 and 5 are not implemented)
Initialization of device mode list will be done later, just before switching to graphics mode.
If no graphic display is available, we will now fail when starting first GUI application in
co_IntGraphicsCheck(). Add a bugcheck here to prevent frozen screen.
This function can create a MDEV for the whole display (maybe containing multiple
PDEVs), or update settings of a specific PDEV.
- call PDEVOBJ_lChangeDisplaySettings when switching to graphics mode.
- modify EngpGetPDEV to search requested PDEV only in current MDEV
This will be used (later) to store the list of all enabled display devices.
Add a global variable gpmdev (should really be stored in DISPLAYINFO structure)
Replace global variable gppdevPrimary by pmdev->ppdevGlobal.
- change first argument to be a PGRAPHICS_DEVICE instead of a device name
- add ldevtype (for now, only LDEV_DEVICE_DISPLAY is allowed)
- always pass a devmode if ldevtype is LDEV_DEVICE_DISPLAY
- insert the ppdev into gppdevList on success
- change callers to adapt them to new rules
- make it return a new allocated PDEVMODEW instead of a pointer into
existing PGRAPHICS_DEVICE (usefull when available display modes can
dynamically change: VirtualBox, RDP, ...)
- update all callers
- Change INIT_FUNCTION and INIT_SECTION to CODE_SEG("INIT") and DATA_SEG("INIT") respectively
- Remove INIT_FUNCTION from function prototypes
- Remove alloc_text pragma calls as they are not needed anymore