diff --git a/dlls/wined3d/arb_program_shader.c b/dlls/wined3d/arb_program_shader.c index be660331680..e5ee5c649cb 100644 --- a/dlls/wined3d/arb_program_shader.c +++ b/dlls/wined3d/arb_program_shader.c @@ -104,7 +104,7 @@ void shader_arb_load_constants( IWineD3DDeviceImpl* deviceImpl = (IWineD3DDeviceImpl*) device; IWineD3DStateBlockImpl* stateBlock = deviceImpl->stateBlock; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl*)deviceImpl->wineD3D)->gl_info; + WineD3D_GL_Info *gl_info = &deviceImpl->adapter->gl_info; if (useVertexShader) { IWineD3DBaseShaderImpl* vshader = (IWineD3DBaseShaderImpl*) stateBlock->vertexShader; @@ -383,7 +383,7 @@ static void shader_hw_sample(SHADER_OPCODE_ARG* arg, DWORD sampler_idx, const ch IWineD3DPixelShaderImpl* This = (IWineD3DPixelShaderImpl*) arg->shader; IWineD3DDeviceImpl* deviceImpl = (IWineD3DDeviceImpl*) This->baseShader.device; IWineD3DBaseTextureImpl *texture = (IWineD3DBaseTextureImpl *) deviceImpl->stateBlock->textures[sampler_idx]; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(((IWineD3DDeviceImpl *)(This->baseShader.device))->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &((IWineD3DDeviceImpl *)This->baseShader.device)->adapter->gl_info; SHADER_BUFFER* buffer = arg->buffer; DWORD sampler_type = arg->reg_maps->samplers[sampler_idx] & WINED3DSP_TEXTURETYPE_MASK; @@ -1033,7 +1033,7 @@ static GLuint create_arb_blt_fragment_program(WineD3D_GL_Info *gl_info) { static void shader_arb_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; if (useVS) { TRACE("Using vertex shader\n"); @@ -1074,7 +1074,7 @@ static void shader_arb_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) { static void shader_arb_select_depth_blt(IWineD3DDevice *iface) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; static GLuint vprogram_id = 0; static GLuint fprogram_id = 0; @@ -1089,7 +1089,7 @@ static void shader_arb_select_depth_blt(IWineD3DDevice *iface) { static void shader_arb_cleanup(IWineD3DDevice *iface) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; if (GL_SUPPORT(ARB_VERTEX_PROGRAM)) glDisable(GL_VERTEX_PROGRAM_ARB); if (GL_SUPPORT(ARB_FRAGMENT_PROGRAM)) glDisable(GL_FRAGMENT_PROGRAM_ARB); } diff --git a/dlls/wined3d/basetexture.c b/dlls/wined3d/basetexture.c index 8e18362782d..278bb399c60 100644 --- a/dlls/wined3d/basetexture.c +++ b/dlls/wined3d/basetexture.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info static const Wined3dTextureStateMap textureObjectSamplerStates[] = { {WINED3DSAMP_ADDRESSU, WINED3DSAMP_ADDRESSU}, diff --git a/dlls/wined3d/context.c b/dlls/wined3d/context.c index 1f17bb1f7ec..c2834c7f5a9 100644 --- a/dlls/wined3d/context.c +++ b/dlls/wined3d/context.c @@ -27,7 +27,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(This->wineD3D))->gl_info +#define GLINFO_LOCATION This->adapter->gl_info /***************************************************************************** * Context_MarkStateDirty diff --git a/dlls/wined3d/cubetexture.c b/dlls/wined3d/cubetexture.c index 6be0f7e314f..362868ffe64 100644 --- a/dlls/wined3d/cubetexture.c +++ b/dlls/wined3d/cubetexture.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info static const GLenum cube_targets[6] = { GL_TEXTURE_CUBE_MAP_POSITIVE_X_ARB, diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 3ede72094f4..96186d5bc20 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -33,7 +33,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(This->wineD3D))->gl_info +#define GLINFO_LOCATION This->adapter->gl_info /* Define the default light parameters as specified by MSDN */ const WINED3DLIGHT WINED3D_default_light = { @@ -1855,12 +1855,7 @@ static HRESULT WINAPI IWineD3DDeviceImpl_Init3D(IWineD3DDevice *iface, WINED3DPR /* Set up some starting GL setup */ ENTER_GL(); - /* - * Initialize openGL extension related variables - * with Default values - */ - ((IWineD3DImpl *) This->wineD3D)->isGLInfoValid = IWineD3DImpl_FillGLCaps(This->wineD3D, swapchain->context[0]->display); /* Setup all the devices defaults */ IWineD3DStateBlock_InitStartupStateBlock((IWineD3DStateBlock *)This->stateBlock); #if 0 diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index 0446179896f..c98152831b6 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -35,7 +35,6 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DECLARE_DEBUG_CHANNEL(d3d_caps); -#define GLINFO_LOCATION This->gl_info /********************************************************** * Utility functions follow @@ -61,6 +60,10 @@ static inline Display *get_display( HDC hdc ) return display; } +/* Adapters */ +static int numAdapters = 0; +static struct WineD3DAdapter Adapters[1]; + /* lookup tables */ int minLookup[MAX_LOOKUPS]; int maxLookup[MAX_LOOKUPS]; @@ -314,10 +317,8 @@ static void select_shader_max_constants( * IWineD3D parts follows **********************************************************/ -BOOL IWineD3DImpl_FillGLCaps(IWineD3D *iface, Display* display) { - IWineD3DImpl *This = (IWineD3DImpl *)iface; - WineD3D_GL_Info *gl_info = &This->gl_info; - +#define GLINFO_LOCATION (*gl_info) +BOOL IWineD3DImpl_FillGLCaps(WineD3D_GL_Info *gl_info, Display* display) { const char *GL_Extensions = NULL; const char *GLX_Extensions = NULL; const char *gl_string = NULL; @@ -1072,6 +1073,7 @@ BOOL IWineD3DImpl_FillGLCaps(IWineD3D *iface, Display* display) { WineD3D_ReleaseFakeGLContext(); return return_value; } +#undef GLINFO_LOCATION /********************************************************** * IWineD3D implementation follows @@ -1080,9 +1082,8 @@ BOOL IWineD3DImpl_FillGLCaps(IWineD3D *iface, Display* display) { static UINT WINAPI IWineD3DImpl_GetAdapterCount (IWineD3D *iface) { IWineD3DImpl *This = (IWineD3DImpl *)iface; - /* FIXME: Set to one for now to imply the display */ - TRACE_(d3d_caps)("(%p): Mostly stub, only returns primary display\n", This); - return 1; + TRACE_(d3d_caps)("(%p): Reporting %d adapters\n", This, numAdapters); + return numAdapters; } static HRESULT WINAPI IWineD3DImpl_RegisterSoftwareDevice(IWineD3D *iface, void* pInitializeFunction) { @@ -1093,14 +1094,13 @@ static HRESULT WINAPI IWineD3DImpl_RegisterSoftwareDevice(IWineD3D *iface, void static HMONITOR WINAPI IWineD3DImpl_GetAdapterMonitor(IWineD3D *iface, UINT Adapter) { IWineD3DImpl *This = (IWineD3DImpl *)iface; - POINT pt = { -1, -1 }; if (Adapter >= IWineD3DImpl_GetAdapterCount(iface)) { return NULL; } - FIXME_(d3d_caps)("(%p): returning the primary monitor for adapter %d\n", This, Adapter); - return MonitorFromPoint(pt, MONITOR_DEFAULTTOPRIMARY); + TRACE_(d3d_caps)("(%p)->(%d)\n", This, Adapter); + return MonitorFromPoint(Adapters[Adapter].monitorPoint, MONITOR_DEFAULTTOPRIMARY); } /* FIXME: GetAdapterModeCount and EnumAdapterModes currently only returns modes @@ -1115,6 +1115,7 @@ static UINT WINAPI IWineD3DImpl_GetAdapterModeCount(IWineD3D *iface, UINT Ad return 0; } + /* TODO: Store modes per adapter and read it from the adapter structure */ if (Adapter == 0) { /* Display */ int i = 0; int j = 0; @@ -1170,6 +1171,7 @@ static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapte return WINED3DERR_INVALIDCALL; } + /* TODO: Store modes per adapter and read it from the adapter structure */ if (Adapter == 0 && !DEBUG_SINGLE_MODE) { /* Display */ DEVMODEW DevModeW; int ModeIdx = 0; @@ -1300,18 +1302,6 @@ static HRESULT WINAPI IWineD3DImpl_GetAdapterDisplayMode(IWineD3D *iface, UINT A return WINED3D_OK; } -static Display * WINAPI IWineD3DImpl_GetAdapterDisplay(IWineD3D *iface, UINT Adapter) { - Display *display; - HDC device_context; - /* only works with one adapter at the moment... */ - - /* Get the display */ - device_context = GetDC(0); - display = get_display(device_context); - ReleaseDC(0, device_context); - return display; -} - /* NOTE: due to structure differences between dx8 and dx9 D3DADAPTER_IDENTIFIER, and fields being inserted in the middle, a new structure is used in place */ static HRESULT WINAPI IWineD3DImpl_GetAdapterIdentifier(IWineD3D *iface, UINT Adapter, DWORD Flags, @@ -1324,42 +1314,26 @@ static HRESULT WINAPI IWineD3DImpl_GetAdapterIdentifier(IWineD3D *iface, UINT Ad return WINED3DERR_INVALIDCALL; } - if (Adapter == 0) { /* Display - only device supported for now */ + /* Return the information requested */ + TRACE_(d3d_caps)("device/Vendor Name and Version detection using FillGLCaps\n"); + strcpy(pIdentifier->Driver, "Display"); + strcpy(pIdentifier->Description, "Direct3D HAL"); - BOOL isGLInfoValid = This->isGLInfoValid; - - /* FillGLCaps updates gl_info, but we only want to store and - reuse the values once we have a context which is valid. Values from - a temporary context may differ from the final ones */ - if (!isGLInfoValid) { - /* If we don't know the device settings, go query them now */ - isGLInfoValid = IWineD3DImpl_FillGLCaps(iface, IWineD3DImpl_GetAdapterDisplay(iface, Adapter)); - } - - /* Return the information requested */ - TRACE_(d3d_caps)("device/Vendor Name and Version detection using FillGLCaps\n"); - strcpy(pIdentifier->Driver, "Display"); - strcpy(pIdentifier->Description, "Direct3D HAL"); - - /* Note dx8 doesn't supply a DeviceName */ - if (NULL != pIdentifier->DeviceName) strcpy(pIdentifier->DeviceName, "\\\\.\\DISPLAY"); /* FIXME: May depend on desktop? */ - /* Current Windows drivers have versions like 6.14.... (some older have an earlier version) */ - pIdentifier->DriverVersion->u.HighPart = MAKEDWORD_VERSION(6, 14); - pIdentifier->DriverVersion->u.LowPart = This->gl_info.gl_driver_version; - *(pIdentifier->VendorId) = This->gl_info.gl_vendor; - *(pIdentifier->DeviceId) = This->gl_info.gl_card; - *(pIdentifier->SubSysId) = 0; - *(pIdentifier->Revision) = 0; - - /*FIXME: memcpy(&pIdentifier->DeviceIdentifier, ??, sizeof(??GUID)); */ - if (Flags & WINED3DENUM_NO_WHQL_LEVEL) { - *(pIdentifier->WHQLLevel) = 0; - } else { - *(pIdentifier->WHQLLevel) = 1; - } + /* Note dx8 doesn't supply a DeviceName */ + if (NULL != pIdentifier->DeviceName) strcpy(pIdentifier->DeviceName, "\\\\.\\DISPLAY"); /* FIXME: May depend on desktop? */ + /* Current Windows drivers have versions like 6.14.... (some older have an earlier version) */ + pIdentifier->DriverVersion->u.HighPart = MAKEDWORD_VERSION(6, 14); + pIdentifier->DriverVersion->u.LowPart = Adapters[Adapter].gl_info.gl_driver_version; + *(pIdentifier->VendorId) = Adapters[Adapter].gl_info.gl_vendor; + *(pIdentifier->DeviceId) = Adapters[Adapter].gl_info.gl_card; + *(pIdentifier->SubSysId) = 0; + *(pIdentifier->Revision) = 0; + /*FIXME: memcpy(&pIdentifier->DeviceIdentifier, ??, sizeof(??GUID)); */ + if (Flags & WINED3DENUM_NO_WHQL_LEVEL) { + *(pIdentifier->WHQLLevel) = 0; } else { - FIXME_(d3d_caps)("Adapter not primary display\n"); + *(pIdentifier->WHQLLevel) = 1; } return WINED3D_OK; @@ -1512,6 +1486,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface, UINT return WINED3DERR_INVALIDCALL; } + /* TODO: Store an array in the adapter */ if(WineD3D_CreateFakeGLContext()) cfgs = glXGetFBConfigs(wined3d_fake_gl_context_display, DefaultScreen(wined3d_fake_gl_context_display), &nCfgs); @@ -1559,6 +1534,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, U return WINED3DERR_INVALIDCALL; } + /* TODO: Store in Adapter structure */ if (pQualityLevels != NULL) { static int s_single_shot = 0; if (!s_single_shot) { @@ -1594,6 +1570,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceType(IWineD3D *iface, UINT Adapter return WINED3DERR_INVALIDCALL; } + /* TODO: Store in adapter structure */ if (WineD3D_CreateFakeGLContext()) { cfgs = glXGetFBConfigs(wined3d_fake_gl_context_display, DefaultScreen(wined3d_fake_gl_context_display), &nCfgs); for (it = 0; it < nCfgs; ++it) { @@ -1615,6 +1592,7 @@ static HRESULT WINAPI IWineD3DImpl_CheckDeviceType(IWineD3D *iface, UINT Adapter return hr; } +#define GLINFO_LOCATION Adapters[Adapter].gl_info static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType, WINED3DFORMAT AdapterFormat, DWORD Usage, WINED3DRESOURCETYPE RType, WINED3DFORMAT CheckFormat) { IWineD3DImpl *This = (IWineD3DImpl *)iface; @@ -1923,21 +1901,11 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter, return WINED3DERR_INVALIDCALL; } - /* FIXME: GL info should be per adapter */ - - /* If we don't know the device settings, go query them now */ - if (!This->isGLInfoValid) { - /* use the desktop window to fill gl caps */ - BOOL rc = IWineD3DImpl_FillGLCaps(iface, IWineD3DImpl_GetAdapterDisplay(iface, Adapter)); - - /* We are running off a real context, save the values */ - if (rc) This->isGLInfoValid = TRUE; - } - select_shader_mode(&This->gl_info, DeviceType, &ps_selected_mode, &vs_selected_mode); + select_shader_mode(&Adapters[Adapter].gl_info, DeviceType, &ps_selected_mode, &vs_selected_mode); /* This function should *not* be modifying GL caps * TODO: move the functionality where it belongs */ - select_shader_max_constants(ps_selected_mode, vs_selected_mode, &This->gl_info); + select_shader_max_constants(ps_selected_mode, vs_selected_mode, &Adapters[Adapter].gl_info); /* ------------------------------------------------ The following fields apply to both d3d8 and d3d9 @@ -2312,7 +2280,7 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter, models with GLSL support only support 2.0. In case of nvidia we can detect VS 2.0 support using vs_nv_version which is based on NV_vertex_program. For Ati cards there's no easy way, so for now only support 2.0/3.0 detection on Nvidia GeforceFX cards and default to 3.0 for everything else */ - if(This->gl_info.vs_nv_version == VS_VERSION_20) + if(GLINFO_LOCATION.vs_nv_version == VS_VERSION_20) *pCaps->VertexShaderVersion = WINED3DVS_VERSION(2,0); else *pCaps->VertexShaderVersion = WINED3DVS_VERSION(3,0); @@ -2330,7 +2298,7 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter, if (ps_selected_mode == SHADER_GLSL) { /* See the comment about VS2.0/VS3.0 detection as we do the same here but then based on NV_fragment_program in case of GeforceFX cards. */ - if(This->gl_info.ps_nv_version == PS_VERSION_20) + if(GLINFO_LOCATION.ps_nv_version == PS_VERSION_20) *pCaps->PixelShaderVersion = WINED3DPS_VERSION(2,0); else *pCaps->PixelShaderVersion = WINED3DPS_VERSION(3,0); @@ -2391,15 +2359,15 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter, use the VS 3.0 from MSDN or else if there's OpenGL spec use a hardcoded value minimum VS3.0 value. */ *pCaps->VS20Caps.Caps = WINED3DVS20CAPS_PREDICATION; *pCaps->VS20Caps.DynamicFlowControlDepth = WINED3DVS20_MAX_DYNAMICFLOWCONTROLDEPTH; /* VS 3.0 requires MAX_DYNAMICFLOWCONTROLDEPTH (24) */ - *pCaps->VS20Caps.NumTemps = max(32, This->gl_info.vs_arb_max_temps); + *pCaps->VS20Caps.NumTemps = max(32, GLINFO_LOCATION.vs_arb_max_temps); *pCaps->VS20Caps.StaticFlowControlDepth = WINED3DVS20_MAX_STATICFLOWCONTROLDEPTH ; /* level of nesting in loops / if-statements; VS 3.0 requires MAX (4) */ *pCaps->MaxVShaderInstructionsExecuted = 65535; /* VS 3.0 needs at least 65535, some cards even use 2^32-1 */ - *pCaps->MaxVertexShader30InstructionSlots = max(512, This->gl_info.vs_arb_max_instructions); + *pCaps->MaxVertexShader30InstructionSlots = max(512, GLINFO_LOCATION.vs_arb_max_instructions); } else if(*pCaps->VertexShaderVersion == WINED3DVS_VERSION(2,0)) { *pCaps->VS20Caps.Caps = 0; *pCaps->VS20Caps.DynamicFlowControlDepth = WINED3DVS20_MIN_DYNAMICFLOWCONTROLDEPTH; - *pCaps->VS20Caps.NumTemps = max(12, This->gl_info.vs_arb_max_temps); + *pCaps->VS20Caps.NumTemps = max(12, GLINFO_LOCATION.vs_arb_max_temps); *pCaps->VS20Caps.StaticFlowControlDepth = 1; *pCaps->MaxVShaderInstructionsExecuted = 65535; @@ -2425,17 +2393,17 @@ static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter, WINED3DPS20CAPS_NODEPENDENTREADLIMIT | WINED3DPS20CAPS_NOTEXINSTRUCTIONLIMIT; *pCaps->PS20Caps.DynamicFlowControlDepth = WINED3DPS20_MAX_DYNAMICFLOWCONTROLDEPTH; /* PS 3.0 requires MAX_DYNAMICFLOWCONTROLDEPTH (24) */ - *pCaps->PS20Caps.NumTemps = max(32, This->gl_info.ps_arb_max_temps); + *pCaps->PS20Caps.NumTemps = max(32, GLINFO_LOCATION.ps_arb_max_temps); *pCaps->PS20Caps.StaticFlowControlDepth = WINED3DPS20_MAX_STATICFLOWCONTROLDEPTH; /* PS 3.0 requires MAX_STATICFLOWCONTROLDEPTH (4) */ *pCaps->PS20Caps.NumInstructionSlots = WINED3DPS20_MAX_NUMINSTRUCTIONSLOTS; /* PS 3.0 requires MAX_NUMINSTRUCTIONSLOTS (512) */ *pCaps->MaxPShaderInstructionsExecuted = 65535; - *pCaps->MaxPixelShader30InstructionSlots = max(WINED3DMIN30SHADERINSTRUCTIONS, This->gl_info.ps_arb_max_instructions); + *pCaps->MaxPixelShader30InstructionSlots = max(WINED3DMIN30SHADERINSTRUCTIONS, GLINFO_LOCATION.ps_arb_max_instructions); } else if(*pCaps->PixelShaderVersion == WINED3DPS_VERSION(2,0)) { /* Below we assume PS2.0 specs, not extended 2.0a(GeforceFX)/2.0b(Radeon R3xx) ones */ *pCaps->PS20Caps.Caps = 0; *pCaps->PS20Caps.DynamicFlowControlDepth = 0; /* WINED3DVS20_MIN_DYNAMICFLOWCONTROLDEPTH = 0 */ - *pCaps->PS20Caps.NumTemps = max(12, This->gl_info.ps_arb_max_temps); + *pCaps->PS20Caps.NumTemps = max(12, GLINFO_LOCATION.ps_arb_max_temps); *pCaps->PS20Caps.StaticFlowControlDepth = WINED3DPS20_MIN_STATICFLOWCONTROLDEPTH; /* Minumum: 1 */ *pCaps->PS20Caps.NumInstructionSlots = WINED3DPS20_MIN_NUMINSTRUCTIONSLOTS; /* Minimum number (64 ALU + 32 Texture), a GeforceFX uses 512 */ @@ -2505,6 +2473,7 @@ static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT Adapter, object->lpVtbl = &IWineD3DDevice_Vtbl; object->ref = 1; object->wineD3D = iface; + object->adapter = &Adapters[Adapter]; IWineD3D_AddRef(object->wineD3D); object->parent = parent; @@ -2538,12 +2507,7 @@ static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT Adapter, IWineD3DStateBlock_AddRef((IWineD3DStateBlock*)object->updateStateBlock); /* Setup surfaces for the backbuffer, frontbuffer and depthstencil buffer */ - /* Setup some defaults for creating the implicit swapchain */ - ENTER_GL(); - /* FIXME: GL info should be per adapter */ - IWineD3DImpl_FillGLCaps(iface, IWineD3DImpl_GetAdapterDisplay(iface, Adapter)); - LEAVE_GL(); - select_shader_mode(&This->gl_info, DeviceType, &object->ps_selected_mode, &object->vs_selected_mode); + select_shader_mode(&GLINFO_LOCATION, DeviceType, &object->ps_selected_mode, &object->vs_selected_mode); if (object->ps_selected_mode == SHADER_GLSL || object->vs_selected_mode == SHADER_GLSL) { object->shader_backend = &glsl_shader_backend; object->glsl_program_lookup = hash_table_create(&glsl_program_key_hash, &glsl_program_key_compare); @@ -2555,7 +2519,7 @@ static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT Adapter, /* This function should *not* be modifying GL caps * TODO: move the functionality where it belongs */ - select_shader_max_constants(object->ps_selected_mode, object->vs_selected_mode, &This->gl_info); + select_shader_max_constants(object->ps_selected_mode, object->vs_selected_mode, &GLINFO_LOCATION); temp_result = allocate_shader_constants(object->updateStateBlock); if (WINED3D_OK != temp_result) @@ -2602,6 +2566,7 @@ create_device_error: return WINED3DERR_INVALIDCALL; } +#undef GLINFO_LOCATION static HRESULT WINAPI IWineD3DImpl_GetParent(IWineD3D *iface, IUnknown **pParent) { IWineD3DImpl *This = (IWineD3DImpl *)iface; @@ -2630,6 +2595,40 @@ ULONG WINAPI D3DCB_DefaultDestroyVolume(IWineD3DVolume *pVolume) { return IUnknown_Release(volumeParent); } +BOOL InitAdapters(void) { + HDC device_context; + BOOL ret; + + /* No need to hold any lock. The calling library makes sure only one thread calls + * wined3d simultaneously + */ + if(numAdapters > 0) return TRUE; + + TRACE("Initializing adapters\n"); + /* For now only one default adapter */ + { + TRACE("Initializing default adapter\n"); + Adapters[0].monitorPoint.x = -1; + Adapters[0].monitorPoint.y = -1; + + device_context = GetDC(0); + Adapters[0].display = get_display(device_context); + ReleaseDC(0, device_context); + + ret = IWineD3DImpl_FillGLCaps(&Adapters[0].gl_info, Adapters[0].display); + if(ret != TRUE) { + ERR("Failed to initialize gl caps for default adapter\n"); + HeapFree(GetProcessHeap(), 0, Adapters); + return FALSE; + } + } + numAdapters = 1; + TRACE("%d adapters successfully initialized\n", numAdapters); + + return TRUE; +} + + /********************************************************** * IWineD3D VTbl follows **********************************************************/ diff --git a/dlls/wined3d/drawprim.c b/dlls/wined3d/drawprim.c index bfe90307778..16504d5ef42 100644 --- a/dlls/wined3d/drawprim.c +++ b/dlls/wined3d/drawprim.c @@ -27,7 +27,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d_draw); -#define GLINFO_LOCATION ((IWineD3DImpl *)(This->wineD3D))->gl_info +#define GLINFO_LOCATION This->adapter->gl_info #include diff --git a/dlls/wined3d/glsl_shader.c b/dlls/wined3d/glsl_shader.c index 6636892eb66..49998418183 100644 --- a/dlls/wined3d/glsl_shader.c +++ b/dlls/wined3d/glsl_shader.c @@ -287,7 +287,7 @@ void shader_glsl_load_constants( IWineD3DDeviceImpl* deviceImpl = (IWineD3DDeviceImpl*) device; IWineD3DStateBlockImpl* stateBlock = deviceImpl->stateBlock; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl*) deviceImpl->wineD3D)->gl_info; + WineD3D_GL_Info *gl_info = &deviceImpl->adapter->gl_info; GLhandleARB *constant_locations; struct list *constant_list; @@ -583,7 +583,7 @@ static void shader_glsl_get_register_name( DWORD regtype = shader_get_regtype(param); IWineD3DBaseShaderImpl* This = (IWineD3DBaseShaderImpl*) arg->shader; IWineD3DDeviceImpl* deviceImpl = (IWineD3DDeviceImpl*) This->baseShader.device; - WineD3D_GL_Info* gl_info = &((IWineD3DImpl*)deviceImpl->wineD3D)->gl_info; + WineD3D_GL_Info* gl_info = &deviceImpl->adapter->gl_info; char pshader = shader_is_pshader_version(This->baseShader.hex_version); char tmpStr[50]; @@ -2099,7 +2099,7 @@ static struct glsl_shader_prog_link *get_glsl_program_entry(IWineD3DDeviceImpl * void delete_glsl_program_entry(IWineD3DDevice *iface, struct glsl_shader_prog_link *entry) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; glsl_program_key_t *key; key = HeapAlloc(GetProcessHeap(), 0, sizeof(glsl_program_key_t)); @@ -2125,7 +2125,7 @@ void delete_glsl_program_entry(IWineD3DDevice *iface, struct glsl_shader_prog_li */ static void set_glsl_shader_program(IWineD3DDevice *iface, BOOL use_ps, BOOL use_vs) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; IWineD3DPixelShader *pshader = This->stateBlock->pixelShader; IWineD3DVertexShader *vshader = This->stateBlock->vertexShader; struct glsl_shader_prog_link *entry = NULL; @@ -2250,7 +2250,7 @@ static GLhandleARB create_glsl_blt_shader(WineD3D_GL_Info *gl_info) { static void shader_glsl_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; GLhandleARB program_id = 0; if (useVS || usePS) set_glsl_shader_program(iface, usePS, useVS); @@ -2264,7 +2264,7 @@ static void shader_glsl_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) { static void shader_glsl_select_depth_blt(IWineD3DDevice *iface) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; static GLhandleARB program_id = 0; static GLhandleARB loc = -1; @@ -2279,7 +2279,7 @@ static void shader_glsl_select_depth_blt(IWineD3DDevice *iface) { static void shader_glsl_cleanup(IWineD3DDevice *iface) { IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface; - WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info; + WineD3D_GL_Info *gl_info = &This->adapter->gl_info; GL_EXTCALL(glUseProgramObjectARB(0)); } diff --git a/dlls/wined3d/indexbuffer.c b/dlls/wined3d/indexbuffer.c index 2d29563de18..9146699b7f5 100644 --- a/dlls/wined3d/indexbuffer.c +++ b/dlls/wined3d/indexbuffer.c @@ -25,7 +25,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info /* ******************************************* IWineD3DIndexBuffer IUnknown parts follow diff --git a/dlls/wined3d/pixelshader.c b/dlls/wined3d/pixelshader.c index a8bc50be93e..1f81fbdcf64 100644 --- a/dlls/wined3d/pixelshader.c +++ b/dlls/wined3d/pixelshader.c @@ -31,7 +31,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d_shader); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->baseShader.device)->wineD3D))->gl_info +#define GLINFO_LOCATION ((IWineD3DDeviceImpl *) This->baseShader.device)->adapter->gl_info #if 0 /* Must not be 1 in cvs version */ # define PSTRACE(A) TRACE A diff --git a/dlls/wined3d/query.c b/dlls/wined3d/query.c index 9e6e3241673..99390f867ea 100644 --- a/dlls/wined3d/query.c +++ b/dlls/wined3d/query.c @@ -33,7 +33,7 @@ */ WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->wineD3DDevice->adapter->gl_info /* ******************************************* IWineD3DQuery IUnknown parts follow diff --git a/dlls/wined3d/state.c b/dlls/wined3d/state.c index 3eac19245dd..54c62e4ffdb 100644 --- a/dlls/wined3d/state.c +++ b/dlls/wined3d/state.c @@ -34,7 +34,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d); WINE_DECLARE_DEBUG_CHANNEL(d3d_shader); -#define GLINFO_LOCATION ((IWineD3DImpl *)(stateblock->wineD3DDevice->wineD3D))->gl_info +#define GLINFO_LOCATION stateblock->wineD3DDevice->adapter->gl_info static void state_nogl(DWORD state, IWineD3DStateBlockImpl *stateblock, WineD3DContext *context) { /* Used for states which are not mapped to a gl state as-is, but used somehow different, diff --git a/dlls/wined3d/stateblock.c b/dlls/wined3d/stateblock.c index 28c9a604740..d186e80cf92 100644 --- a/dlls/wined3d/stateblock.c +++ b/dlls/wined3d/stateblock.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->wineD3DDevice->adapter->gl_info /*************************************** * Stateblock helper functions follow diff --git a/dlls/wined3d/surface.c b/dlls/wined3d/surface.c index 6715b1fcea3..2d3b9253162 100644 --- a/dlls/wined3d/surface.c +++ b/dlls/wined3d/surface.c @@ -30,7 +30,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d_surface); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info typedef enum { NO_CONVERSION, diff --git a/dlls/wined3d/texture.c b/dlls/wined3d/texture.c index 794cd0a7606..238a7e47b20 100644 --- a/dlls/wined3d/texture.c +++ b/dlls/wined3d/texture.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info /* ******************************************* IWineD3DTexture IUnknown parts follow diff --git a/dlls/wined3d/utils.c b/dlls/wined3d/utils.c index 04a15a46294..271842026d9 100644 --- a/dlls/wined3d/utils.c +++ b/dlls/wined3d/utils.c @@ -27,7 +27,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(This->wineD3D))->gl_info +#define GLINFO_LOCATION This->adapter->gl_info /***************************************************************************** * Pixel format array @@ -1217,7 +1217,6 @@ void set_tex_op(IWineD3DDevice *iface, BOOL isAlpha, int Stage, WINED3DTEXTUREOP /* Setup the texture operations texture stage states */ void set_tex_op(IWineD3DDevice *iface, BOOL isAlpha, int Stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3) { -#define GLINFO_LOCATION ((IWineD3DImpl *)(This->wineD3D))->gl_info GLenum src1, src2, src3; GLenum opr1, opr2, opr3; GLenum comb_target; @@ -2577,7 +2576,7 @@ DWORD get_flexible_vertex_size(DWORD d3dvtVertexType) { * FALSE otherwise * *********************************************************************/ -#define GLINFO_LOCATION ((IWineD3DImpl *)(This->resource.wineD3DDevice->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info BOOL CalculateTexRect(IWineD3DSurfaceImpl *This, RECT *Rect, float glTexCoord[4]) { int x1 = Rect->left, x2 = Rect->right; diff --git a/dlls/wined3d/vertexbuffer.c b/dlls/wined3d/vertexbuffer.c index 6fd48a9a036..7a7942380e2 100644 --- a/dlls/wined3d/vertexbuffer.c +++ b/dlls/wined3d/vertexbuffer.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info #define VB_MAXDECLCHANGES 100 /* After that number we stop converting */ #define VB_RESETDECLCHANGE 1000 /* Reset the changecount after that number of draws */ diff --git a/dlls/wined3d/vertexshader.c b/dlls/wined3d/vertexshader.c index fbad6fba10b..b5349180f34 100644 --- a/dlls/wined3d/vertexshader.c +++ b/dlls/wined3d/vertexshader.c @@ -31,7 +31,7 @@ WINE_DEFAULT_DEBUG_CHANNEL(d3d_shader); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->baseShader.device)->wineD3D))->gl_info +#define GLINFO_LOCATION ((IWineD3DDeviceImpl *)This->baseShader.device)->adapter->gl_info /* Shader debugging - Change the following line to enable debugging of software vertex shaders */ diff --git a/dlls/wined3d/volume.c b/dlls/wined3d/volume.c index 3566df493d9..d18fea85426 100644 --- a/dlls/wined3d/volume.c +++ b/dlls/wined3d/volume.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info /* ******************************************* IWineD3DVolume IUnknown parts follow diff --git a/dlls/wined3d/volumetexture.c b/dlls/wined3d/volumetexture.c index 33e6234f6c2..79fef1534f8 100644 --- a/dlls/wined3d/volumetexture.c +++ b/dlls/wined3d/volumetexture.c @@ -24,7 +24,7 @@ #include "wined3d_private.h" WINE_DEFAULT_DEBUG_CHANNEL(d3d); -#define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info +#define GLINFO_LOCATION This->resource.wineD3DDevice->adapter->gl_info /* ******************************************* IWineD3DTexture IUnknown parts follow diff --git a/dlls/wined3d/wined3d_main.c b/dlls/wined3d/wined3d_main.c index 5d00ba8c4aa..d232a2b85a2 100644 --- a/dlls/wined3d/wined3d_main.c +++ b/dlls/wined3d/wined3d_main.c @@ -59,7 +59,14 @@ long globalChangeGlRam(long glram){ } IWineD3D* WINAPI WineDirect3DCreate(UINT SDKVersion, UINT dxVersion, IUnknown *parent) { - IWineD3DImpl* object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IWineD3DImpl)); + IWineD3DImpl* object; + + if (!InitAdapters()) { + ERR("Failed to initialize direct3d adapters\n"); + return NULL; + } + + object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(IWineD3DImpl)); object->lpVtbl = &IWineD3D_Vtbl; object->dxVersion = dxVersion; object->ref = 1; @@ -72,7 +79,6 @@ IWineD3D* WINAPI WineDirect3DCreate(UINT SDKVersion, UINT dxVersion, IUnknown *p } - TRACE("Created WineD3D object @ %p for d3d%d support\n", object, dxVersion); return (IWineD3D *)object; diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index facdebec229..fdb2cbbf310 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -537,9 +537,6 @@ WineD3DContext *CreateContext(IWineD3DDeviceImpl *This, IWineD3DSurfaceImpl *tar void DestroyContext(IWineD3DDeviceImpl *This, WineD3DContext *context); void apply_fbo_state(IWineD3DDevice *iface); -/* Routine to fill gl caps for swapchains and IWineD3D */ -BOOL IWineD3DImpl_FillGLCaps(IWineD3D *iface, Display* display); - /* Macros for doing basic GPU detection based on opengl capabilities */ #define WINE_D3D6_CAPABLE(gl_info) (gl_info->supported[ARB_MULTITEXTURE]) #define WINE_D3D7_CAPABLE(gl_info) (gl_info->supported[ARB_TEXTURE_COMPRESSION] && gl_info->supported[ARB_TEXTURE_CUBE_MAP] && gl_info->supported[ARB_TEXTURE_ENV_DOT3]) @@ -574,6 +571,16 @@ struct PLIGHTINFOEL { /* The default light parameters */ extern const WINED3DLIGHT WINED3D_default_light; +/* The adapter structure */ +struct WineD3DAdapter +{ + POINT monitorPoint; + Display *display; + WineD3D_GL_Info gl_info; +}; + +extern BOOL InitAdapters(void); + /***************************************************************************** * IWineD3D implementation structure */ @@ -586,10 +593,6 @@ typedef struct IWineD3DImpl /* WineD3D Information */ IUnknown *parent; UINT dxVersion; - - /* GL Information */ - BOOL isGLInfoValid; - WineD3D_GL_Info gl_info; } IWineD3DImpl; extern const IWineD3DVtbl IWineD3D_Vtbl; @@ -620,6 +623,7 @@ struct IWineD3DDeviceImpl /* WineD3D Information */ IUnknown *parent; IWineD3D *wineD3D; + struct WineD3DAdapter *adapter; /* Window styles to restore when switching fullscreen mode */ LONG style;