[PATCH v2 1/2] win32u: Don't pass physdev to wine_get_wgl_driver() driver function.
Paul Gofman
pgofman at codeweavers.com
Thu Feb 3 09:41:26 CST 2022
On 2/3/22 17:25, Jacek Caban wrote:
> Hi Paul,
>
> On 2/1/22 18:32, Paul Gofman wrote:
>> @@ -1347,13 +1349,29 @@ NTSTATUS WINAPI
>> NtGdiDdDDICheckVidPnExclusiveOwnership( const D3DKMT_CHECKVIDPNE
>> */
>> struct opengl_funcs * CDECL __wine_get_wgl_driver( HDC hdc, UINT
>> version )
>> {
>> + const struct gdi_dc_funcs *driver_funcs[11], **next_funcs;
>> struct opengl_funcs *ret = NULL;
>> DC * dc = get_dc_ptr( hdc );
>> + PHYSDEV physdev;
>> if (dc)
>> {
>> - PHYSDEV physdev = GET_DC_PHYSDEV( dc, wine_get_wgl_driver );
>> - ret = physdev->funcs->wine_get_wgl_driver( physdev, version );
>> + next_funcs = driver_funcs;
>> + physdev = GET_DC_PHYSDEV( dc, wine_get_wgl_driver );
>> + while (physdev && next_funcs - driver_funcs <
>> ARRAY_SIZE(driver_funcs) - 1)
>> + {
>> + *next_funcs++ = physdev->funcs;
>> + if (physdev->funcs == &null_driver) break;
>> + physdev = GET_NEXT_PHYSDEV( physdev, wine_get_wgl_driver );
>> + }
>> + *next_funcs = NULL;
>> + next_funcs = driver_funcs;
>> + while (*next_funcs)
>> + {
>> + ret = (*next_funcs)->wine_get_wgl_driver( version,
>> &next_funcs );
>> + if (ret || !next_funcs) break;
>> + ++next_funcs;
>> + }
>
>
> If the current PHYSDEV locking does not fit what we need here, it may
> be indeed a good idea to use something different here. It seems unique
> in this aspect anyway. However, it doesn't seem like hacking around
> PHYSDEV pointers like this is really what we need here. You could, for
> example, move wine_get_wgl from gdi_dc_funcs to user_driver_funcs
> (similar to what 9596e7f2a4e972c35efdca38b01d068bfc055d36 did for
> Vulkan) and call it with no PHYSDEV involved. __wine_get_wgl_driver
> could look roughly like this:
>
>
> if ((hwnd = NtUserWindowFromDC( hdc )) && (ret =
> user_driver->wine_get_wgl_driver( hwnd, version )) return ret;
>
> if (selected correct bitmap on hdc) return get_osmesa_driver( version );
>
> return (void *)-1;
>
>
> How does it look to you?
>
>
I am not quite sure, but this looks a bit convoluted to me. First in
terms of getting user hwnd from dc (which can work as I understand but
brings some dependency on the not directly related locking and logic).
Then heuristics in __wine_get_wgl_driver() for guessing if osmesa should
be used while currently it is more straightforward as all that knowledge
is already incorporated into the driver chain, there is the logic spread
elsewhere which controls that.
I realize that hacking out driver function pointers indeed does not look
nice. Maybe if getting hwnd is really not an issue (I assume
user_callbacks->pWindowFromDC() can be used for that?) we can indicate
in the DC structure if osmesa should be used (to be set when the dibdrv
is added to device chain not through windrv)? This way we won't be
duplicating that logic.
More information about the wine-devel
mailing list