wined3d: Recognize Evergreen in select_card_ati_mesa().
[wine] / dlls / wined3d / directx.c
1 /*
2  * IWineD3D implementation
3  *
4  * Copyright 2002-2004 Jason Edmeades
5  * Copyright 2003-2004 Raphael Junqueira
6  * Copyright 2004 Christian Costa
7  * Copyright 2005 Oliver Stieber
8  * Copyright 2007-2008 Stefan Dösinger for CodeWeavers
9  * Copyright 2009 Henri Verbeet for CodeWeavers
10  *
11  * This library is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU Lesser General Public
13  * License as published by the Free Software Foundation; either
14  * version 2.1 of the License, or (at your option) any later version.
15  *
16  * This library is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19  * Lesser General Public License for more details.
20  *
21  * You should have received a copy of the GNU Lesser General Public
22  * License along with this library; if not, write to the Free Software
23  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
24  */
25
26 #include "config.h"
27 #include <stdio.h>
28 #include "wined3d_private.h"
29
30 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
31 WINE_DECLARE_DEBUG_CHANNEL(d3d_caps);
32
33 #define WINE_DEFAULT_VIDMEM (64 * 1024 * 1024)
34
35 /* The d3d device ID */
36 static const GUID IID_D3DDEVICE_D3DUID = { 0xaeb2cdd4, 0x6e41, 0x43ea, { 0x94,0x1c,0x83,0x61,0xcc,0x76,0x07,0x81 } };
37
38 /* Extension detection */
39 static const struct {
40     const char *extension_string;
41     GL_SupportedExt extension;
42     DWORD version;
43 } EXTENSION_MAP[] = {
44     /* APPLE */
45     {"GL_APPLE_client_storage",             APPLE_CLIENT_STORAGE,           0                           },
46     {"GL_APPLE_fence",                      APPLE_FENCE,                    0                           },
47     {"GL_APPLE_float_pixels",               APPLE_FLOAT_PIXELS,             0                           },
48     {"GL_APPLE_flush_buffer_range",         APPLE_FLUSH_BUFFER_RANGE,       0                           },
49     {"GL_APPLE_flush_render",               APPLE_FLUSH_RENDER,             0                           },
50     {"GL_APPLE_ycbcr_422",                  APPLE_YCBCR_422,                0                           },
51
52     /* ARB */
53     {"GL_ARB_color_buffer_float",           ARB_COLOR_BUFFER_FLOAT,         0                           },
54     {"GL_ARB_depth_buffer_float",           ARB_DEPTH_BUFFER_FLOAT,         0                           },
55     {"GL_ARB_depth_clamp",                  ARB_DEPTH_CLAMP,                0                           },
56     {"GL_ARB_depth_texture",                ARB_DEPTH_TEXTURE,              0                           },
57     {"GL_ARB_draw_buffers",                 ARB_DRAW_BUFFERS,               0                           },
58     {"GL_ARB_fragment_program",             ARB_FRAGMENT_PROGRAM,           0                           },
59     {"GL_ARB_fragment_shader",              ARB_FRAGMENT_SHADER,            0                           },
60     {"GL_ARB_framebuffer_object",           ARB_FRAMEBUFFER_OBJECT,         0                           },
61     {"GL_ARB_geometry_shader4",             ARB_GEOMETRY_SHADER4,           0                           },
62     {"GL_ARB_half_float_pixel",             ARB_HALF_FLOAT_PIXEL,           0                           },
63     {"GL_ARB_half_float_vertex",            ARB_HALF_FLOAT_VERTEX,          0                           },
64     {"GL_ARB_imaging",                      ARB_IMAGING,                    0                           },
65     {"GL_ARB_map_buffer_range",             ARB_MAP_BUFFER_RANGE,           0                           },
66     {"GL_ARB_multisample",                  ARB_MULTISAMPLE,                0                           }, /* needs GLX_ARB_MULTISAMPLE as well */
67     {"GL_ARB_multitexture",                 ARB_MULTITEXTURE,               0                           },
68     {"GL_ARB_occlusion_query",              ARB_OCCLUSION_QUERY,            0                           },
69     {"GL_ARB_pixel_buffer_object",          ARB_PIXEL_BUFFER_OBJECT,        0                           },
70     {"GL_ARB_point_parameters",             ARB_POINT_PARAMETERS,           0                           },
71     {"GL_ARB_point_sprite",                 ARB_POINT_SPRITE,               0                           },
72     {"GL_ARB_provoking_vertex",             ARB_PROVOKING_VERTEX,           0                           },
73     {"GL_ARB_shader_objects",               ARB_SHADER_OBJECTS,             0                           },
74     {"GL_ARB_shader_texture_lod",           ARB_SHADER_TEXTURE_LOD,         0                           },
75     {"GL_ARB_shading_language_100",         ARB_SHADING_LANGUAGE_100,       0                           },
76     {"GL_ARB_shadow",                       ARB_SHADOW,                     0                           },
77     {"GL_ARB_sync",                         ARB_SYNC,                       0                           },
78     {"GL_ARB_texture_border_clamp",         ARB_TEXTURE_BORDER_CLAMP,       0                           },
79     {"GL_ARB_texture_compression",          ARB_TEXTURE_COMPRESSION,        0                           },
80     {"GL_ARB_texture_compression_rgtc",     ARB_TEXTURE_COMPRESSION_RGTC,   0                           },
81     {"GL_ARB_texture_cube_map",             ARB_TEXTURE_CUBE_MAP,           0                           },
82     {"GL_ARB_texture_env_add",              ARB_TEXTURE_ENV_ADD,            0                           },
83     {"GL_ARB_texture_env_combine",          ARB_TEXTURE_ENV_COMBINE,        0                           },
84     {"GL_ARB_texture_env_dot3",             ARB_TEXTURE_ENV_DOT3,           0                           },
85     {"GL_ARB_texture_float",                ARB_TEXTURE_FLOAT,              0                           },
86     {"GL_ARB_texture_mirrored_repeat",      ARB_TEXTURE_MIRRORED_REPEAT,    0                           },
87     {"GL_ARB_texture_non_power_of_two",     ARB_TEXTURE_NON_POWER_OF_TWO,   MAKEDWORD_VERSION(2, 0)     },
88     {"GL_ARB_texture_rectangle",            ARB_TEXTURE_RECTANGLE,          0                           },
89     {"GL_ARB_texture_rg",                   ARB_TEXTURE_RG,                 0                           },
90     {"GL_ARB_vertex_array_bgra",            ARB_VERTEX_ARRAY_BGRA,          0                           },
91     {"GL_ARB_vertex_blend",                 ARB_VERTEX_BLEND,               0                           },
92     {"GL_ARB_vertex_buffer_object",         ARB_VERTEX_BUFFER_OBJECT,       0                           },
93     {"GL_ARB_vertex_program",               ARB_VERTEX_PROGRAM,             0                           },
94     {"GL_ARB_vertex_shader",                ARB_VERTEX_SHADER,              0                           },
95
96     /* ATI */
97     {"GL_ATI_fragment_shader",              ATI_FRAGMENT_SHADER,            0                           },
98     {"GL_ATI_separate_stencil",             ATI_SEPARATE_STENCIL,           0                           },
99     {"GL_ATI_texture_compression_3dc",      ATI_TEXTURE_COMPRESSION_3DC,    0                           },
100     {"GL_ATI_texture_env_combine3",         ATI_TEXTURE_ENV_COMBINE3,       0                           },
101     {"GL_ATI_texture_mirror_once",          ATI_TEXTURE_MIRROR_ONCE,        0                           },
102
103     /* EXT */
104     {"GL_EXT_blend_color",                  EXT_BLEND_COLOR,                0                           },
105     {"GL_EXT_blend_equation_separate",      EXT_BLEND_EQUATION_SEPARATE,    0                           },
106     {"GL_EXT_blend_func_separate",          EXT_BLEND_FUNC_SEPARATE,        0                           },
107     {"GL_EXT_blend_minmax",                 EXT_BLEND_MINMAX,               0                           },
108     {"GL_EXT_depth_bounds_test",            EXT_DEPTH_BOUNDS_TEST,          0                           },
109     {"GL_EXT_draw_buffers2",                EXT_DRAW_BUFFERS2,              0                           },
110     {"GL_EXT_fog_coord",                    EXT_FOG_COORD,                  0                           },
111     {"GL_EXT_framebuffer_blit",             EXT_FRAMEBUFFER_BLIT,           0                           },
112     {"GL_EXT_framebuffer_multisample",      EXT_FRAMEBUFFER_MULTISAMPLE,    0                           },
113     {"GL_EXT_framebuffer_object",           EXT_FRAMEBUFFER_OBJECT,         0                           },
114     {"GL_EXT_gpu_program_parameters",       EXT_GPU_PROGRAM_PARAMETERS,     0                           },
115     {"GL_EXT_gpu_shader4",                  EXT_GPU_SHADER4,                0                           },
116     {"GL_EXT_packed_depth_stencil",         EXT_PACKED_DEPTH_STENCIL,       0                           },
117     {"GL_EXT_paletted_texture",             EXT_PALETTED_TEXTURE,           0                           },
118     {"GL_EXT_point_parameters",             EXT_POINT_PARAMETERS,           0                           },
119     {"GL_EXT_provoking_vertex",             EXT_PROVOKING_VERTEX,           0                           },
120     {"GL_EXT_secondary_color",              EXT_SECONDARY_COLOR,            0                           },
121     {"GL_EXT_stencil_two_side",             EXT_STENCIL_TWO_SIDE,           0                           },
122     {"GL_EXT_stencil_wrap",                 EXT_STENCIL_WRAP,               0                           },
123     {"GL_EXT_texture3D",                    EXT_TEXTURE3D,                  MAKEDWORD_VERSION(1, 2)     },
124     {"GL_EXT_texture_compression_rgtc",     EXT_TEXTURE_COMPRESSION_RGTC,   0                           },
125     {"GL_EXT_texture_compression_s3tc",     EXT_TEXTURE_COMPRESSION_S3TC,   0                           },
126     {"GL_EXT_texture_env_add",              EXT_TEXTURE_ENV_ADD,            0                           },
127     {"GL_EXT_texture_env_combine",          EXT_TEXTURE_ENV_COMBINE,        0                           },
128     {"GL_EXT_texture_env_dot3",             EXT_TEXTURE_ENV_DOT3,           0                           },
129     {"GL_EXT_texture_filter_anisotropic",   EXT_TEXTURE_FILTER_ANISOTROPIC, 0                           },
130     {"GL_EXT_texture_lod_bias",             EXT_TEXTURE_LOD_BIAS,           0                           },
131     {"GL_EXT_texture_sRGB",                 EXT_TEXTURE_SRGB,               0                           },
132     {"GL_EXT_vertex_array_bgra",            EXT_VERTEX_ARRAY_BGRA,          0                           },
133
134     /* NV */
135     {"GL_NV_depth_clamp",                   NV_DEPTH_CLAMP,                 0                           },
136     {"GL_NV_fence",                         NV_FENCE,                       0                           },
137     {"GL_NV_fog_distance",                  NV_FOG_DISTANCE,                0                           },
138     {"GL_NV_fragment_program",              NV_FRAGMENT_PROGRAM,            0                           },
139     {"GL_NV_fragment_program2",             NV_FRAGMENT_PROGRAM2,           0                           },
140     {"GL_NV_fragment_program_option",       NV_FRAGMENT_PROGRAM_OPTION,     0                           },
141     {"GL_NV_half_float",                    NV_HALF_FLOAT,                  0                           },
142     {"GL_NV_light_max_exponent",            NV_LIGHT_MAX_EXPONENT,          0                           },
143     {"GL_NV_point_sprite",                  NV_POINT_SPRITE,                0                           },
144     {"GL_NV_register_combiners",            NV_REGISTER_COMBINERS,          0                           },
145     {"GL_NV_register_combiners2",           NV_REGISTER_COMBINERS2,         0                           },
146     {"GL_NV_texgen_reflection",             NV_TEXGEN_REFLECTION,           0                           },
147     {"GL_NV_texture_env_combine4",          NV_TEXTURE_ENV_COMBINE4,        0                           },
148     {"GL_NV_texture_shader",                NV_TEXTURE_SHADER,              0                           },
149     {"GL_NV_texture_shader2",               NV_TEXTURE_SHADER2,             0                           },
150     {"GL_NV_vertex_program",                NV_VERTEX_PROGRAM,              0                           },
151     {"GL_NV_vertex_program1_1",             NV_VERTEX_PROGRAM1_1,           0                           },
152     {"GL_NV_vertex_program2",               NV_VERTEX_PROGRAM2,             0                           },
153     {"GL_NV_vertex_program2_option",        NV_VERTEX_PROGRAM2_OPTION,      0                           },
154     {"GL_NV_vertex_program3",               NV_VERTEX_PROGRAM3,             0                           },
155
156     /* SGI */
157     {"GL_SGIS_generate_mipmap",             SGIS_GENERATE_MIPMAP,           0                           },
158 };
159
160 /**********************************************************
161  * Utility functions follow
162  **********************************************************/
163
164 const struct min_lookup minMipLookup[] =
165 {
166     /* NONE         POINT                       LINEAR */
167     {{GL_NEAREST,   GL_NEAREST,                 GL_NEAREST}},               /* NONE */
168     {{GL_NEAREST,   GL_NEAREST_MIPMAP_NEAREST,  GL_NEAREST_MIPMAP_LINEAR}}, /* POINT*/
169     {{GL_LINEAR,    GL_LINEAR_MIPMAP_NEAREST,   GL_LINEAR_MIPMAP_LINEAR}},  /* LINEAR */
170 };
171
172 const struct min_lookup minMipLookup_noFilter[] =
173 {
174     /* NONE         POINT                       LINEAR */
175     {{GL_NEAREST,   GL_NEAREST,                 GL_NEAREST}},               /* NONE */
176     {{GL_NEAREST,   GL_NEAREST,                 GL_NEAREST}},               /* POINT */
177     {{GL_NEAREST,   GL_NEAREST,                 GL_NEAREST}},               /* LINEAR */
178 };
179
180 const struct min_lookup minMipLookup_noMip[] =
181 {
182     /* NONE         POINT                       LINEAR */
183     {{GL_NEAREST,   GL_NEAREST,                 GL_NEAREST}},               /* NONE */
184     {{GL_NEAREST,   GL_NEAREST,                 GL_NEAREST}},               /* POINT */
185     {{GL_LINEAR,    GL_LINEAR,                  GL_LINEAR }},               /* LINEAR */
186 };
187
188 const GLenum magLookup[] =
189 {
190     /* NONE     POINT       LINEAR */
191     GL_NEAREST, GL_NEAREST, GL_LINEAR,
192 };
193
194 const GLenum magLookup_noFilter[] =
195 {
196     /* NONE     POINT       LINEAR */
197     GL_NEAREST, GL_NEAREST, GL_NEAREST,
198 };
199
200 /* drawStridedSlow attributes */
201 glAttribFunc position_funcs[WINED3D_FFP_EMIT_COUNT];
202 glAttribFunc diffuse_funcs[WINED3D_FFP_EMIT_COUNT];
203 glAttribFunc specular_func_3ubv;
204 glAttribFunc specular_funcs[WINED3D_FFP_EMIT_COUNT];
205 glAttribFunc normal_funcs[WINED3D_FFP_EMIT_COUNT];
206 glMultiTexCoordFunc multi_texcoord_funcs[WINED3D_FFP_EMIT_COUNT];
207
208 /**
209  * Note: GL seems to trap if GetDeviceCaps is called before any HWND's created,
210  * i.e., there is no GL Context - Get a default rendering context to enable the
211  * function query some info from GL.
212  */
213
214 struct wined3d_fake_gl_ctx
215 {
216     HDC dc;
217     HWND wnd;
218     HGLRC gl_ctx;
219     HDC restore_dc;
220     HGLRC restore_gl_ctx;
221 };
222
223 static void WineD3D_ReleaseFakeGLContext(struct wined3d_fake_gl_ctx *ctx)
224 {
225     TRACE_(d3d_caps)("Destroying fake GL context.\n");
226
227     if (!pwglMakeCurrent(NULL, NULL))
228     {
229         ERR_(d3d_caps)("Failed to disable fake GL context.\n");
230     }
231
232     if (!pwglDeleteContext(ctx->gl_ctx))
233     {
234         DWORD err = GetLastError();
235         ERR("wglDeleteContext(%p) failed, last error %#x.\n", ctx->gl_ctx, err);
236     }
237
238     ReleaseDC(ctx->wnd, ctx->dc);
239     DestroyWindow(ctx->wnd);
240
241     if (ctx->restore_gl_ctx && !pwglMakeCurrent(ctx->restore_dc, ctx->restore_gl_ctx))
242     {
243         ERR_(d3d_caps)("Failed to restore previous GL context.\n");
244     }
245 }
246
247 /* Do not call while under the GL lock. */
248 static BOOL WineD3D_CreateFakeGLContext(struct wined3d_fake_gl_ctx *ctx)
249 {
250     PIXELFORMATDESCRIPTOR pfd;
251     int iPixelFormat;
252
253     TRACE("getting context...\n");
254
255     ctx->restore_dc = pwglGetCurrentDC();
256     ctx->restore_gl_ctx = pwglGetCurrentContext();
257
258     /* We need a fake window as a hdc retrieved using GetDC(0) can't be used for much GL purposes. */
259     ctx->wnd = CreateWindowA(WINED3D_OPENGL_WINDOW_CLASS_NAME, "WineD3D fake window",
260             WS_OVERLAPPEDWINDOW, 10, 10, 10, 10, NULL, NULL, NULL, NULL);
261     if (!ctx->wnd)
262     {
263         ERR_(d3d_caps)("Failed to create a window.\n");
264         goto fail;
265     }
266
267     ctx->dc = GetDC(ctx->wnd);
268     if (!ctx->dc)
269     {
270         ERR_(d3d_caps)("Failed to get a DC.\n");
271         goto fail;
272     }
273
274     /* PixelFormat selection */
275     ZeroMemory(&pfd, sizeof(pfd));
276     pfd.nSize = sizeof(pfd);
277     pfd.nVersion = 1;
278     pfd.dwFlags = PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER | PFD_DRAW_TO_WINDOW; /* PFD_GENERIC_ACCELERATED */
279     pfd.iPixelType = PFD_TYPE_RGBA;
280     pfd.cColorBits = 32;
281     pfd.iLayerType = PFD_MAIN_PLANE;
282
283     iPixelFormat = ChoosePixelFormat(ctx->dc, &pfd);
284     if (!iPixelFormat)
285     {
286         /* If this happens something is very wrong as ChoosePixelFormat barely fails. */
287         ERR_(d3d_caps)("Can't find a suitable iPixelFormat.\n");
288         goto fail;
289     }
290     DescribePixelFormat(ctx->dc, iPixelFormat, sizeof(pfd), &pfd);
291     SetPixelFormat(ctx->dc, iPixelFormat, &pfd);
292
293     /* Create a GL context. */
294     ctx->gl_ctx = pwglCreateContext(ctx->dc);
295     if (!ctx->gl_ctx)
296     {
297         WARN_(d3d_caps)("Error creating default context for capabilities initialization.\n");
298         goto fail;
299     }
300
301     /* Make it the current GL context. */
302     if (!context_set_current(NULL))
303     {
304         ERR_(d3d_caps)("Failed to clear current D3D context.\n");
305     }
306
307     if (!pwglMakeCurrent(ctx->dc, ctx->gl_ctx))
308     {
309         ERR_(d3d_caps)("Failed to make fake GL context current.\n");
310         goto fail;
311     }
312
313     return TRUE;
314
315 fail:
316     if (ctx->gl_ctx) pwglDeleteContext(ctx->gl_ctx);
317     ctx->gl_ctx = NULL;
318     if (ctx->dc) ReleaseDC(ctx->wnd, ctx->dc);
319     ctx->dc = NULL;
320     if (ctx->wnd) DestroyWindow(ctx->wnd);
321     ctx->wnd = NULL;
322     if (ctx->restore_gl_ctx && !pwglMakeCurrent(ctx->restore_dc, ctx->restore_gl_ctx))
323     {
324         ERR_(d3d_caps)("Failed to restore previous GL context.\n");
325     }
326
327     return FALSE;
328 }
329
330 /* Adjust the amount of used texture memory */
331 unsigned int WineD3DAdapterChangeGLRam(IWineD3DDeviceImpl *device, unsigned int glram)
332 {
333     struct wined3d_adapter *adapter = device->adapter;
334
335     adapter->UsedTextureRam += glram;
336     TRACE("Adjusted gl ram by %d to %d\n", glram, adapter->UsedTextureRam);
337     return adapter->UsedTextureRam;
338 }
339
340 static void wined3d_adapter_cleanup(struct wined3d_adapter *adapter)
341 {
342     HeapFree(GetProcessHeap(), 0, adapter->gl_info.formats);
343     HeapFree(GetProcessHeap(), 0, adapter->cfgs);
344 }
345
346 /**********************************************************
347  * IUnknown parts follows
348  **********************************************************/
349
350 static HRESULT WINAPI IWineD3DImpl_QueryInterface(IWineD3D *iface,REFIID riid,LPVOID *ppobj)
351 {
352     IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
353
354     TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(riid),ppobj);
355     if (IsEqualGUID(riid, &IID_IUnknown)
356         || IsEqualGUID(riid, &IID_IWineD3DBase)
357         || IsEqualGUID(riid, &IID_IWineD3DDevice)) {
358         IUnknown_AddRef(iface);
359         *ppobj = This;
360         return S_OK;
361     }
362     *ppobj = NULL;
363     return E_NOINTERFACE;
364 }
365
366 static ULONG WINAPI IWineD3DImpl_AddRef(IWineD3D *iface) {
367     IWineD3DImpl *This = (IWineD3DImpl *)iface;
368     ULONG refCount = InterlockedIncrement(&This->ref);
369
370     TRACE("(%p) : AddRef increasing from %d\n", This, refCount - 1);
371     return refCount;
372 }
373
374 static ULONG WINAPI IWineD3DImpl_Release(IWineD3D *iface) {
375     IWineD3DImpl *This = (IWineD3DImpl *)iface;
376     ULONG ref;
377     TRACE("(%p) : Releasing from %d\n", This, This->ref);
378     ref = InterlockedDecrement(&This->ref);
379
380     if (!ref)
381     {
382         unsigned int i;
383
384         for (i = 0; i < This->adapter_count; ++i)
385         {
386             wined3d_adapter_cleanup(&This->adapters[i]);
387         }
388         HeapFree(GetProcessHeap(), 0, This);
389     }
390
391     return ref;
392 }
393
394 /**********************************************************
395  * IWineD3D parts follows
396  **********************************************************/
397
398 /* GL locking is done by the caller */
399 static inline BOOL test_arb_vs_offset_limit(const struct wined3d_gl_info *gl_info)
400 {
401     GLuint prog;
402     BOOL ret = FALSE;
403     const char *testcode =
404         "!!ARBvp1.0\n"
405         "PARAM C[66] = { program.env[0..65] };\n"
406         "ADDRESS A0;"
407         "PARAM zero = {0.0, 0.0, 0.0, 0.0};\n"
408         "ARL A0.x, zero.x;\n"
409         "MOV result.position, C[A0.x + 65];\n"
410         "END\n";
411
412     while(glGetError());
413     GL_EXTCALL(glGenProgramsARB(1, &prog));
414     if(!prog) {
415         ERR("Failed to create an ARB offset limit test program\n");
416     }
417     GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, prog));
418     GL_EXTCALL(glProgramStringARB(GL_VERTEX_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB,
419                                   strlen(testcode), testcode));
420     if (glGetError())
421     {
422         TRACE("OpenGL implementation does not allow indirect addressing offsets > 63\n");
423         TRACE("error: %s\n", debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
424         ret = TRUE;
425     } else TRACE("OpenGL implementation allows offsets > 63\n");
426
427     GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, 0));
428     GL_EXTCALL(glDeleteProgramsARB(1, &prog));
429     checkGLcall("ARB vp offset limit test cleanup");
430
431     return ret;
432 }
433
434 static DWORD ver_for_ext(GL_SupportedExt ext)
435 {
436     unsigned int i;
437     for (i = 0; i < (sizeof(EXTENSION_MAP) / sizeof(*EXTENSION_MAP)); ++i) {
438         if(EXTENSION_MAP[i].extension == ext) {
439             return EXTENSION_MAP[i].version;
440         }
441     }
442     return 0;
443 }
444
445 static BOOL match_ati_r300_to_500(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
446         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
447 {
448     if (card_vendor != HW_VENDOR_ATI) return FALSE;
449     if (device == CARD_ATI_RADEON_9500) return TRUE;
450     if (device == CARD_ATI_RADEON_X700) return TRUE;
451     if (device == CARD_ATI_RADEON_X1600) return TRUE;
452     return FALSE;
453 }
454
455 static BOOL match_geforce5(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
456         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
457 {
458     if (card_vendor == HW_VENDOR_NVIDIA)
459     {
460         if (device == CARD_NVIDIA_GEFORCEFX_5200 ||
461             device == CARD_NVIDIA_GEFORCEFX_5600 ||
462             device == CARD_NVIDIA_GEFORCEFX_5800)
463         {
464             return TRUE;
465         }
466     }
467     return FALSE;
468 }
469
470 static BOOL match_apple(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
471         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
472 {
473     /* MacOS has various specialities in the extensions it advertises. Some have to be loaded from
474      * the opengl 1.2+ core, while other extensions are advertised, but software emulated. So try to
475      * detect the Apple OpenGL implementation to apply some extension fixups afterwards.
476      *
477      * Detecting this isn't really easy. The vendor string doesn't mention Apple. Compile-time checks
478      * aren't sufficient either because a Linux binary may display on a macos X server via remote X11.
479      * So try to detect the GL implementation by looking at certain Apple extensions. Some extensions
480      * like client storage might be supported on other implementations too, but GL_APPLE_flush_render
481      * is specific to the Mac OS X window management, and GL_APPLE_ycbcr_422 is QuickTime specific. So
482      * the chance that other implementations support them is rather small since Win32 QuickTime uses
483      * DirectDraw, not OpenGL.
484      *
485      * This test has been moved into wined3d_guess_gl_vendor()
486      */
487     if (gl_vendor == GL_VENDOR_APPLE)
488     {
489         return TRUE;
490     }
491     return FALSE;
492 }
493
494 /* Context activation is done by the caller. */
495 static void test_pbo_functionality(struct wined3d_gl_info *gl_info)
496 {
497     /* Some OpenGL implementations, namely Apple's Geforce 8 driver, advertises PBOs,
498      * but glTexSubImage from a PBO fails miserably, with the first line repeated over
499      * all the texture. This function detects this bug by its symptom and disables PBOs
500      * if the test fails.
501      *
502      * The test uploads a 4x4 texture via the PBO in the "native" format GL_BGRA,
503      * GL_UNSIGNED_INT_8_8_8_8_REV. This format triggers the bug, and it is what we use
504      * for D3DFMT_A8R8G8B8. Then the texture is read back without any PBO and the data
505      * read back is compared to the original. If they are equal PBOs are assumed to work,
506      * otherwise the PBO extension is disabled. */
507     GLuint texture, pbo;
508     static const unsigned int pattern[] =
509     {
510         0x00000000, 0x000000ff, 0x0000ff00, 0x40ff0000,
511         0x80ffffff, 0x40ffff00, 0x00ff00ff, 0x0000ffff,
512         0x00ffff00, 0x00ff00ff, 0x0000ffff, 0x000000ff,
513         0x80ff00ff, 0x0000ffff, 0x00ff00ff, 0x40ff00ff
514     };
515     unsigned int check[sizeof(pattern) / sizeof(pattern[0])];
516
517     /* No PBO -> No point in testing them. */
518     if (!gl_info->supported[ARB_PIXEL_BUFFER_OBJECT]) return;
519
520     ENTER_GL();
521
522     while (glGetError());
523     glGenTextures(1, &texture);
524     glBindTexture(GL_TEXTURE_2D, texture);
525
526     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
527     glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 4, 4, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, 0);
528     checkGLcall("Specifying the PBO test texture");
529
530     GL_EXTCALL(glGenBuffersARB(1, &pbo));
531     GL_EXTCALL(glBindBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, pbo));
532     GL_EXTCALL(glBufferDataARB(GL_PIXEL_UNPACK_BUFFER_ARB, sizeof(pattern), pattern, GL_STREAM_DRAW_ARB));
533     checkGLcall("Specifying the PBO test pbo");
534
535     glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 4, 4, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, NULL);
536     checkGLcall("Loading the PBO test texture");
537
538     GL_EXTCALL(glBindBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, 0));
539     LEAVE_GL();
540
541     wglFinish(); /* just to be sure */
542
543     memset(check, 0, sizeof(check));
544     ENTER_GL();
545     glGetTexImage(GL_TEXTURE_2D, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, check);
546     checkGLcall("Reading back the PBO test texture");
547
548     glDeleteTextures(1, &texture);
549     GL_EXTCALL(glDeleteBuffersARB(1, &pbo));
550     checkGLcall("PBO test cleanup");
551
552     LEAVE_GL();
553
554     if (memcmp(check, pattern, sizeof(check)))
555     {
556         WARN_(d3d_caps)("PBO test failed, read back data doesn't match original.\n");
557         WARN_(d3d_caps)("Disabling PBOs. This may result in slower performance.\n");
558         gl_info->supported[ARB_PIXEL_BUFFER_OBJECT] = FALSE;
559     }
560     else
561     {
562         TRACE_(d3d_caps)("PBO test successful.\n");
563     }
564 }
565
566 static BOOL match_apple_intel(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
567         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
568 {
569     return (card_vendor == HW_VENDOR_INTEL) && (gl_vendor == GL_VENDOR_APPLE);
570 }
571
572 static BOOL match_apple_nonr500ati(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
573         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
574 {
575     if (gl_vendor != GL_VENDOR_APPLE) return FALSE;
576     if (card_vendor != HW_VENDOR_ATI) return FALSE;
577     if (device == CARD_ATI_RADEON_X1600) return FALSE;
578     return TRUE;
579 }
580
581 static BOOL match_fglrx(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
582         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
583 {
584     return gl_vendor == GL_VENDOR_FGLRX;
585
586 }
587
588 static BOOL match_dx10_capable(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
589         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
590 {
591     /* DX9 cards support 40 single float varyings in hardware, most drivers report 32. ATI misreports
592      * 44 varyings. So assume that if we have more than 44 varyings we have a dx10 card.
593      * This detection is for the gl_ClipPos varying quirk. If a d3d9 card really supports more than 44
594      * varyings and we subtract one in dx9 shaders its not going to hurt us because the dx9 limit is
595      * hardcoded
596      *
597      * dx10 cards usually have 64 varyings */
598     return gl_info->limits.glsl_varyings > 44;
599 }
600
601 /* A GL context is provided by the caller */
602 static BOOL match_allows_spec_alpha(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
603         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
604 {
605     GLenum error;
606     DWORD data[16];
607
608     if (!gl_info->supported[EXT_SECONDARY_COLOR]) return FALSE;
609
610     ENTER_GL();
611     while(glGetError());
612     GL_EXTCALL(glSecondaryColorPointerEXT)(4, GL_UNSIGNED_BYTE, 4, data);
613     error = glGetError();
614     LEAVE_GL();
615
616     if(error == GL_NO_ERROR)
617     {
618         TRACE("GL Implementation accepts 4 component specular color pointers\n");
619         return TRUE;
620     }
621     else
622     {
623         TRACE("GL implementation does not accept 4 component specular colors, error %s\n",
624               debug_glerror(error));
625         return FALSE;
626     }
627 }
628
629 static BOOL match_apple_nvts(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
630         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
631 {
632     if (!match_apple(gl_info, gl_renderer, gl_vendor, card_vendor, device)) return FALSE;
633     return gl_info->supported[NV_TEXTURE_SHADER];
634 }
635
636 /* A GL context is provided by the caller */
637 static BOOL match_broken_nv_clip(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
638         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
639 {
640     GLuint prog;
641     BOOL ret = FALSE;
642     GLint pos;
643     const char *testcode =
644         "!!ARBvp1.0\n"
645         "OPTION NV_vertex_program2;\n"
646         "MOV result.clip[0], 0.0;\n"
647         "MOV result.position, 0.0;\n"
648         "END\n";
649
650     if (!gl_info->supported[NV_VERTEX_PROGRAM2_OPTION]) return FALSE;
651
652     ENTER_GL();
653     while(glGetError());
654
655     GL_EXTCALL(glGenProgramsARB(1, &prog));
656     if(!prog)
657     {
658         ERR("Failed to create the NVvp clip test program\n");
659         LEAVE_GL();
660         return FALSE;
661     }
662     GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, prog));
663     GL_EXTCALL(glProgramStringARB(GL_VERTEX_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB,
664                                   strlen(testcode), testcode));
665     glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &pos);
666     if(pos != -1)
667     {
668         WARN("GL_NV_vertex_program2_option result.clip[] test failed\n");
669         TRACE("error: %s\n", debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
670         ret = TRUE;
671         while(glGetError());
672     }
673     else TRACE("GL_NV_vertex_program2_option result.clip[] test passed\n");
674
675     GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, 0));
676     GL_EXTCALL(glDeleteProgramsARB(1, &prog));
677     checkGLcall("GL_NV_vertex_program2_option result.clip[] test cleanup");
678
679     LEAVE_GL();
680     return ret;
681 }
682
683 /* Context activation is done by the caller. */
684 static BOOL match_fbo_tex_update(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
685         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
686 {
687     char data[4 * 4 * 4];
688     GLuint tex, fbo;
689     GLenum status;
690
691     if (wined3d_settings.offscreen_rendering_mode != ORM_FBO) return FALSE;
692
693     memset(data, 0xcc, sizeof(data));
694
695     ENTER_GL();
696
697     glGenTextures(1, &tex);
698     glBindTexture(GL_TEXTURE_2D, tex);
699     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
700     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
701     glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 4, 4, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, NULL);
702     checkGLcall("glTexImage2D");
703
704     gl_info->fbo_ops.glGenFramebuffers(1, &fbo);
705     gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, fbo);
706     gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, 0);
707     checkGLcall("glFramebufferTexture2D");
708
709     status = gl_info->fbo_ops.glCheckFramebufferStatus(GL_FRAMEBUFFER);
710     if (status != GL_FRAMEBUFFER_COMPLETE) ERR("FBO status %#x\n", status);
711     checkGLcall("glCheckFramebufferStatus");
712
713     memset(data, 0x11, sizeof(data));
714     glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 4, 4, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, data);
715     checkGLcall("glTexSubImage2D");
716
717     glClearColor(0.996f, 0.729f, 0.745f, 0.792f);
718     glClear(GL_COLOR_BUFFER_BIT);
719     checkGLcall("glClear");
720
721     glGetTexImage(GL_TEXTURE_2D, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, data);
722     checkGLcall("glGetTexImage");
723
724     gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0);
725     gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, 0);
726     glBindTexture(GL_TEXTURE_2D, 0);
727     checkGLcall("glBindTexture");
728
729     gl_info->fbo_ops.glDeleteFramebuffers(1, &fbo);
730     glDeleteTextures(1, &tex);
731     checkGLcall("glDeleteTextures");
732
733     LEAVE_GL();
734
735     return *(DWORD *)data == 0x11111111;
736 }
737
738 static void quirk_arb_constants(struct wined3d_gl_info *gl_info)
739 {
740     TRACE_(d3d_caps)("Using ARB vs constant limit(=%u) for GLSL.\n", gl_info->limits.arb_vs_native_constants);
741     gl_info->limits.glsl_vs_float_constants = gl_info->limits.arb_vs_native_constants;
742     TRACE_(d3d_caps)("Using ARB ps constant limit(=%u) for GLSL.\n", gl_info->limits.arb_ps_native_constants);
743     gl_info->limits.glsl_ps_float_constants = gl_info->limits.arb_ps_native_constants;
744 }
745
746 static void quirk_apple_glsl_constants(struct wined3d_gl_info *gl_info)
747 {
748     quirk_arb_constants(gl_info);
749     /* MacOS needs uniforms for relative addressing offsets. This can accumulate to quite a few uniforms.
750      * Beyond that the general uniform isn't optimal, so reserve a number of uniforms. 12 vec4's should
751      * allow 48 different offsets or other helper immediate values. */
752     TRACE_(d3d_caps)("Reserving 12 GLSL constants for compiler private use.\n");
753     gl_info->reserved_glsl_constants = max(gl_info->reserved_glsl_constants, 12);
754 }
755
756 /* fglrx crashes with a very bad kernel panic if GL_POINT_SPRITE_ARB is set to GL_COORD_REPLACE_ARB
757  * on more than one texture unit. This means that the d3d9 visual point size test will cause a
758  * kernel panic on any machine running fglrx 9.3(latest that supports r300 to r500 cards). This
759  * quirk only enables point sprites on the first texture unit. This keeps point sprites working in
760  * most games, but avoids the crash
761  *
762  * A more sophisticated way would be to find all units that need texture coordinates and enable
763  * point sprites for one if only one is found, and software emulate point sprites in drawStridedSlow
764  * if more than one unit needs texture coordinates(This requires software ffp and vertex shaders though)
765  *
766  * Note that disabling the extension entirely does not gain predictability because there is no point
767  * sprite capability flag in d3d, so the potential rendering bugs are the same if we disable the extension. */
768 static void quirk_one_point_sprite(struct wined3d_gl_info *gl_info)
769 {
770     if (gl_info->supported[ARB_POINT_SPRITE])
771     {
772         TRACE("Limiting point sprites to one texture unit.\n");
773         gl_info->limits.point_sprite_units = 1;
774     }
775 }
776
777 static void quirk_ati_dx9(struct wined3d_gl_info *gl_info)
778 {
779     quirk_arb_constants(gl_info);
780
781     /* MacOS advertises GL_ARB_texture_non_power_of_two on ATI r500 and earlier cards, although
782      * these cards only support GL_ARB_texture_rectangle(D3DPTEXTURECAPS_NONPOW2CONDITIONAL).
783      * If real NP2 textures are used, the driver falls back to software. We could just remove the
784      * extension and use GL_ARB_texture_rectangle instead, but texture_rectangle is inconventient
785      * due to the non-normalized texture coordinates. Thus set an internal extension flag,
786      * GL_WINE_normalized_texrect, which signals the code that it can use non power of two textures
787      * as per GL_ARB_texture_non_power_of_two, but has to stick to the texture_rectangle limits.
788      *
789      * fglrx doesn't advertise GL_ARB_texture_non_power_of_two, but it advertises opengl 2.0 which
790      * has this extension promoted to core. The extension loading code sets this extension supported
791      * due to that, so this code works on fglrx as well. */
792     if(gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO])
793     {
794         TRACE("GL_ARB_texture_non_power_of_two advertised on R500 or earlier card, removing.\n");
795         gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO] = FALSE;
796         gl_info->supported[WINED3D_GL_NORMALIZED_TEXRECT] = TRUE;
797     }
798
799     /* fglrx has the same structural issues as the one described in quirk_apple_glsl_constants, although
800      * it is generally more efficient. Reserve just 8 constants. */
801     TRACE_(d3d_caps)("Reserving 8 GLSL constants for compiler private use.\n");
802     gl_info->reserved_glsl_constants = max(gl_info->reserved_glsl_constants, 8);
803 }
804
805 static void quirk_no_np2(struct wined3d_gl_info *gl_info)
806 {
807     /*  The nVidia GeForceFX series reports OpenGL 2.0 capabilities with the latest drivers versions, but
808      *  doesn't explicitly advertise the ARB_tex_npot extension in the GL extension string.
809      *  This usually means that ARB_tex_npot is supported in hardware as long as the application is staying
810      *  within the limits enforced by the ARB_texture_rectangle extension. This however is not true for the
811      *  FX series, which instantly falls back to a slower software path as soon as ARB_tex_npot is used.
812      *  We therefore completely remove ARB_tex_npot from the list of supported extensions.
813      *
814      *  Note that wine_normalized_texrect can't be used in this case because internally it uses ARB_tex_npot,
815      *  triggering the software fallback. There is not much we can do here apart from disabling the
816      *  software-emulated extension and reenable ARB_tex_rect (which was previously disabled
817      *  in IWineD3DImpl_FillGLCaps).
818      *  This fixup removes performance problems on both the FX 5900 and FX 5700 (e.g. for framebuffer
819      *  post-processing effects in the game "Max Payne 2").
820      *  The behaviour can be verified through a simple test app attached in bugreport #14724. */
821     TRACE("GL_ARB_texture_non_power_of_two advertised through OpenGL 2.0 on NV FX card, removing.\n");
822     gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO] = FALSE;
823     gl_info->supported[ARB_TEXTURE_RECTANGLE] = TRUE;
824 }
825
826 static void quirk_texcoord_w(struct wined3d_gl_info *gl_info)
827 {
828     /* The Intel GPUs on MacOS set the .w register of texcoords to 0.0 by default, which causes problems
829      * with fixed function fragment processing. Ideally this flag should be detected with a test shader
830      * and OpenGL feedback mode, but some GL implementations (MacOS ATI at least, probably all MacOS ones)
831      * do not like vertex shaders in feedback mode and return an error, even though it should be valid
832      * according to the spec.
833      *
834      * We don't want to enable this on all cards, as it adds an extra instruction per texcoord used. This
835      * makes the shader slower and eats instruction slots which should be available to the d3d app.
836      *
837      * ATI Radeon HD 2xxx cards on MacOS have the issue. Instead of checking for the buggy cards, blacklist
838      * all radeon cards on Macs and whitelist the good ones. That way we're prepared for the future. If
839      * this workaround is activated on cards that do not need it, it won't break things, just affect
840      * performance negatively. */
841     TRACE("Enabling vertex texture coord fixes in vertex shaders.\n");
842     gl_info->quirks |= WINED3D_QUIRK_SET_TEXCOORD_W;
843 }
844
845 static void quirk_clip_varying(struct wined3d_gl_info *gl_info)
846 {
847     gl_info->quirks |= WINED3D_QUIRK_GLSL_CLIP_VARYING;
848 }
849
850 static void quirk_allows_specular_alpha(struct wined3d_gl_info *gl_info)
851 {
852     gl_info->quirks |= WINED3D_QUIRK_ALLOWS_SPECULAR_ALPHA;
853 }
854
855 static void quirk_apple_nvts(struct wined3d_gl_info *gl_info)
856 {
857     gl_info->supported[NV_TEXTURE_SHADER] = FALSE;
858     gl_info->supported[NV_TEXTURE_SHADER2] = FALSE;
859 }
860
861 static void quirk_disable_nvvp_clip(struct wined3d_gl_info *gl_info)
862 {
863     gl_info->quirks |= WINED3D_QUIRK_NV_CLIP_BROKEN;
864 }
865
866 static void quirk_fbo_tex_update(struct wined3d_gl_info *gl_info)
867 {
868     gl_info->quirks |= WINED3D_QUIRK_FBO_TEX_UPDATE;
869 }
870
871 struct driver_quirk
872 {
873     BOOL (*match)(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
874             enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device);
875     void (*apply)(struct wined3d_gl_info *gl_info);
876     const char *description;
877 };
878
879 static const struct driver_quirk quirk_table[] =
880 {
881     {
882         match_ati_r300_to_500,
883         quirk_ati_dx9,
884         "ATI GLSL constant and normalized texrect quirk"
885     },
886     /* MacOS advertises more GLSL vertex shader uniforms than supported by the hardware, and if more are
887      * used it falls back to software. While the compiler can detect if the shader uses all declared
888      * uniforms, the optimization fails if the shader uses relative addressing. So any GLSL shader
889      * using relative addressing falls back to software.
890      *
891      * ARB vp gives the correct amount of uniforms, so use it instead of GLSL. */
892     {
893         match_apple,
894         quirk_apple_glsl_constants,
895         "Apple GLSL uniform override"
896     },
897     {
898         match_geforce5,
899         quirk_no_np2,
900         "Geforce 5 NP2 disable"
901     },
902     {
903         match_apple_intel,
904         quirk_texcoord_w,
905         "Init texcoord .w for Apple Intel GPU driver"
906     },
907     {
908         match_apple_nonr500ati,
909         quirk_texcoord_w,
910         "Init texcoord .w for Apple ATI >= r600 GPU driver"
911     },
912     {
913         match_fglrx,
914         quirk_one_point_sprite,
915         "Fglrx point sprite crash workaround"
916     },
917     {
918         match_dx10_capable,
919         quirk_clip_varying,
920         "Reserved varying for gl_ClipPos"
921     },
922     {
923         /* GL_EXT_secondary_color does not allow 4 component secondary colors, but most
924          * GL implementations accept it. The Mac GL is the only implementation known to
925          * reject it.
926          *
927          * If we can pass 4 component specular colors, do it, because (a) we don't have
928          * to screw around with the data, and (b) the D3D fixed function vertex pipeline
929          * passes specular alpha to the pixel shader if any is used. Otherwise the
930          * specular alpha is used to pass the fog coordinate, which we pass to opengl
931          * via GL_EXT_fog_coord.
932          */
933         match_allows_spec_alpha,
934         quirk_allows_specular_alpha,
935         "Allow specular alpha quirk"
936     },
937     {
938         /* The pixel formats provided by GL_NV_texture_shader are broken on OSX
939          * (rdar://5682521).
940          */
941         match_apple_nvts,
942         quirk_apple_nvts,
943         "Apple NV_texture_shader disable"
944     },
945     {
946         match_broken_nv_clip,
947         quirk_disable_nvvp_clip,
948         "Apple NV_vertex_program clip bug quirk"
949     },
950     {
951         match_fbo_tex_update,
952         quirk_fbo_tex_update,
953         "FBO rebind for attachment updates"
954     },
955 };
956
957 /* Certain applications (Steam) complain if we report an outdated driver version. In general,
958  * reporting a driver version is moot because we are not the Windows driver, and we have different
959  * bugs, features, etc.
960  *
961  * The driver version has the form "x.y.z.w".
962  *
963  * "x" is the Windows version the driver is meant for:
964  * 4 -> 95/98/NT4
965  * 5 -> 2000
966  * 6 -> 2000/XP
967  * 7 -> Vista
968  * 8 -> Win 7
969  *
970  * "y" is the maximum Direct3D version the driver supports.
971  * y  -> d3d version mapping:
972  * 11 -> d3d6
973  * 12 -> d3d7
974  * 13 -> d3d8
975  * 14 -> d3d9
976  * 15 -> d3d10
977  * 16 -> d3d10.1
978  * 17 -> d3d11
979  *
980  * "z" is the subversion number.
981  *
982  * "w" is the vendor specific driver build number.
983  */
984
985 struct driver_version_information
986 {
987     enum wined3d_display_driver driver;
988     enum wined3d_driver_model driver_model;
989     const char *driver_name;            /* name of Windows driver */
990     WORD version;                       /* version word ('y'), contained in low word of DriverVersion.HighPart */
991     WORD subversion;                    /* subversion word ('z'), contained in high word of DriverVersion.LowPart */
992     WORD build;                         /* build number ('w'), contained in low word of DriverVersion.LowPart */
993 };
994
995 /* The driver version table contains driver information for different devices on several OS versions. */
996 static const struct driver_version_information driver_version_table[] =
997 {
998     /* ATI
999      * - Radeon HD2x00 (R600) and up supported by current drivers.
1000      * - Radeon 9500 (R300) - X1*00 (R5xx) supported up to Catalyst 9.3 (Linux) and 10.2 (XP/Vista/Win7)
1001      * - Radeon 7xxx (R100) - 9250 (RV250) supported up to Catalyst 6.11 (XP)
1002      * - Rage 128 supported up to XP, latest official build 6.13.3279 dated October 2001 */
1003     {DRIVER_ATI_RAGE_128PRO,    DRIVER_MODEL_NT5X,  "ati2dvaa.dll", 13, 3279,  0},
1004     {DRIVER_ATI_R100,           DRIVER_MODEL_NT5X,  "ati2dvag.dll", 14, 10, 6614},
1005     {DRIVER_ATI_R300,           DRIVER_MODEL_NT5X,  "ati2dvag.dll", 14, 10, 6764},
1006     {DRIVER_ATI_R600,           DRIVER_MODEL_NT5X,  "ati2dvag.dll", 14, 10, 8681},
1007     {DRIVER_ATI_R300,           DRIVER_MODEL_NT6X,  "atiumdag.dll", 14, 10, 741 },
1008     {DRIVER_ATI_R600,           DRIVER_MODEL_NT6X,  "atiumdag.dll", 14, 10, 741 },
1009
1010     /* Intel
1011      * The drivers are unified but not all versions support all GPUs. At some point the 2k/xp
1012      * drivers used ialmrnt5.dll for GMA800/GMA900 but at some point the file was renamed to
1013      * igxprd32.dll but the GMA800 driver was never updated. */
1014     {DRIVER_INTEL_GMA800,       DRIVER_MODEL_NT5X,  "ialmrnt5.dll", 14, 10, 3889},
1015     {DRIVER_INTEL_GMA900,       DRIVER_MODEL_NT5X,  "igxprd32.dll", 14, 10, 4764},
1016     {DRIVER_INTEL_GMA950,       DRIVER_MODEL_NT5X,  "igxprd32.dll", 14, 10, 4926},
1017     {DRIVER_INTEL_GMA3000,      DRIVER_MODEL_NT5X,  "igxprd32.dll", 14, 10, 5218},
1018     {DRIVER_INTEL_GMA950,       DRIVER_MODEL_NT6X,  "igdumd32.dll", 14, 10, 1504},
1019     {DRIVER_INTEL_GMA3000,      DRIVER_MODEL_NT6X,  "igdumd32.dll", 15, 10, 1666},
1020
1021     /* Nvidia
1022      * - Geforce6 and newer cards are supported by the current driver (197.x) on XP-Win7
1023      * - GeforceFX support is up to 173.x on <= XP
1024      * - Geforce2MX/3/4 up to 96.x on <= XP
1025      * - TNT/Geforce1/2 up to 71.x on <= XP
1026      * All version numbers used below are from the Linux nvidia drivers. */
1027     {DRIVER_NVIDIA_TNT,         DRIVER_MODEL_NT5X,  "nv4_disp.dll", 14, 10, 7186},
1028     {DRIVER_NVIDIA_GEFORCE2MX,  DRIVER_MODEL_NT5X,  "nv4_disp.dll", 14, 10, 9371},
1029     {DRIVER_NVIDIA_GEFORCEFX,   DRIVER_MODEL_NT5X,  "nv4_disp.dll", 14, 11, 7516},
1030     {DRIVER_NVIDIA_GEFORCE6,    DRIVER_MODEL_NT5X,  "nv4_disp.dll", 15, 11, 9745},
1031     {DRIVER_NVIDIA_GEFORCE6,    DRIVER_MODEL_NT6X,  "nvd3dum.dll",  15, 11, 9745},
1032 };
1033
1034 struct gpu_description
1035 {
1036     WORD vendor;                    /* reported PCI card vendor ID  */
1037     WORD card;                      /* reported PCI card device ID  */
1038     const char *description;        /* Description of the card e.g. NVIDIA RIVA TNT */
1039     enum wined3d_display_driver driver;
1040     unsigned int vidmem;
1041 };
1042
1043 /* The amount of video memory stored in the gpu description table is the minimum amount of video memory
1044  * found on a board containing a specific GPU. */
1045 static const struct gpu_description gpu_description_table[] =
1046 {
1047     /* Nvidia cards */
1048     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_RIVA_TNT,           "NVIDIA RIVA TNT",                  DRIVER_NVIDIA_TNT,       16  },
1049     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_RIVA_TNT2,          "NVIDIA RIVA TNT2/TNT2 Pro",        DRIVER_NVIDIA_TNT,       32  },
1050     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE,            "NVIDIA GeForce 256",               DRIVER_NVIDIA_TNT,       32  },
1051     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE2,           "NVIDIA GeForce2 GTS/GeForce2 Pro", DRIVER_NVIDIA_TNT,       32  },
1052     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE2_MX,        "NVIDIA GeForce2 MX/MX 400",        DRIVER_NVIDIA_GEFORCE2MX,32  },
1053     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE3,           "NVIDIA GeForce3",                  DRIVER_NVIDIA_GEFORCE2MX,64  },
1054     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE4_MX,        "NVIDIA GeForce4 MX 460",           DRIVER_NVIDIA_GEFORCE2MX,64  },
1055     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE4_TI4200,    "NVIDIA GeForce4 Ti 4200",          DRIVER_NVIDIA_GEFORCE2MX,64, },
1056     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5200,     "NVIDIA GeForce FX 5200",           DRIVER_NVIDIA_GEFORCEFX, 64  },
1057     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5600,     "NVIDIA GeForce FX 5600",           DRIVER_NVIDIA_GEFORCEFX, 128 },
1058     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCEFX_5800,     "NVIDIA GeForce FX 5800",           DRIVER_NVIDIA_GEFORCEFX, 256 },
1059     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6200,       "NVIDIA GeForce 6200",              DRIVER_NVIDIA_GEFORCE6,  64  },
1060     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6600GT,     "NVIDIA GeForce 6600 GT",           DRIVER_NVIDIA_GEFORCE6,  128 },
1061     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_6800,       "NVIDIA GeForce 6800",              DRIVER_NVIDIA_GEFORCE6,  128 },
1062     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7300,       "NVIDIA GeForce Go 7300",           DRIVER_NVIDIA_GEFORCE6,  256 },
1063     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7400,       "NVIDIA GeForce Go 7400",           DRIVER_NVIDIA_GEFORCE6,  256 },
1064     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7600,       "NVIDIA GeForce 7600 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
1065     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_7800GT,     "NVIDIA GeForce 7800 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
1066     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8300GS,     "NVIDIA GeForce 8300 GS",           DRIVER_NVIDIA_GEFORCE6,  128 },
1067     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8400GS,     "NVIDIA GeForce 8400 GS",           DRIVER_NVIDIA_GEFORCE6,  128 },
1068     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8600GT,     "NVIDIA GeForce 8600 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
1069     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8600MGT,    "NVIDIA GeForce 8600M GT",          DRIVER_NVIDIA_GEFORCE6,  512 },
1070     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8800GTS,    "NVIDIA GeForce 8800 GTS",          DRIVER_NVIDIA_GEFORCE6,  320 },
1071     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_8800GTX,    "NVIDIA GeForce 8800 GTX",          DRIVER_NVIDIA_GEFORCE6,  768 },
1072     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9200,       "NVIDIA GeForce 9200",              DRIVER_NVIDIA_GEFORCE6,  256 },
1073     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9400GT,     "NVIDIA GeForce 9400 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
1074     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9500GT,     "NVIDIA GeForce 9500 GT",           DRIVER_NVIDIA_GEFORCE6,  256 },
1075     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9600GT,     "NVIDIA GeForce 9600 GT",           DRIVER_NVIDIA_GEFORCE6,  384 },
1076     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_9800GT,     "NVIDIA GeForce 9800 GT",           DRIVER_NVIDIA_GEFORCE6,  512 },
1077     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_210,        "NVIDIA GeForce 210",               DRIVER_NVIDIA_GEFORCE6,  512 },
1078     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT220,      "NVIDIA GeForce GT 220",            DRIVER_NVIDIA_GEFORCE6,  512 },
1079     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT240,      "NVIDIA GeForce GT 240",            DRIVER_NVIDIA_GEFORCE6,  512 },
1080     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX260,     "NVIDIA GeForce GTX 260",           DRIVER_NVIDIA_GEFORCE6,  1024},
1081     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX275,     "NVIDIA GeForce GTX 275",           DRIVER_NVIDIA_GEFORCE6,  896 },
1082     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX280,     "NVIDIA GeForce GTX 280",           DRIVER_NVIDIA_GEFORCE6,  1024},
1083     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GT325M,     "NVIDIA GeForce GT 325M",           DRIVER_NVIDIA_GEFORCE6,  1024},
1084     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTS350M,    "NVIDIA GeForce GTS 350M",          DRIVER_NVIDIA_GEFORCE6,  1024},
1085     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX460,     "NVIDIA GeForce GTX 460",           DRIVER_NVIDIA_GEFORCE6,  768 },
1086     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX465,     "NVIDIA GeForce GTX 465",           DRIVER_NVIDIA_GEFORCE6,  1024},
1087     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX470,     "NVIDIA GeForce GTX 470",           DRIVER_NVIDIA_GEFORCE6,  1280},
1088     {HW_VENDOR_NVIDIA,     CARD_NVIDIA_GEFORCE_GTX480,     "NVIDIA GeForce GTX 480",           DRIVER_NVIDIA_GEFORCE6,  1536},
1089     /* ATI cards */
1090     {HW_VENDOR_ATI,        CARD_ATI_RAGE_128PRO,           "ATI Rage Fury",                    DRIVER_ATI_RAGE_128PRO,  16  },
1091     {HW_VENDOR_ATI,        CARD_ATI_RADEON_7200,           "ATI RADEON 7200 SERIES",           DRIVER_ATI_R100,         32  },
1092     {HW_VENDOR_ATI,        CARD_ATI_RADEON_8500,           "ATI RADEON 8500 SERIES",           DRIVER_ATI_R100,         64  },
1093     {HW_VENDOR_ATI,        CARD_ATI_RADEON_9500,           "ATI Radeon 9500",                  DRIVER_ATI_R300,         64  },
1094     {HW_VENDOR_ATI,        CARD_ATI_RADEON_XPRESS_200M,    "ATI RADEON XPRESS 200M Series",    DRIVER_ATI_R300,         64  },
1095     {HW_VENDOR_ATI,        CARD_ATI_RADEON_X700,           "ATI Radeon X700 SE",               DRIVER_ATI_R300,         128 },
1096     {HW_VENDOR_ATI,        CARD_ATI_RADEON_X1600,          "ATI Radeon X1600 Series",          DRIVER_ATI_R300,         128 },
1097     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2350,         "ATI Mobility Radeon HD 2350",      DRIVER_ATI_R600,         256 },
1098     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2600,         "ATI Mobility Radeon HD 2600",      DRIVER_ATI_R600,         256 },
1099     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD2900,         "ATI Radeon HD 2900 XT",            DRIVER_ATI_R600,         512 },
1100     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD3200,         "ATI Radeon HD 3200 Graphics",      DRIVER_ATI_R600,         128 },
1101     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4350,         "ATI Radeon HD 4350",               DRIVER_ATI_R600,         256 },
1102     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4600,         "ATI Radeon HD 4600 Series",        DRIVER_ATI_R600,         512 },
1103     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4700,         "ATI Radeon HD 4700 Series",        DRIVER_ATI_R600,         512 },
1104     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD4800,         "ATI Radeon HD 4800 Series",        DRIVER_ATI_R600,         512 },
1105     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5400,         "ATI Radeon HD 5400 Series",        DRIVER_ATI_R600,         512 },
1106     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5600,         "ATI Radeon HD 5600 Series",        DRIVER_ATI_R600,         512 },
1107     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5700,         "ATI Radeon HD 5700 Series",        DRIVER_ATI_R600,         512 },
1108     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5800,         "ATI Radeon HD 5800 Series",        DRIVER_ATI_R600,         1024},
1109     {HW_VENDOR_ATI,        CARD_ATI_RADEON_HD5900,         "ATI Radeon HD 5900 Series",        DRIVER_ATI_R600,         1024},
1110     /* Intel cards */
1111     {HW_VENDOR_INTEL,      CARD_INTEL_I830G,               "Intel(R) 82830M Graphics Controller",                       DRIVER_INTEL_GMA800,  32 },
1112     {HW_VENDOR_INTEL,      CARD_INTEL_I855G,               "Intel(R) 82852/82855 GM/GME Graphics Controller",           DRIVER_INTEL_GMA800,  32 },
1113     {HW_VENDOR_INTEL,      CARD_INTEL_I865G,               "Intel(R) 82865G Graphics Controller",                       DRIVER_INTEL_GMA800,  32 },
1114     {HW_VENDOR_INTEL,      CARD_INTEL_I915G,               "Intel(R) 82915G/GV/910GL Express Chipset Family",           DRIVER_INTEL_GMA900,  64 },
1115     {HW_VENDOR_INTEL,      CARD_INTEL_I915GM,              "Mobile Intel(R) 915GM/GMS,910GML Express Chipset Family",   DRIVER_INTEL_GMA900,  64 },
1116     {HW_VENDOR_INTEL,      CARD_INTEL_I945GM,              "Mobile Intel(R) 945GM Express Chipset Family",              DRIVER_INTEL_GMA950,  64 },
1117     {HW_VENDOR_INTEL,      CARD_INTEL_X3100,               "Mobile Intel(R) 965 Express Chipset Family",                DRIVER_INTEL_GMA3000, 128}
1118 };
1119
1120 static const struct driver_version_information *get_driver_version_info(enum wined3d_display_driver driver,
1121         enum wined3d_driver_model driver_model)
1122 {
1123     unsigned int i;
1124
1125     TRACE("Looking up version info for driver=%d driver_model=%d\n", driver, driver_model);
1126     for (i = 0; i < (sizeof(driver_version_table) / sizeof(driver_version_table[0])); i++)
1127     {
1128         const struct driver_version_information *entry = &driver_version_table[i];
1129
1130         if (entry->driver == driver && entry->driver_model == driver_model)
1131         {
1132             TRACE_(d3d_caps)("Found driver '%s' version=%d subversion=%d build=%d\n",
1133                 entry->driver_name, entry->version, entry->subversion, entry->build);
1134
1135             return entry;
1136         }
1137     }
1138     return NULL;
1139 }
1140
1141 static void init_driver_info(struct wined3d_driver_info *driver_info,
1142         enum wined3d_pci_vendor vendor, enum wined3d_pci_device device)
1143 {
1144     OSVERSIONINFOW os_version;
1145     WORD driver_os_version;
1146     unsigned int i;
1147     enum wined3d_display_driver driver = DRIVER_UNKNOWN;
1148     enum wined3d_driver_model driver_model;
1149     const struct driver_version_information *version_info;
1150
1151     if (wined3d_settings.pci_vendor_id != PCI_VENDOR_NONE)
1152     {
1153         TRACE_(d3d_caps)("Overriding PCI vendor ID with: %04x\n", wined3d_settings.pci_vendor_id);
1154         vendor = wined3d_settings.pci_vendor_id;
1155     }
1156     driver_info->vendor = vendor;
1157
1158     if (wined3d_settings.pci_device_id != PCI_DEVICE_NONE)
1159     {
1160         TRACE_(d3d_caps)("Overriding PCI device ID with: %04x\n", wined3d_settings.pci_device_id);
1161         device = wined3d_settings.pci_device_id;
1162     }
1163     driver_info->device = device;
1164
1165     /* Set a default amount of video memory (64MB). In general this code isn't used unless the user
1166      * overrides the pci ids to a card which is not in our database. */
1167     driver_info->vidmem = WINE_DEFAULT_VIDMEM;
1168
1169     memset(&os_version, 0, sizeof(os_version));
1170     os_version.dwOSVersionInfoSize = sizeof(os_version);
1171     if (!GetVersionExW(&os_version))
1172     {
1173         ERR("Failed to get OS version, reporting 2000/XP.\n");
1174         driver_os_version = 6;
1175         driver_model = DRIVER_MODEL_NT5X;
1176     }
1177     else
1178     {
1179         TRACE("OS version %u.%u.\n", os_version.dwMajorVersion, os_version.dwMinorVersion);
1180         switch (os_version.dwMajorVersion)
1181         {
1182             case 4:
1183                 /* If needed we could distinguish between 9x and NT4, but this code won't make
1184                  * sense for NT4 since it had no way to obtain this info through DirectDraw 3.0.
1185                  */
1186                 driver_os_version = 4;
1187                 driver_model = DRIVER_MODEL_WIN9X;
1188                 break;
1189
1190             case 5:
1191                 driver_os_version = 6;
1192                 driver_model = DRIVER_MODEL_NT5X;
1193                 break;
1194
1195             case 6:
1196                 if (os_version.dwMinorVersion == 0)
1197                 {
1198                     driver_os_version = 7;
1199                     driver_model = DRIVER_MODEL_NT6X;
1200                 }
1201                 else
1202                 {
1203                     if (os_version.dwMinorVersion > 1)
1204                     {
1205                         FIXME("Unhandled OS version %u.%u, reporting Win 7.\n",
1206                                 os_version.dwMajorVersion, os_version.dwMinorVersion);
1207                     }
1208                     driver_os_version = 8;
1209                     driver_model = DRIVER_MODEL_NT6X;
1210                 }
1211                 break;
1212
1213             default:
1214                 FIXME("Unhandled OS version %u.%u, reporting 2000/XP.\n",
1215                         os_version.dwMajorVersion, os_version.dwMinorVersion);
1216                 driver_os_version = 6;
1217                 driver_model = DRIVER_MODEL_NT5X;
1218                 break;
1219         }
1220     }
1221
1222     /* When we reach this stage we always have a vendor or device id (it can be a default one).
1223      * This means that unless the ids are overriden, we will always find a GPU description. */
1224     for (i = 0; i < (sizeof(gpu_description_table) / sizeof(gpu_description_table[0])); i++)
1225     {
1226         if (vendor == gpu_description_table[i].vendor && device == gpu_description_table[i].card)
1227         {
1228             TRACE_(d3d_caps)("Found card %04x:%04x in driver DB.\n", vendor, device);
1229
1230             driver_info->description = gpu_description_table[i].description;
1231             driver_info->vidmem = gpu_description_table[i].vidmem * 1024*1024;
1232             driver = gpu_description_table[i].driver;
1233             break;
1234         }
1235     }
1236
1237     if (wined3d_settings.emulated_textureram)
1238     {
1239         TRACE_(d3d_caps)("Overriding amount of video memory with: %d byte\n", wined3d_settings.emulated_textureram);
1240         driver_info->vidmem = wined3d_settings.emulated_textureram;
1241     }
1242
1243     /* Try to obtain driver version information for the current Windows version. This fails in
1244      * some cases:
1245      * - the gpu is not available on the currently selected OS version:
1246      *   - Geforce GTX480 on Win98. When running applications in compatibility mode on Windows,
1247      *     version information for the current Windows version is returned instead of faked info.
1248      *     We do the same and assume the default Windows version to emulate is WinXP.
1249      *
1250      *   - Videocard is a Riva TNT but winver is set to win7 (there are no drivers for this beast)
1251      *     For now return the XP driver info. Perhaps later on we should return VESA.
1252      *
1253      * - the gpu is not in our database (can happen when the user overrides the vendor_id / device_id)
1254      *   This could be an indication that our database is not up to date, so this should be fixed.
1255      */
1256     version_info = get_driver_version_info(driver, driver_model);
1257     if (version_info)
1258     {
1259         driver_info->name = version_info->driver_name;
1260         driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, version_info->version);
1261         driver_info->version_low = MAKEDWORD_VERSION(version_info->subversion, version_info->build);
1262     }
1263     else
1264     {
1265         version_info = get_driver_version_info(driver, DRIVER_MODEL_NT5X);
1266         if (version_info)
1267         {
1268             driver_info->name = version_info->driver_name;
1269             driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, version_info->version);
1270             driver_info->version_low = MAKEDWORD_VERSION(version_info->subversion, version_info->build);
1271         }
1272         else
1273         {
1274             driver_info->description = "Direct3D HAL";
1275             driver_info->name = "Display";
1276             driver_info->version_high = MAKEDWORD_VERSION(driver_os_version, 15);
1277             driver_info->version_low = MAKEDWORD_VERSION(8, 6); /* Nvidia RIVA TNT, arbitrary */
1278
1279             FIXME("Unable to find a driver/device info for vendor_id=%#x device_id=%#x for driver_model=%d\n",
1280                     vendor, device, driver_model);
1281         }
1282     }
1283
1284     TRACE_(d3d_caps)("Reporting (fake) driver version 0x%08x-0x%08x.\n",
1285             driver_info->version_high, driver_info->version_low);
1286 }
1287
1288 /* Context activation is done by the caller. */
1289 static void fixup_extensions(struct wined3d_gl_info *gl_info, const char *gl_renderer,
1290         enum wined3d_gl_vendor gl_vendor, enum wined3d_pci_vendor card_vendor, enum wined3d_pci_device device)
1291 {
1292     unsigned int i;
1293
1294     for (i = 0; i < (sizeof(quirk_table) / sizeof(*quirk_table)); ++i)
1295     {
1296         if (!quirk_table[i].match(gl_info, gl_renderer, gl_vendor, card_vendor, device)) continue;
1297         TRACE_(d3d_caps)("Applying driver quirk \"%s\".\n", quirk_table[i].description);
1298         quirk_table[i].apply(gl_info);
1299     }
1300
1301     /* Find out if PBOs work as they are supposed to. */
1302     test_pbo_functionality(gl_info);
1303 }
1304
1305 static DWORD wined3d_parse_gl_version(const char *gl_version)
1306 {
1307     const char *ptr = gl_version;
1308     int major, minor;
1309
1310     major = atoi(ptr);
1311     if (major <= 0) ERR_(d3d_caps)("Invalid opengl major version: %d.\n", major);
1312
1313     while (isdigit(*ptr)) ++ptr;
1314     if (*ptr++ != '.') ERR_(d3d_caps)("Invalid opengl version string: %s.\n", debugstr_a(gl_version));
1315
1316     minor = atoi(ptr);
1317
1318     TRACE_(d3d_caps)("Found OpenGL version: %d.%d.\n", major, minor);
1319
1320     return MAKEDWORD_VERSION(major, minor);
1321 }
1322
1323 static enum wined3d_gl_vendor wined3d_guess_gl_vendor(struct wined3d_gl_info *gl_info, const char *gl_vendor_string, const char *gl_renderer)
1324 {
1325
1326     /* MacOS has various specialities in the extensions it advertises. Some have to be loaded from
1327      * the opengl 1.2+ core, while other extensions are advertised, but software emulated. So try to
1328      * detect the Apple OpenGL implementation to apply some extension fixups afterwards.
1329      *
1330      * Detecting this isn't really easy. The vendor string doesn't mention Apple. Compile-time checks
1331      * aren't sufficient either because a Linux binary may display on a macos X server via remote X11.
1332      * So try to detect the GL implementation by looking at certain Apple extensions. Some extensions
1333      * like client storage might be supported on other implementations too, but GL_APPLE_flush_render
1334      * is specific to the Mac OS X window management, and GL_APPLE_ycbcr_422 is QuickTime specific. So
1335      * the chance that other implementations support them is rather small since Win32 QuickTime uses
1336      * DirectDraw, not OpenGL. */
1337     if (gl_info->supported[APPLE_FENCE]
1338             && gl_info->supported[APPLE_CLIENT_STORAGE]
1339             && gl_info->supported[APPLE_FLUSH_RENDER]
1340             && gl_info->supported[APPLE_YCBCR_422])
1341         return GL_VENDOR_APPLE;
1342
1343     if (strstr(gl_vendor_string, "NVIDIA"))
1344         return GL_VENDOR_NVIDIA;
1345
1346     if (strstr(gl_vendor_string, "ATI"))
1347         return GL_VENDOR_FGLRX;
1348
1349     if (strstr(gl_vendor_string, "Intel(R)")
1350             /* Intel switched from Intel(R) to Intel® recently, so just match Intel. */
1351             || strstr(gl_renderer, "Intel")
1352             || strstr(gl_vendor_string, "Intel Inc."))
1353         return GL_VENDOR_INTEL;
1354
1355     if (strstr(gl_vendor_string, "Mesa")
1356             || strstr(gl_vendor_string, "Advanced Micro Devices, Inc.")
1357             || strstr(gl_vendor_string, "DRI R300 Project")
1358             || strstr(gl_vendor_string, "X.Org R300 Project")
1359             || strstr(gl_vendor_string, "Tungsten Graphics, Inc")
1360             || strstr(gl_vendor_string, "VMware, Inc.")
1361             || strstr(gl_renderer, "Mesa")
1362             || strstr(gl_renderer, "Gallium"))
1363         return GL_VENDOR_MESA;
1364
1365     FIXME_(d3d_caps)("Received unrecognized GL_VENDOR %s. Returning GL_VENDOR_UNKNOWN.\n",
1366             debugstr_a(gl_vendor_string));
1367
1368     return GL_VENDOR_UNKNOWN;
1369 }
1370
1371 static enum wined3d_pci_vendor wined3d_guess_card_vendor(const char *gl_vendor_string, const char *gl_renderer)
1372 {
1373     if (strstr(gl_vendor_string, "NVIDIA"))
1374         return HW_VENDOR_NVIDIA;
1375
1376     if (strstr(gl_vendor_string, "ATI")
1377             || strstr(gl_vendor_string, "Advanced Micro Devices, Inc.")
1378             || strstr(gl_vendor_string, "X.Org R300 Project")
1379             || strstr(gl_renderer, "AMD")
1380             || strstr(gl_renderer, "R100")
1381             || strstr(gl_renderer, "R200")
1382             || strstr(gl_renderer, "R300")
1383             || strstr(gl_renderer, "R600")
1384             || strstr(gl_renderer, "R700"))
1385         return HW_VENDOR_ATI;
1386
1387     if (strstr(gl_vendor_string, "Intel(R)")
1388             /* Intel switched from Intel(R) to Intel® recently, so just match Intel. */
1389             || strstr(gl_renderer, "Intel")
1390             || strstr(gl_vendor_string, "Intel Inc."))
1391         return HW_VENDOR_INTEL;
1392
1393     if (strstr(gl_vendor_string, "Mesa")
1394             || strstr(gl_vendor_string, "Tungsten Graphics, Inc")
1395             || strstr(gl_vendor_string, "VMware, Inc."))
1396         return HW_VENDOR_SOFTWARE;
1397
1398     FIXME_(d3d_caps)("Received unrecognized GL_VENDOR %s. Returning HW_VENDOR_NVIDIA.\n", debugstr_a(gl_vendor_string));
1399
1400     return HW_VENDOR_NVIDIA;
1401 }
1402
1403
1404
1405 static enum wined3d_pci_device select_card_nvidia_binary(const struct wined3d_gl_info *gl_info,
1406         const char *gl_renderer)
1407 {
1408     if (WINE_D3D10_CAPABLE(gl_info))
1409     {
1410         /* Geforce 400 - highend */
1411         if (strstr(gl_renderer, "GTX 480"))
1412         {
1413             return CARD_NVIDIA_GEFORCE_GTX480;
1414         }
1415
1416         /* Geforce 400 - midend high */
1417         if (strstr(gl_renderer, "GTX 470"))
1418         {
1419             return CARD_NVIDIA_GEFORCE_GTX470;
1420         }
1421
1422         /* Geforce 400 - midend */
1423         if (strstr(gl_renderer, "GTX 465"))
1424         {
1425             return CARD_NVIDIA_GEFORCE_GTX465;
1426         }
1427
1428         /* Geforce 400 - midend */
1429         if (strstr(gl_renderer, "GTX 460"))
1430         {
1431             return CARD_NVIDIA_GEFORCE_GTX460;
1432         }
1433
1434         /* Geforce 300 highend mobile */
1435         if (strstr(gl_renderer, "GTS 350M")
1436                 || strstr(gl_renderer, "GTS 360M"))
1437         {
1438             return CARD_NVIDIA_GEFORCE_GTS350M;
1439         }
1440
1441         /* Geforce 300 midend mobile (Geforce GT 325M/330M use the same core) */
1442         if (strstr(gl_renderer, "GT 325M")
1443                 || strstr(gl_renderer, "GT 330M"))
1444         {
1445             return CARD_NVIDIA_GEFORCE_GT325M;
1446         }
1447
1448         /* Geforce 200 - highend */
1449         if (strstr(gl_renderer, "GTX 280")
1450                 || strstr(gl_renderer, "GTX 285")
1451                 || strstr(gl_renderer, "GTX 295"))
1452         {
1453             return CARD_NVIDIA_GEFORCE_GTX280;
1454         }
1455
1456         /* Geforce 200 - midend high */
1457         if (strstr(gl_renderer, "GTX 275"))
1458         {
1459             return CARD_NVIDIA_GEFORCE_GTX275;
1460         }
1461
1462         /* Geforce 200 - midend */
1463         if (strstr(gl_renderer, "GTX 260"))
1464         {
1465             return CARD_NVIDIA_GEFORCE_GTX260;
1466         }
1467         /* Geforce 200 - midend */
1468         if (strstr(gl_renderer, "GT 240"))
1469         {
1470            return CARD_NVIDIA_GEFORCE_GT240;
1471         }
1472
1473         /* Geforce 200 lowend */
1474         if (strstr(gl_renderer, "GT 220"))
1475         {
1476            return CARD_NVIDIA_GEFORCE_GT220;
1477         }
1478         /* Geforce 200 lowend (Geforce 305/310 use the same core) */
1479         if (strstr(gl_renderer, "Geforce 210")
1480                 || strstr(gl_renderer, "G 210")
1481                 || strstr(gl_renderer, "Geforce 305")
1482                 || strstr(gl_renderer, "Geforce 310"))
1483         {
1484            return CARD_NVIDIA_GEFORCE_210;
1485         }
1486
1487         /* Geforce9 - highend / Geforce 200 - midend (GTS 150/250 are based on the same core) */
1488         if (strstr(gl_renderer, "9800")
1489                 || strstr(gl_renderer, "GTS 150")
1490                 || strstr(gl_renderer, "GTS 250"))
1491         {
1492             return CARD_NVIDIA_GEFORCE_9800GT;
1493         }
1494
1495         /* Geforce9 - midend (GT 140 uses the same core as the 9600GT) */
1496         if (strstr(gl_renderer, "9600")
1497                 || strstr(gl_renderer, "GT 140"))
1498         {
1499             return CARD_NVIDIA_GEFORCE_9600GT;
1500         }
1501
1502         /* Geforce9 - midend low / Geforce 200 - low */
1503         if (strstr(gl_renderer, "9500")
1504                 || strstr(gl_renderer, "GT 120")
1505                 || strstr(gl_renderer, "GT 130"))
1506         {
1507             return CARD_NVIDIA_GEFORCE_9500GT;
1508         }
1509
1510         /* Geforce9 - lowend */
1511         if (strstr(gl_renderer, "9400"))
1512         {
1513             return CARD_NVIDIA_GEFORCE_9400GT;
1514         }
1515
1516         /* Geforce9 - lowend low */
1517         if (strstr(gl_renderer, "9100")
1518                 || strstr(gl_renderer, "9200")
1519                 || strstr(gl_renderer, "9300")
1520                 || strstr(gl_renderer, "G 100"))
1521         {
1522             return CARD_NVIDIA_GEFORCE_9200;
1523         }
1524
1525         /* Geforce8 - highend high*/
1526         if (strstr(gl_renderer, "8800 GTX"))
1527         {
1528             return CARD_NVIDIA_GEFORCE_8800GTX;
1529         }
1530
1531         /* Geforce8 - highend */
1532         if (strstr(gl_renderer, "8800"))
1533         {
1534             return CARD_NVIDIA_GEFORCE_8800GTS;
1535         }
1536
1537         /* Geforce8 - midend mobile */
1538         if (strstr(gl_renderer, "8600 M"))
1539         {
1540             return CARD_NVIDIA_GEFORCE_8600MGT;
1541         }
1542
1543         /* Geforce8 - midend */
1544         if (strstr(gl_renderer, "8600")
1545                 || strstr(gl_renderer, "8700"))
1546         {
1547             return CARD_NVIDIA_GEFORCE_8600GT;
1548         }
1549
1550         /* Geforce8 - mid-lowend */
1551         if (strstr(gl_renderer, "8400")
1552                 || strstr(gl_renderer, "8500"))
1553         {
1554             return CARD_NVIDIA_GEFORCE_8400GS;
1555         }
1556
1557         /* Geforce8 - lowend */
1558         if (strstr(gl_renderer, "8100")
1559                 || strstr(gl_renderer, "8200")
1560                 || strstr(gl_renderer, "8300"))
1561         {
1562             return CARD_NVIDIA_GEFORCE_8300GS;
1563         }
1564
1565         /* Geforce8-compatible fall back if the GPU is not in the list yet */
1566         return CARD_NVIDIA_GEFORCE_8300GS;
1567     }
1568
1569     /* Both the GeforceFX, 6xxx and 7xxx series support D3D9. The last two types have more
1570      * shader capabilities, so we use the shader capabilities to distinguish between FX and 6xxx/7xxx.
1571      */
1572     if (WINE_D3D9_CAPABLE(gl_info) && gl_info->supported[NV_VERTEX_PROGRAM3])
1573     {
1574         /* Geforce7 - highend */
1575         if (strstr(gl_renderer, "7800")
1576                 || strstr(gl_renderer, "7900")
1577                 || strstr(gl_renderer, "7950")
1578                 || strstr(gl_renderer, "Quadro FX 4")
1579                 || strstr(gl_renderer, "Quadro FX 5"))
1580         {
1581             return CARD_NVIDIA_GEFORCE_7800GT;
1582         }
1583
1584         /* Geforce7 midend */
1585         if (strstr(gl_renderer, "7600")
1586                 || strstr(gl_renderer, "7700"))
1587         {
1588             return CARD_NVIDIA_GEFORCE_7600;
1589         }
1590
1591         /* Geforce7 lower medium */
1592         if (strstr(gl_renderer, "7400"))
1593         {
1594             return CARD_NVIDIA_GEFORCE_7400;
1595         }
1596
1597         /* Geforce7 lowend */
1598         if (strstr(gl_renderer, "7300"))
1599         {
1600             return CARD_NVIDIA_GEFORCE_7300;
1601         }
1602
1603         /* Geforce6 highend */
1604         if (strstr(gl_renderer, "6800"))
1605         {
1606             return CARD_NVIDIA_GEFORCE_6800;
1607         }
1608
1609         /* Geforce6 - midend */
1610         if (strstr(gl_renderer, "6600")
1611                 || strstr(gl_renderer, "6610")
1612                 || strstr(gl_renderer, "6700"))
1613         {
1614             return CARD_NVIDIA_GEFORCE_6600GT;
1615         }
1616
1617         /* Geforce6/7 lowend */
1618         return CARD_NVIDIA_GEFORCE_6200; /* Geforce 6100/6150/6200/7300/7400/7500 */
1619     }
1620
1621     if (WINE_D3D9_CAPABLE(gl_info))
1622     {
1623         /* GeforceFX - highend */
1624         if (strstr(gl_renderer, "5800")
1625                 || strstr(gl_renderer, "5900")
1626                 || strstr(gl_renderer, "5950")
1627                 || strstr(gl_renderer, "Quadro FX"))
1628         {
1629             return CARD_NVIDIA_GEFORCEFX_5800;
1630         }
1631
1632         /* GeforceFX - midend */
1633         if (strstr(gl_renderer, "5600")
1634                 || strstr(gl_renderer, "5650")
1635                 || strstr(gl_renderer, "5700")
1636                 || strstr(gl_renderer, "5750"))
1637         {
1638             return CARD_NVIDIA_GEFORCEFX_5600;
1639         }
1640
1641         /* GeforceFX - lowend */
1642         return CARD_NVIDIA_GEFORCEFX_5200; /* GeforceFX 5100/5200/5250/5300/5500 */
1643     }
1644
1645     if (WINE_D3D8_CAPABLE(gl_info))
1646     {
1647         if (strstr(gl_renderer, "GeForce4 Ti") || strstr(gl_renderer, "Quadro4"))
1648         {
1649             return CARD_NVIDIA_GEFORCE4_TI4200; /* Geforce4 Ti4200/Ti4400/Ti4600/Ti4800, Quadro4 */
1650         }
1651
1652         return CARD_NVIDIA_GEFORCE3; /* Geforce3 standard/Ti200/Ti500, Quadro DCC */
1653     }
1654
1655     if (WINE_D3D7_CAPABLE(gl_info))
1656     {
1657         if (strstr(gl_renderer, "GeForce4 MX"))
1658         {
1659             return CARD_NVIDIA_GEFORCE4_MX; /* MX420/MX440/MX460/MX4000 */
1660         }
1661
1662         if (strstr(gl_renderer, "GeForce2 MX") || strstr(gl_renderer, "Quadro2 MXR"))
1663         {
1664             return CARD_NVIDIA_GEFORCE2_MX; /* Geforce2 standard/MX100/MX200/MX400, Quadro2 MXR */
1665         }
1666
1667         if (strstr(gl_renderer, "GeForce2") || strstr(gl_renderer, "Quadro2"))
1668         {
1669             return CARD_NVIDIA_GEFORCE2; /* Geforce2 GTS/Pro/Ti/Ultra, Quadro2 */
1670         }
1671
1672         return CARD_NVIDIA_GEFORCE; /* Geforce 256/DDR, Quadro */
1673     }
1674
1675     if (strstr(gl_renderer, "TNT2"))
1676     {
1677         return CARD_NVIDIA_RIVA_TNT2; /* Riva TNT2 standard/M64/Pro/Ultra */
1678     }
1679
1680     return CARD_NVIDIA_RIVA_TNT; /* Riva TNT, Vanta */
1681 }
1682
1683 static enum wined3d_pci_device select_card_ati_binary(const struct wined3d_gl_info *gl_info,
1684         const char *gl_renderer)
1685 {
1686     /* See http://developer.amd.com/drivers/pc_vendor_id/Pages/default.aspx
1687      *
1688      * Beware: renderer string do not match exact card model,
1689      * eg HD 4800 is returned for multiple cards, even for RV790 based ones. */
1690     if (WINE_D3D10_CAPABLE(gl_info))
1691     {
1692         /* Radeon EG CYPRESS XT / PRO HD5800 - highend */
1693         if (strstr(gl_renderer, "HD 5800")          /* Radeon EG CYPRESS HD58xx generic renderer string */
1694                 || strstr(gl_renderer, "HD 5850")   /* Radeon EG CYPRESS XT */
1695                 || strstr(gl_renderer, "HD 5870"))  /* Radeon EG CYPRESS PRO */
1696         {
1697             return CARD_ATI_RADEON_HD5800;
1698         }
1699
1700         /* Radeon EG JUNIPER XT / LE HD5700 - midend */
1701         if (strstr(gl_renderer, "HD 5700")          /* Radeon EG JUNIPER HD57xx generic renderer string */
1702                 || strstr(gl_renderer, "HD 5750")   /* Radeon EG JUNIPER LE */
1703                 || strstr(gl_renderer, "HD 5770"))  /* Radeon EG JUNIPER XT */
1704         {
1705             return CARD_ATI_RADEON_HD5700;
1706         }
1707
1708         /* Radeon R7xx HD4800 - highend */
1709         if (strstr(gl_renderer, "HD 4800")          /* Radeon RV7xx HD48xx generic renderer string */
1710                 || strstr(gl_renderer, "HD 4830")   /* Radeon RV770 */
1711                 || strstr(gl_renderer, "HD 4850")   /* Radeon RV770 */
1712                 || strstr(gl_renderer, "HD 4870")   /* Radeon RV770 */
1713                 || strstr(gl_renderer, "HD 4890"))  /* Radeon RV790 */
1714         {
1715             return CARD_ATI_RADEON_HD4800;
1716         }
1717
1718         /* Radeon R740 HD4700 - midend */
1719         if (strstr(gl_renderer, "HD 4700")          /* Radeon RV770 */
1720                 || strstr(gl_renderer, "HD 4770"))  /* Radeon RV740 */
1721         {
1722             return CARD_ATI_RADEON_HD4700;
1723         }
1724
1725         /* Radeon R730 HD4600 - midend */
1726         if (strstr(gl_renderer, "HD 4600")          /* Radeon RV730 */
1727                 || strstr(gl_renderer, "HD 4650")   /* Radeon RV730 */
1728                 || strstr(gl_renderer, "HD 4670"))  /* Radeon RV730 */
1729         {
1730             return CARD_ATI_RADEON_HD4600;
1731         }
1732
1733         /* Radeon R710 HD4500/HD4350 - lowend */
1734         if (strstr(gl_renderer, "HD 4350")          /* Radeon RV710 */
1735                 || strstr(gl_renderer, "HD 4550"))  /* Radeon RV710 */
1736         {
1737             return CARD_ATI_RADEON_HD4350;
1738         }
1739
1740         /* Radeon R6xx HD2900/HD3800 - highend */
1741         if (strstr(gl_renderer, "HD 2900")
1742                 || strstr(gl_renderer, "HD 3870")
1743                 || strstr(gl_renderer, "HD 3850"))
1744         {
1745             return CARD_ATI_RADEON_HD2900;
1746         }
1747
1748         /* Radeon R6xx HD2600/HD3600 - midend; HD3830 is China-only midend */
1749         if (strstr(gl_renderer, "HD 2600")
1750                 || strstr(gl_renderer, "HD 3830")
1751                 || strstr(gl_renderer, "HD 3690")
1752                 || strstr(gl_renderer, "HD 3650"))
1753         {
1754             return CARD_ATI_RADEON_HD2600;
1755         }
1756
1757         /* Radeon R6xx HD2350/HD2400/HD3400 - lowend
1758          * Note HD2300=DX9, HD2350=DX10 */
1759         if (strstr(gl_renderer, "HD 2350")
1760                 || strstr(gl_renderer, "HD 2400")
1761                 || strstr(gl_renderer, "HD 3470")
1762                 || strstr(gl_renderer, "HD 3450")
1763                 || strstr(gl_renderer, "HD 3430")
1764                 || strstr(gl_renderer, "HD 3400"))
1765         {
1766             return CARD_ATI_RADEON_HD2350;
1767         }
1768
1769         /* Radeon R6xx/R7xx integrated */
1770         if (strstr(gl_renderer, "HD 3100")
1771                 || strstr(gl_renderer, "HD 3200")
1772                 || strstr(gl_renderer, "HD 3300"))
1773         {
1774             return CARD_ATI_RADEON_HD3200;
1775         }
1776
1777         /* Default for when no GPU has been found */
1778         return CARD_ATI_RADEON_HD3200;
1779     }
1780
1781     if (WINE_D3D8_CAPABLE(gl_info))
1782     {
1783         /* Radeon R5xx */
1784         if (strstr(gl_renderer, "X1600")
1785                 || strstr(gl_renderer, "X1650")
1786                 || strstr(gl_renderer, "X1800")
1787                 || strstr(gl_renderer, "X1900")
1788                 || strstr(gl_renderer, "X1950"))
1789         {
1790             return CARD_ATI_RADEON_X1600;
1791         }
1792
1793         /* Radeon R4xx + X1300/X1400/X1450/X1550/X2300/X2500/HD2300 (lowend R5xx)
1794          * Note X2300/X2500/HD2300 are R5xx GPUs with a 2xxx naming but they are still DX9-only */
1795         if (strstr(gl_renderer, "X700")
1796                 || strstr(gl_renderer, "X800")
1797                 || strstr(gl_renderer, "X850")
1798                 || strstr(gl_renderer, "X1300")
1799                 || strstr(gl_renderer, "X1400")
1800                 || strstr(gl_renderer, "X1450")
1801                 || strstr(gl_renderer, "X1550")
1802                 || strstr(gl_renderer, "X2300")
1803                 || strstr(gl_renderer, "X2500")
1804                 || strstr(gl_renderer, "HD 2300")
1805                 )
1806         {
1807             return CARD_ATI_RADEON_X700;
1808         }
1809
1810         /* Radeon Xpress Series - onboard, DX9b, Shader 2.0, 300-400MHz */
1811         if (strstr(gl_renderer, "Radeon Xpress"))
1812         {
1813             return CARD_ATI_RADEON_XPRESS_200M;
1814         }
1815
1816         /* Radeon R3xx */
1817         return CARD_ATI_RADEON_9500; /* Radeon 9500/9550/9600/9700/9800/X300/X550/X600 */
1818     }
1819
1820     if (WINE_D3D8_CAPABLE(gl_info))
1821     {
1822         return CARD_ATI_RADEON_8500; /* Radeon 8500/9000/9100/9200/9300 */
1823     }
1824
1825     if (WINE_D3D7_CAPABLE(gl_info))
1826     {
1827         return CARD_ATI_RADEON_7200; /* Radeon 7000/7100/7200/7500 */
1828     }
1829
1830     return CARD_ATI_RAGE_128PRO;
1831 }
1832
1833 static enum wined3d_pci_device select_card_intel(const struct wined3d_gl_info *gl_info,
1834         const char *gl_renderer)
1835 {
1836     if (strstr(gl_renderer, "X3100") || strstr(gl_renderer, "965GM"))
1837     {
1838         /* MacOS calls the card GMA X3100, otherwise known as GM965/GL960 */
1839         return CARD_INTEL_X3100;
1840     }
1841
1842     if (strstr(gl_renderer, "GMA 950") || strstr(gl_renderer, "945GM"))
1843     {
1844         /* MacOS calls the card GMA 950, but everywhere else the PCI ID is named 945GM */
1845         return CARD_INTEL_I945GM;
1846     }
1847
1848     if (strstr(gl_renderer, "915GM")) return CARD_INTEL_I915GM;
1849     if (strstr(gl_renderer, "915G")) return CARD_INTEL_I915G;
1850     if (strstr(gl_renderer, "865G")) return CARD_INTEL_I865G;
1851     if (strstr(gl_renderer, "855G")) return CARD_INTEL_I855G;
1852     if (strstr(gl_renderer, "830G")) return CARD_INTEL_I830G;
1853     return CARD_INTEL_I915G;
1854
1855 }
1856
1857 static enum wined3d_pci_device select_card_ati_mesa(const struct wined3d_gl_info *gl_info,
1858         const char *gl_renderer)
1859 {
1860     /* See http://developer.amd.com/drivers/pc_vendor_id/Pages/default.aspx
1861      *
1862      * Beware: renderer string do not match exact card model,
1863      * eg HD 4800 is returned for multiple cards, even for RV790 based ones. */
1864     if (strstr(gl_renderer, "Gallium"))
1865     {
1866         if (strstr(gl_renderer, "HEMLOCK"))
1867             return CARD_ATI_RADEON_HD5900;
1868         if (strstr(gl_renderer, "CYPRESS"))
1869             return CARD_ATI_RADEON_HD5800;
1870         if (strstr(gl_renderer, "JUNIPER"))
1871             return CARD_ATI_RADEON_HD5700;
1872         if (strstr(gl_renderer, "REDWOOD"))
1873             return CARD_ATI_RADEON_HD5600;
1874         if (strstr(gl_renderer, "CEDAR"))
1875             return CARD_ATI_RADEON_HD5400;
1876
1877         /* Radeon R7xx HD4800 - highend */
1878         if (strstr(gl_renderer, "R700")          /* Radeon R7xx HD48xx generic renderer string */
1879                 || strstr(gl_renderer, "RV770")  /* Radeon RV770 */
1880                 || strstr(gl_renderer, "RV790"))  /* Radeon RV790 */
1881         {
1882             return CARD_ATI_RADEON_HD4800;
1883         }
1884
1885         /* Radeon R740 HD4700 - midend */
1886         if (strstr(gl_renderer, "RV740"))          /* Radeon RV740 */
1887         {
1888             return CARD_ATI_RADEON_HD4700;
1889         }
1890
1891         /* Radeon R730 HD4600 - midend */
1892         if (strstr(gl_renderer, "RV730"))        /* Radeon RV730 */
1893         {
1894             return CARD_ATI_RADEON_HD4600;
1895         }
1896
1897         /* Radeon R710 HD4500/HD4350 - lowend */
1898         if (strstr(gl_renderer, "RV710"))          /* Radeon RV710 */
1899         {
1900             return CARD_ATI_RADEON_HD4350;
1901         }
1902
1903         /* Radeon R6xx HD2900/HD3800 - highend */
1904         if (strstr(gl_renderer, "R600")
1905                 || strstr(gl_renderer, "RV670")
1906                 || strstr(gl_renderer, "R680"))
1907         {
1908             return CARD_ATI_RADEON_HD2900;
1909         }
1910
1911         /* Radeon R6xx HD2600/HD3600 - midend; HD3830 is China-only midend */
1912         if (strstr(gl_renderer, "RV630")
1913                 || strstr(gl_renderer, "RV635"))
1914         {
1915             return CARD_ATI_RADEON_HD2600;
1916         }
1917
1918         /* Radeon R6xx HD2350/HD2400/HD3400 - lowend */
1919         if (strstr(gl_renderer, "RV610")
1920                 || strstr(gl_renderer, "RV620"))
1921         {
1922             return CARD_ATI_RADEON_HD2350;
1923         }
1924
1925         /* Radeon R6xx/R7xx integrated */
1926         if (strstr(gl_renderer, "RS780")
1927                 || strstr(gl_renderer, "RS880"))
1928         {
1929             return CARD_ATI_RADEON_HD3200;
1930         }
1931
1932         /* Radeon R5xx */
1933         if (strstr(gl_renderer, "RV530")
1934                 || strstr(gl_renderer, "RV535")
1935                 || strstr(gl_renderer, "RV560")
1936                 || strstr(gl_renderer, "R520")
1937                 || strstr(gl_renderer, "RV570")
1938                 || strstr(gl_renderer, "R580"))
1939         {
1940             return CARD_ATI_RADEON_X1600;
1941         }
1942
1943         /* Radeon R4xx + X1300/X1400/X1450/X1550/X2300 (lowend R5xx) */
1944         if (strstr(gl_renderer, "R410")
1945                 || strstr(gl_renderer, "R420")
1946                 || strstr(gl_renderer, "R423")
1947                 || strstr(gl_renderer, "R430")
1948                 || strstr(gl_renderer, "R480")
1949                 || strstr(gl_renderer, "R481")
1950                 || strstr(gl_renderer, "RV410")
1951                 || strstr(gl_renderer, "RV515")
1952                 || strstr(gl_renderer, "RV516"))
1953         {
1954             return CARD_ATI_RADEON_X700;
1955         }
1956
1957         /* Radeon Xpress Series - onboard, DX9b, Shader 2.0, 300-400MHz */
1958         if (strstr(gl_renderer, "RS400")
1959                 || strstr(gl_renderer, "RS480")
1960                 || strstr(gl_renderer, "RS482")
1961                 || strstr(gl_renderer, "RS485")
1962                 || strstr(gl_renderer, "RS600")
1963                 || strstr(gl_renderer, "RS690")
1964                 || strstr(gl_renderer, "RS740"))
1965         {
1966             return CARD_ATI_RADEON_XPRESS_200M;
1967         }
1968
1969         /* Radeon R3xx */
1970         if (strstr(gl_renderer, "R300")
1971                 || strstr(gl_renderer, "RV350")
1972                 || strstr(gl_renderer, "RV351")
1973                 || strstr(gl_renderer, "RV360")
1974                 || strstr(gl_renderer, "RV370")
1975                 || strstr(gl_renderer, "R350")
1976                 || strstr(gl_renderer, "R360"))
1977         {
1978             return CARD_ATI_RADEON_9500; /* Radeon 9500/9550/9600/9700/9800/X300/X550/X600 */
1979         }
1980     }
1981
1982     if (WINE_D3D9_CAPABLE(gl_info))
1983     {
1984         /* Radeon R7xx HD4800 - highend */
1985         if (strstr(gl_renderer, "(R700")          /* Radeon R7xx HD48xx generic renderer string */
1986                 || strstr(gl_renderer, "(RV770")  /* Radeon RV770 */
1987                 || strstr(gl_renderer, "(RV790"))  /* Radeon RV790 */
1988         {
1989             return CARD_ATI_RADEON_HD4800;
1990         }
1991
1992         /* Radeon R740 HD4700 - midend */
1993         if (strstr(gl_renderer, "(RV740"))          /* Radeon RV740 */
1994         {
1995             return CARD_ATI_RADEON_HD4700;
1996         }
1997
1998         /* Radeon R730 HD4600 - midend */
1999         if (strstr(gl_renderer, "(RV730"))        /* Radeon RV730 */
2000         {
2001             return CARD_ATI_RADEON_HD4600;
2002         }
2003
2004         /* Radeon R710 HD4500/HD4350 - lowend */
2005         if (strstr(gl_renderer, "(RV710"))          /* Radeon RV710 */
2006         {
2007             return CARD_ATI_RADEON_HD4350;
2008         }
2009
2010         /* Radeon R6xx HD2900/HD3800 - highend */
2011         if (strstr(gl_renderer, "(R600")
2012                 || strstr(gl_renderer, "(RV670")
2013                 || strstr(gl_renderer, "(R680"))
2014         {
2015             return CARD_ATI_RADEON_HD2900;
2016         }
2017
2018         /* Radeon R6xx HD2600/HD3600 - midend; HD3830 is China-only midend */
2019         if (strstr(gl_renderer, "(RV630")
2020                 || strstr(gl_renderer, "(RV635"))
2021         {
2022             return CARD_ATI_RADEON_HD2600;
2023         }
2024
2025         /* Radeon R6xx HD2300/HD2400/HD3400 - lowend */
2026         if (strstr(gl_renderer, "(RV610")
2027                 || strstr(gl_renderer, "(RV620"))
2028         {
2029             return CARD_ATI_RADEON_HD2350;
2030         }
2031
2032         /* Radeon R6xx/R7xx integrated */
2033         if (strstr(gl_renderer, "(RS780")
2034                 || strstr(gl_renderer, "(RS880"))
2035         {
2036             return CARD_ATI_RADEON_HD3200;
2037         }
2038     }
2039
2040     if (WINE_D3D8_CAPABLE(gl_info))
2041     {
2042         return CARD_ATI_RADEON_8500; /* Radeon 8500/9000/9100/9200/9300 */
2043     }
2044
2045     if (WINE_D3D7_CAPABLE(gl_info))
2046     {
2047         return CARD_ATI_RADEON_7200; /* Radeon 7000/7100/7200/7500 */
2048     }
2049
2050     return CARD_ATI_RAGE_128PRO;
2051 }
2052
2053 static enum wined3d_pci_device select_card_nvidia_mesa(const struct wined3d_gl_info *gl_info,
2054         const char *gl_renderer)
2055 {
2056     FIXME_(d3d_caps)("Card selection not handled for Mesa Nouveau driver\n");
2057     if (WINE_D3D9_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCEFX_5600;
2058     if (WINE_D3D8_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCE3;
2059     if (WINE_D3D7_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCE;
2060     if (WINE_D3D6_CAPABLE(gl_info)) return CARD_NVIDIA_RIVA_TNT;
2061     return CARD_NVIDIA_RIVA_128;
2062 }
2063
2064
2065 struct vendor_card_selection
2066 {
2067     enum wined3d_gl_vendor gl_vendor;
2068     enum wined3d_pci_vendor card_vendor;
2069     const char *description;        /* Description of the card selector i.e. Apple OS/X Intel */
2070     enum wined3d_pci_device (*select_card)(const struct wined3d_gl_info *gl_info, const char *gl_renderer);
2071 };
2072
2073 static const struct vendor_card_selection vendor_card_select_table[] =
2074 {
2075     {GL_VENDOR_NVIDIA, HW_VENDOR_NVIDIA,  "Nvidia binary driver",     select_card_nvidia_binary},
2076     {GL_VENDOR_APPLE,  HW_VENDOR_NVIDIA,  "Apple OSX NVidia binary driver",   select_card_nvidia_binary},
2077     {GL_VENDOR_APPLE,  HW_VENDOR_ATI,     "Apple OSX AMD/ATI binary driver",  select_card_ati_binary},
2078     {GL_VENDOR_APPLE,  HW_VENDOR_INTEL,   "Apple OSX Intel binary driver",    select_card_intel},
2079     {GL_VENDOR_FGLRX,  HW_VENDOR_ATI,     "AMD/ATI binary driver",    select_card_ati_binary},
2080     {GL_VENDOR_MESA,   HW_VENDOR_ATI,     "Mesa AMD/ATI driver",      select_card_ati_mesa},
2081     {GL_VENDOR_MESA,   HW_VENDOR_NVIDIA,  "Mesa Nouveau driver",      select_card_nvidia_mesa},
2082     {GL_VENDOR_MESA,   HW_VENDOR_INTEL,   "Mesa Intel driver",        select_card_intel},
2083     {GL_VENDOR_INTEL,  HW_VENDOR_INTEL,   "Mesa Intel driver",        select_card_intel}
2084 };
2085
2086
2087 static enum wined3d_pci_device wined3d_guess_card(const struct wined3d_gl_info *gl_info, const char *gl_renderer,
2088         enum wined3d_gl_vendor *gl_vendor, enum wined3d_pci_vendor *card_vendor)
2089 {
2090     /* Above is a list of Nvidia and ATI GPUs. Both vendors have dozens of
2091      * different GPUs with roughly the same features. In most cases GPUs from a
2092      * certain family differ in clockspeeds, the amount of video memory and the
2093      * number of shader pipelines.
2094      *
2095      * A Direct3D device object contains the PCI id (vendor + device) of the
2096      * videocard which is used for rendering. Various applications use this
2097      * information to get a rough estimation of the features of the card and
2098      * some might use it for enabling 3d effects only on certain types of
2099      * videocards. In some cases games might even use it to work around bugs
2100      * which happen on certain videocards/driver combinations. The problem is
2101      * that OpenGL only exposes a rendering string containing the name of the
2102      * videocard and not the PCI id.
2103      *
2104      * Various games depend on the PCI id, so somehow we need to provide one.
2105      * A simple option is to parse the renderer string and translate this to
2106      * the right PCI id. This is a lot of work because there are more than 200
2107      * GPUs just for Nvidia. Various cards share the same renderer string, so
2108      * the amount of code might be 'small' but there are quite a number of
2109      * exceptions which would make this a pain to maintain. Another way would
2110      * be to query the PCI id from the operating system (assuming this is the
2111      * videocard which is used for rendering which is not always the case).
2112      * This would work but it is not very portable. Second it would not work
2113      * well in, let's say, a remote X situation in which the amount of 3d
2114      * features which can be used is limited.
2115      *
2116      * As said most games only use the PCI id to get an indication of the
2117      * capabilities of the card. It doesn't really matter if the given id is
2118      * the correct one if we return the id of a card with similar 3d features.
2119      *
2120      * The code below checks the OpenGL capabilities of a videocard and matches
2121      * that to a certain level of Direct3D functionality. Once a card passes
2122      * the Direct3D9 check, we know that the card (in case of Nvidia) is at
2123      * least a GeforceFX. To give a better estimate we do a basic check on the
2124      * renderer string but if that won't pass we return a default card. This
2125      * way is better than maintaining a full card database as even without a
2126      * full database we can return a card with similar features. Second the
2127      * size of the database can be made quite small because when you know what
2128      * type of 3d functionality a card has, you know to which GPU family the
2129      * GPU must belong. Because of this you only have to check a small part of
2130      * the renderer string to distinguishes between different models from that
2131      * family.
2132      *
2133      * The code also selects a default amount of video memory which we will
2134      * use for an estimation of the amount of free texture memory. In case of
2135      * real D3D the amount of texture memory includes video memory and system
2136      * memory (to be specific AGP memory or in case of PCIE TurboCache /
2137      * HyperMemory). We don't know how much system memory can be addressed by
2138      * the system but we can make a reasonable estimation about the amount of
2139      * video memory. If the value is slightly wrong it doesn't matter as we
2140      * didn't include AGP-like memory which makes the amount of addressable
2141      * memory higher and second OpenGL isn't that critical it moves to system
2142      * memory behind our backs if really needed. Note that the amount of video
2143      * memory can be overruled using a registry setting. */
2144
2145     int i;
2146
2147     for (i = 0; i < (sizeof(vendor_card_select_table) / sizeof(*vendor_card_select_table)); ++i)
2148     {
2149         if ((vendor_card_select_table[i].gl_vendor != *gl_vendor)
2150             || (vendor_card_select_table[i].card_vendor != *card_vendor))
2151                 continue;
2152         TRACE_(d3d_caps)("Applying card_selector \"%s\".\n", vendor_card_select_table[i].description);
2153         return vendor_card_select_table[i].select_card(gl_info, gl_renderer);
2154     }
2155
2156     FIXME_(d3d_caps)("No card selector available for GL vendor %d and card vendor %04x.\n",
2157                      *gl_vendor, *card_vendor);
2158
2159     /* Default to generic Nvidia hardware based on the supported OpenGL extensions. The choice
2160      * for Nvidia was because the hardware and drivers they make are of good quality. This makes
2161      * them a good generic choice. */
2162     *card_vendor = HW_VENDOR_NVIDIA;
2163     if (WINE_D3D9_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCEFX_5600;
2164     if (WINE_D3D8_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCE3;
2165     if (WINE_D3D7_CAPABLE(gl_info)) return CARD_NVIDIA_GEFORCE;
2166     if (WINE_D3D6_CAPABLE(gl_info)) return CARD_NVIDIA_RIVA_TNT;
2167     return CARD_NVIDIA_RIVA_128;
2168 }
2169
2170 static const struct fragment_pipeline *select_fragment_implementation(struct wined3d_adapter *adapter)
2171 {
2172     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
2173     int vs_selected_mode, ps_selected_mode;
2174
2175     select_shader_mode(gl_info, &ps_selected_mode, &vs_selected_mode);
2176     if ((ps_selected_mode == SHADER_ARB || ps_selected_mode == SHADER_GLSL)
2177             && gl_info->supported[ARB_FRAGMENT_PROGRAM]) return &arbfp_fragment_pipeline;
2178     else if (ps_selected_mode == SHADER_ATI) return &atifs_fragment_pipeline;
2179     else if (gl_info->supported[NV_REGISTER_COMBINERS]
2180             && gl_info->supported[NV_TEXTURE_SHADER2]) return &nvts_fragment_pipeline;
2181     else if (gl_info->supported[NV_REGISTER_COMBINERS]) return &nvrc_fragment_pipeline;
2182     else return &ffp_fragment_pipeline;
2183 }
2184
2185 static const shader_backend_t *select_shader_backend(struct wined3d_adapter *adapter)
2186 {
2187     int vs_selected_mode, ps_selected_mode;
2188
2189     select_shader_mode(&adapter->gl_info, &ps_selected_mode, &vs_selected_mode);
2190     if (vs_selected_mode == SHADER_GLSL || ps_selected_mode == SHADER_GLSL) return &glsl_shader_backend;
2191     if (vs_selected_mode == SHADER_ARB || ps_selected_mode == SHADER_ARB) return &arb_program_shader_backend;
2192     return &none_shader_backend;
2193 }
2194
2195 static const struct blit_shader *select_blit_implementation(struct wined3d_adapter *adapter)
2196 {
2197     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
2198     int vs_selected_mode, ps_selected_mode;
2199
2200     select_shader_mode(gl_info, &ps_selected_mode, &vs_selected_mode);
2201     if ((ps_selected_mode == SHADER_ARB || ps_selected_mode == SHADER_GLSL)
2202             && gl_info->supported[ARB_FRAGMENT_PROGRAM]) return &arbfp_blit;
2203     else return &ffp_blit;
2204 }
2205
2206 static void load_gl_funcs(struct wined3d_gl_info *gl_info, DWORD gl_version)
2207 {
2208     DWORD ver;
2209
2210 #define USE_GL_FUNC(type, pfn, ext, replace) \
2211     if (gl_info->supported[ext]) gl_info->pfn = (type)pwglGetProcAddress(#pfn); \
2212     else if ((ver = ver_for_ext(ext)) && ver <= gl_version) gl_info->pfn = (type)pwglGetProcAddress(#replace); \
2213     else gl_info->pfn = NULL;
2214
2215     GL_EXT_FUNCS_GEN;
2216 #undef USE_GL_FUNC
2217
2218 #define USE_GL_FUNC(type, pfn, ext, replace) gl_info->pfn = (type)pwglGetProcAddress(#pfn);
2219     WGL_EXT_FUNCS_GEN;
2220 #undef USE_GL_FUNC
2221 }
2222
2223 /* Context activation is done by the caller. */
2224 static BOOL IWineD3DImpl_FillGLCaps(struct wined3d_adapter *adapter)
2225 {
2226     struct wined3d_driver_info *driver_info = &adapter->driver_info;
2227     struct wined3d_gl_info *gl_info = &adapter->gl_info;
2228     const char *GL_Extensions    = NULL;
2229     const char *WGL_Extensions   = NULL;
2230     const char *gl_vendor_str, *gl_renderer_str, *gl_version_str;
2231     struct fragment_caps fragment_caps;
2232     enum wined3d_gl_vendor gl_vendor;
2233     enum wined3d_pci_vendor card_vendor;
2234     enum wined3d_pci_device device;
2235     GLint       gl_max;
2236     GLfloat     gl_floatv[2];
2237     unsigned    i;
2238     HDC         hdc;
2239     DWORD gl_version;
2240     size_t len;
2241
2242     TRACE_(d3d_caps)("(%p)\n", gl_info);
2243
2244     ENTER_GL();
2245
2246     gl_renderer_str = (const char *)glGetString(GL_RENDERER);
2247     TRACE_(d3d_caps)("GL_RENDERER: %s.\n", debugstr_a(gl_renderer_str));
2248     if (!gl_renderer_str)
2249     {
2250         LEAVE_GL();
2251         ERR_(d3d_caps)("Received a NULL GL_RENDERER.\n");
2252         return FALSE;
2253     }
2254
2255     gl_vendor_str = (const char *)glGetString(GL_VENDOR);
2256     TRACE_(d3d_caps)("GL_VENDOR: %s.\n", debugstr_a(gl_vendor_str));
2257     if (!gl_vendor_str)
2258     {
2259         LEAVE_GL();
2260         ERR_(d3d_caps)("Received a NULL GL_VENDOR.\n");
2261         return FALSE;
2262     }
2263
2264     /* Parse the GL_VERSION field into major and minor information */
2265     gl_version_str = (const char *)glGetString(GL_VERSION);
2266     TRACE_(d3d_caps)("GL_VERSION: %s.\n", debugstr_a(gl_version_str));
2267     if (!gl_version_str)
2268     {
2269         LEAVE_GL();
2270         ERR_(d3d_caps)("Received a NULL GL_VERSION.\n");
2271         return FALSE;
2272     }
2273     gl_version = wined3d_parse_gl_version(gl_version_str);
2274
2275     /*
2276      * Initialize openGL extension related variables
2277      *  with Default values
2278      */
2279     memset(gl_info->supported, 0, sizeof(gl_info->supported));
2280     gl_info->limits.blends = 1;
2281     gl_info->limits.buffers = 1;
2282     gl_info->limits.textures = 1;
2283     gl_info->limits.fragment_samplers = 1;
2284     gl_info->limits.vertex_samplers = 0;
2285     gl_info->limits.combined_samplers = gl_info->limits.fragment_samplers + gl_info->limits.vertex_samplers;
2286     gl_info->limits.sampler_stages = 1;
2287     gl_info->limits.glsl_vs_float_constants = 0;
2288     gl_info->limits.glsl_ps_float_constants = 0;
2289     gl_info->limits.arb_vs_float_constants = 0;
2290     gl_info->limits.arb_vs_native_constants = 0;
2291     gl_info->limits.arb_vs_instructions = 0;
2292     gl_info->limits.arb_vs_temps = 0;
2293     gl_info->limits.arb_ps_float_constants = 0;
2294     gl_info->limits.arb_ps_local_constants = 0;
2295     gl_info->limits.arb_ps_instructions = 0;
2296     gl_info->limits.arb_ps_temps = 0;
2297
2298     /* Retrieve opengl defaults */
2299     glGetIntegerv(GL_MAX_CLIP_PLANES, &gl_max);
2300     gl_info->limits.clipplanes = min(WINED3DMAXUSERCLIPPLANES, gl_max);
2301     TRACE_(d3d_caps)("ClipPlanes support - num Planes=%d\n", gl_max);
2302
2303     glGetIntegerv(GL_MAX_LIGHTS, &gl_max);
2304     gl_info->limits.lights = gl_max;
2305     TRACE_(d3d_caps)("Lights support - max lights=%d\n", gl_max);
2306
2307     glGetIntegerv(GL_MAX_TEXTURE_SIZE, &gl_max);
2308     gl_info->limits.texture_size = gl_max;
2309     TRACE_(d3d_caps)("Maximum texture size support - max texture size=%d\n", gl_max);
2310
2311     glGetFloatv(GL_ALIASED_POINT_SIZE_RANGE, gl_floatv);
2312     gl_info->limits.pointsize_min = gl_floatv[0];
2313     gl_info->limits.pointsize_max = gl_floatv[1];
2314     TRACE_(d3d_caps)("Maximum point size support - max point size=%f\n", gl_floatv[1]);
2315
2316     /* Parse the gl supported features, in theory enabling parts of our code appropriately. */
2317     GL_Extensions = (const char *)glGetString(GL_EXTENSIONS);
2318     if (!GL_Extensions)
2319     {
2320         LEAVE_GL();
2321         ERR_(d3d_caps)("Received a NULL GL_EXTENSIONS.\n");
2322         return FALSE;
2323     }
2324
2325     LEAVE_GL();
2326
2327     TRACE_(d3d_caps)("GL_Extensions reported:\n");
2328
2329     gl_info->supported[WINED3D_GL_EXT_NONE] = TRUE;
2330
2331     while (*GL_Extensions)
2332     {
2333         const char *start;
2334
2335         while (isspace(*GL_Extensions)) ++GL_Extensions;
2336         start = GL_Extensions;
2337         while (!isspace(*GL_Extensions) && *GL_Extensions) ++GL_Extensions;
2338
2339         len = GL_Extensions - start;
2340         if (!len) continue;
2341
2342         TRACE_(d3d_caps)("- %s\n", debugstr_an(start, len));
2343
2344         for (i = 0; i < (sizeof(EXTENSION_MAP) / sizeof(*EXTENSION_MAP)); ++i)
2345         {
2346             if (len == strlen(EXTENSION_MAP[i].extension_string)
2347                     && !memcmp(start, EXTENSION_MAP[i].extension_string, len))
2348             {
2349                 TRACE_(d3d_caps)(" FOUND: %s support.\n", EXTENSION_MAP[i].extension_string);
2350                 gl_info->supported[EXTENSION_MAP[i].extension] = TRUE;
2351                 break;
2352             }
2353         }
2354     }
2355
2356     /* Now work out what GL support this card really has */
2357     load_gl_funcs( gl_info, gl_version );
2358
2359     ENTER_GL();
2360
2361     /* Now mark all the extensions supported which are included in the opengl core version. Do this *after*
2362      * loading the functions, otherwise the code above will load the extension entry points instead of the
2363      * core functions, which may not work. */
2364     for (i = 0; i < (sizeof(EXTENSION_MAP) / sizeof(*EXTENSION_MAP)); ++i)
2365     {
2366         if (!gl_info->supported[EXTENSION_MAP[i].extension]
2367                 && EXTENSION_MAP[i].version <= gl_version && EXTENSION_MAP[i].version)
2368         {
2369             TRACE_(d3d_caps)(" GL CORE: %s support.\n", EXTENSION_MAP[i].extension_string);
2370             gl_info->supported[EXTENSION_MAP[i].extension] = TRUE;
2371         }
2372     }
2373
2374     if (gl_version >= MAKEDWORD_VERSION(2, 0)) gl_info->supported[WINED3D_GL_VERSION_2_0] = TRUE;
2375
2376     if (gl_info->supported[APPLE_FENCE])
2377     {
2378         /* GL_NV_fence and GL_APPLE_fence provide the same functionality basically.
2379          * The apple extension interacts with some other apple exts. Disable the NV
2380          * extension if the apple one is support to prevent confusion in other parts
2381          * of the code. */
2382         gl_info->supported[NV_FENCE] = FALSE;
2383     }
2384     if (gl_info->supported[APPLE_FLOAT_PIXELS])
2385     {
2386         /* GL_APPLE_float_pixels == GL_ARB_texture_float + GL_ARB_half_float_pixel
2387          *
2388          * The enums are the same:
2389          * GL_RGBA16F_ARB     = GL_RGBA_FLOAT16_APPLE = 0x881A
2390          * GL_RGB16F_ARB      = GL_RGB_FLOAT16_APPLE  = 0x881B
2391          * GL_RGBA32F_ARB     = GL_RGBA_FLOAT32_APPLE = 0x8814
2392          * GL_RGB32F_ARB      = GL_RGB_FLOAT32_APPLE  = 0x8815
2393          * GL_HALF_FLOAT_ARB  = GL_HALF_APPLE         = 0x140B
2394          */
2395         if (!gl_info->supported[ARB_TEXTURE_FLOAT])
2396         {
2397             TRACE_(d3d_caps)(" IMPLIED: GL_ARB_texture_float support(from GL_APPLE_float_pixels.\n");
2398             gl_info->supported[ARB_TEXTURE_FLOAT] = TRUE;
2399         }
2400         if (!gl_info->supported[ARB_HALF_FLOAT_PIXEL])
2401         {
2402             TRACE_(d3d_caps)(" IMPLIED: GL_ARB_half_float_pixel support(from GL_APPLE_float_pixels.\n");
2403             gl_info->supported[ARB_HALF_FLOAT_PIXEL] = TRUE;
2404         }
2405     }
2406     if (gl_info->supported[ARB_MAP_BUFFER_RANGE])
2407     {
2408         /* GL_ARB_map_buffer_range and GL_APPLE_flush_buffer_range provide the same
2409          * functionality. Prefer the ARB extension */
2410         gl_info->supported[APPLE_FLUSH_BUFFER_RANGE] = FALSE;
2411     }
2412     if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2413     {
2414         TRACE_(d3d_caps)(" IMPLIED: NVIDIA (NV) Texture Gen Reflection support.\n");
2415         gl_info->supported[NV_TEXGEN_REFLECTION] = TRUE;
2416     }
2417     if (!gl_info->supported[ARB_DEPTH_CLAMP] && gl_info->supported[NV_DEPTH_CLAMP])
2418     {
2419         TRACE_(d3d_caps)(" IMPLIED: ARB_depth_clamp support (by NV_depth_clamp).\n");
2420         gl_info->supported[ARB_DEPTH_CLAMP] = TRUE;
2421     }
2422     if (!gl_info->supported[ARB_VERTEX_ARRAY_BGRA] && gl_info->supported[EXT_VERTEX_ARRAY_BGRA])
2423     {
2424         TRACE_(d3d_caps)(" IMPLIED: ARB_vertex_array_bgra support (by EXT_vertex_array_bgra).\n");
2425         gl_info->supported[ARB_VERTEX_ARRAY_BGRA] = TRUE;
2426     }
2427     if (!gl_info->supported[ARB_TEXTURE_COMPRESSION_RGTC] && gl_info->supported[EXT_TEXTURE_COMPRESSION_RGTC])
2428     {
2429         TRACE_(d3d_caps)(" IMPLIED: ARB_texture_compression_rgtc support (by EXT_texture_compression_rgtc).\n");
2430         gl_info->supported[ARB_TEXTURE_COMPRESSION_RGTC] = TRUE;
2431     }
2432     if (gl_info->supported[NV_TEXTURE_SHADER2])
2433     {
2434         if (gl_info->supported[NV_REGISTER_COMBINERS])
2435         {
2436             /* Also disable ATI_FRAGMENT_SHADER if register combiners and texture_shader2
2437              * are supported. The nv extensions provide the same functionality as the
2438              * ATI one, and a bit more(signed pixelformats). */
2439             gl_info->supported[ATI_FRAGMENT_SHADER] = FALSE;
2440         }
2441     }
2442
2443     if (gl_info->supported[NV_REGISTER_COMBINERS])
2444     {
2445         glGetIntegerv(GL_MAX_GENERAL_COMBINERS_NV, &gl_max);
2446         gl_info->limits.general_combiners = gl_max;
2447         TRACE_(d3d_caps)("Max general combiners: %d.\n", gl_max);
2448     }
2449     if (gl_info->supported[ARB_DRAW_BUFFERS])
2450     {
2451         glGetIntegerv(GL_MAX_DRAW_BUFFERS_ARB, &gl_max);
2452         gl_info->limits.buffers = gl_max;
2453         TRACE_(d3d_caps)("Max draw buffers: %u.\n", gl_max);
2454     }
2455     if (gl_info->supported[ARB_MULTITEXTURE])
2456     {
2457         glGetIntegerv(GL_MAX_TEXTURE_UNITS_ARB, &gl_max);
2458         gl_info->limits.textures = min(MAX_TEXTURES, gl_max);
2459         TRACE_(d3d_caps)("Max textures: %d.\n", gl_info->limits.textures);
2460
2461         if (gl_info->supported[ARB_FRAGMENT_PROGRAM])
2462         {
2463             GLint tmp;
2464             glGetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS_ARB, &tmp);
2465             gl_info->limits.fragment_samplers = min(MAX_FRAGMENT_SAMPLERS, tmp);
2466         }
2467         else
2468         {
2469             gl_info->limits.fragment_samplers = max(gl_info->limits.fragment_samplers, gl_max);
2470         }
2471         TRACE_(d3d_caps)("Max fragment samplers: %d.\n", gl_info->limits.fragment_samplers);
2472
2473         if (gl_info->supported[ARB_VERTEX_SHADER])
2474         {
2475             GLint tmp;
2476             glGetIntegerv(GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS_ARB, &tmp);
2477             gl_info->limits.vertex_samplers = tmp;
2478             glGetIntegerv(GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS_ARB, &tmp);
2479             gl_info->limits.combined_samplers = tmp;
2480
2481             /* Loading GLSL sampler uniforms is much simpler if we can assume that the sampler setup
2482              * is known at shader link time. In a vertex shader + pixel shader combination this isn't
2483              * an issue because then the sampler setup only depends on the two shaders. If a pixel
2484              * shader is used with fixed function vertex processing we're fine too because fixed function
2485              * vertex processing doesn't use any samplers. If fixed function fragment processing is
2486              * used we have to make sure that all vertex sampler setups are valid together with all
2487              * possible fixed function fragment processing setups. This is true if vsamplers + MAX_TEXTURES
2488              * <= max_samplers. This is true on all d3d9 cards that support vtf(gf 6 and gf7 cards).
2489              * dx9 radeon cards do not support vertex texture fetch. DX10 cards have 128 samplers, and
2490              * dx9 is limited to 8 fixed function texture stages and 4 vertex samplers. DX10 does not have
2491              * a fixed function pipeline anymore.
2492              *
2493              * So this is just a check to check that our assumption holds true. If not, write a warning
2494              * and reduce the number of vertex samplers or probably disable vertex texture fetch. */
2495             if (gl_info->limits.vertex_samplers && gl_info->limits.combined_samplers < 12
2496                     && MAX_TEXTURES + gl_info->limits.vertex_samplers > gl_info->limits.combined_samplers)
2497             {
2498                 FIXME("OpenGL implementation supports %u vertex samplers and %u total samplers.\n",
2499                         gl_info->limits.vertex_samplers, gl_info->limits.combined_samplers);
2500                 FIXME("Expected vertex samplers + MAX_TEXTURES(=8) > combined_samplers.\n");
2501                 if (gl_info->limits.combined_samplers > MAX_TEXTURES)
2502                     gl_info->limits.vertex_samplers = gl_info->limits.combined_samplers - MAX_TEXTURES;
2503                 else
2504                     gl_info->limits.vertex_samplers = 0;
2505             }
2506         }
2507         else
2508         {
2509             gl_info->limits.combined_samplers = gl_info->limits.fragment_samplers;
2510         }
2511         TRACE_(d3d_caps)("Max vertex samplers: %u.\n", gl_info->limits.vertex_samplers);
2512         TRACE_(d3d_caps)("Max combined samplers: %u.\n", gl_info->limits.combined_samplers);
2513     }
2514     if (gl_info->supported[ARB_VERTEX_BLEND])
2515     {
2516         glGetIntegerv(GL_MAX_VERTEX_UNITS_ARB, &gl_max);
2517         gl_info->limits.blends = gl_max;
2518         TRACE_(d3d_caps)("Max blends: %u.\n", gl_info->limits.blends);
2519     }
2520     if (gl_info->supported[EXT_TEXTURE3D])
2521     {
2522         glGetIntegerv(GL_MAX_3D_TEXTURE_SIZE_EXT, &gl_max);
2523         gl_info->limits.texture3d_size = gl_max;
2524         TRACE_(d3d_caps)("Max texture3D size: %d.\n", gl_info->limits.texture3d_size);
2525     }
2526     if (gl_info->supported[EXT_TEXTURE_FILTER_ANISOTROPIC])
2527     {
2528         glGetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &gl_max);
2529         gl_info->limits.anisotropy = gl_max;
2530         TRACE_(d3d_caps)("Max anisotropy: %d.\n", gl_info->limits.anisotropy);
2531     }
2532     if (gl_info->supported[ARB_FRAGMENT_PROGRAM])
2533     {
2534         GL_EXTCALL(glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB, GL_MAX_PROGRAM_ENV_PARAMETERS_ARB, &gl_max));
2535         gl_info->limits.arb_ps_float_constants = gl_max;
2536         TRACE_(d3d_caps)("Max ARB_FRAGMENT_PROGRAM float constants: %d.\n", gl_info->limits.arb_ps_float_constants);
2537         GL_EXTCALL(glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB, GL_MAX_PROGRAM_NATIVE_PARAMETERS_ARB, &gl_max));
2538         gl_info->limits.arb_ps_native_constants = gl_max;
2539         TRACE_(d3d_caps)("Max ARB_FRAGMENT_PROGRAM native float constants: %d.\n",
2540                 gl_info->limits.arb_ps_native_constants);
2541         GL_EXTCALL(glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB, GL_MAX_PROGRAM_NATIVE_TEMPORARIES_ARB, &gl_max));
2542         gl_info->limits.arb_ps_temps = gl_max;
2543         TRACE_(d3d_caps)("Max ARB_FRAGMENT_PROGRAM native temporaries: %d.\n", gl_info->limits.arb_ps_temps);
2544         GL_EXTCALL(glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB, GL_MAX_PROGRAM_NATIVE_INSTRUCTIONS_ARB, &gl_max));
2545         gl_info->limits.arb_ps_instructions = gl_max;
2546         TRACE_(d3d_caps)("Max ARB_FRAGMENT_PROGRAM native instructions: %d.\n", gl_info->limits.arb_ps_instructions);
2547         GL_EXTCALL(glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB, GL_MAX_PROGRAM_LOCAL_PARAMETERS_ARB, &gl_max));
2548         gl_info->limits.arb_ps_local_constants = gl_max;
2549         TRACE_(d3d_caps)("Max ARB_FRAGMENT_PROGRAM local parameters: %d.\n", gl_info->limits.arb_ps_instructions);
2550     }
2551     if (gl_info->supported[ARB_VERTEX_PROGRAM])
2552     {
2553         GL_EXTCALL(glGetProgramivARB(GL_VERTEX_PROGRAM_ARB, GL_MAX_PROGRAM_ENV_PARAMETERS_ARB, &gl_max));
2554         gl_info->limits.arb_vs_float_constants = gl_max;
2555         TRACE_(d3d_caps)("Max ARB_VERTEX_PROGRAM float constants: %d.\n", gl_info->limits.arb_vs_float_constants);
2556         GL_EXTCALL(glGetProgramivARB(GL_VERTEX_PROGRAM_ARB, GL_MAX_PROGRAM_NATIVE_PARAMETERS_ARB, &gl_max));
2557         gl_info->limits.arb_vs_native_constants = gl_max;
2558         TRACE_(d3d_caps)("Max ARB_VERTEX_PROGRAM native float constants: %d.\n",
2559                 gl_info->limits.arb_vs_native_constants);
2560         GL_EXTCALL(glGetProgramivARB(GL_VERTEX_PROGRAM_ARB, GL_MAX_PROGRAM_NATIVE_TEMPORARIES_ARB, &gl_max));
2561         gl_info->limits.arb_vs_temps = gl_max;
2562         TRACE_(d3d_caps)("Max ARB_VERTEX_PROGRAM native temporaries: %d.\n", gl_info->limits.arb_vs_temps);
2563         GL_EXTCALL(glGetProgramivARB(GL_VERTEX_PROGRAM_ARB, GL_MAX_PROGRAM_NATIVE_INSTRUCTIONS_ARB, &gl_max));
2564         gl_info->limits.arb_vs_instructions = gl_max;
2565         TRACE_(d3d_caps)("Max ARB_VERTEX_PROGRAM native instructions: %d.\n", gl_info->limits.arb_vs_instructions);
2566
2567         if (test_arb_vs_offset_limit(gl_info)) gl_info->quirks |= WINED3D_QUIRK_ARB_VS_OFFSET_LIMIT;
2568     }
2569     if (gl_info->supported[ARB_VERTEX_SHADER])
2570     {
2571         glGetIntegerv(GL_MAX_VERTEX_UNIFORM_COMPONENTS_ARB, &gl_max);
2572         gl_info->limits.glsl_vs_float_constants = gl_max / 4;
2573         TRACE_(d3d_caps)("Max ARB_VERTEX_SHADER float constants: %u.\n", gl_info->limits.glsl_vs_float_constants);
2574     }
2575     if (gl_info->supported[ARB_FRAGMENT_SHADER])
2576     {
2577         glGetIntegerv(GL_MAX_FRAGMENT_UNIFORM_COMPONENTS_ARB, &gl_max);
2578         gl_info->limits.glsl_ps_float_constants = gl_max / 4;
2579         TRACE_(d3d_caps)("Max ARB_FRAGMENT_SHADER float constants: %u.\n", gl_info->limits.glsl_ps_float_constants);
2580         glGetIntegerv(GL_MAX_VARYING_FLOATS_ARB, &gl_max);
2581         gl_info->limits.glsl_varyings = gl_max;
2582         TRACE_(d3d_caps)("Max GLSL varyings: %u (%u 4 component varyings).\n", gl_max, gl_max / 4);
2583     }
2584     if (gl_info->supported[ARB_SHADING_LANGUAGE_100])
2585     {
2586         const char *str = (const char *)glGetString(GL_SHADING_LANGUAGE_VERSION_ARB);
2587         unsigned int major, minor;
2588
2589         TRACE_(d3d_caps)("GLSL version string: %s.\n", debugstr_a(str));
2590
2591         /* The format of the GLSL version string is "major.minor[.release] [vendor info]". */
2592         sscanf(str, "%u.%u", &major, &minor);
2593         gl_info->glsl_version = MAKEDWORD_VERSION(major, minor);
2594     }
2595     if (gl_info->supported[NV_LIGHT_MAX_EXPONENT])
2596     {
2597         glGetFloatv(GL_MAX_SHININESS_NV, &gl_info->limits.shininess);
2598     }
2599     else
2600     {
2601         gl_info->limits.shininess = 128.0f;
2602     }
2603     if (gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO])
2604     {
2605         /* If we have full NP2 texture support, disable
2606          * GL_ARB_texture_rectangle because we will never use it.
2607          * This saves a few redundant glDisable calls. */
2608         gl_info->supported[ARB_TEXTURE_RECTANGLE] = FALSE;
2609     }
2610     if (gl_info->supported[ATI_FRAGMENT_SHADER])
2611     {
2612         /* Disable NV_register_combiners and fragment shader if this is supported.
2613          * generally the NV extensions are preferred over the ATI ones, and this
2614          * extension is disabled if register_combiners and texture_shader2 are both
2615          * supported. So we reach this place only if we have incomplete NV dxlevel 8
2616          * fragment processing support. */
2617         gl_info->supported[NV_REGISTER_COMBINERS] = FALSE;
2618         gl_info->supported[NV_REGISTER_COMBINERS2] = FALSE;
2619         gl_info->supported[NV_TEXTURE_SHADER] = FALSE;
2620         gl_info->supported[NV_TEXTURE_SHADER2] = FALSE;
2621     }
2622     if (gl_info->supported[NV_HALF_FLOAT])
2623     {
2624         /* GL_ARB_half_float_vertex is a subset of GL_NV_half_float. */
2625         gl_info->supported[ARB_HALF_FLOAT_VERTEX] = TRUE;
2626     }
2627     if (gl_info->supported[ARB_POINT_SPRITE])
2628     {
2629         gl_info->limits.point_sprite_units = gl_info->limits.textures;
2630     }
2631     else
2632     {
2633         gl_info->limits.point_sprite_units = 0;
2634     }
2635     checkGLcall("extension detection");
2636
2637     LEAVE_GL();
2638
2639     adapter->fragment_pipe = select_fragment_implementation(adapter);
2640     adapter->shader_backend = select_shader_backend(adapter);
2641     adapter->blitter = select_blit_implementation(adapter);
2642
2643     adapter->fragment_pipe->get_caps(gl_info, &fragment_caps);
2644     gl_info->limits.texture_stages = fragment_caps.MaxTextureBlendStages;
2645     TRACE_(d3d_caps)("Max texture stages: %u.\n", gl_info->limits.texture_stages);
2646
2647     /* In some cases the number of texture stages can be larger than the number
2648      * of samplers. The GF4 for example can use only 2 samplers (no fragment
2649      * shaders), but 8 texture stages (register combiners). */
2650     gl_info->limits.sampler_stages = max(gl_info->limits.fragment_samplers, gl_info->limits.texture_stages);
2651
2652     if (gl_info->supported[ARB_FRAMEBUFFER_OBJECT])
2653     {
2654         gl_info->fbo_ops.glIsRenderbuffer = gl_info->glIsRenderbuffer;
2655         gl_info->fbo_ops.glBindRenderbuffer = gl_info->glBindRenderbuffer;
2656         gl_info->fbo_ops.glDeleteRenderbuffers = gl_info->glDeleteRenderbuffers;
2657         gl_info->fbo_ops.glGenRenderbuffers = gl_info->glGenRenderbuffers;
2658         gl_info->fbo_ops.glRenderbufferStorage = gl_info->glRenderbufferStorage;
2659         gl_info->fbo_ops.glRenderbufferStorageMultisample = gl_info->glRenderbufferStorageMultisample;
2660         gl_info->fbo_ops.glGetRenderbufferParameteriv = gl_info->glGetRenderbufferParameteriv;
2661         gl_info->fbo_ops.glIsFramebuffer = gl_info->glIsFramebuffer;
2662         gl_info->fbo_ops.glBindFramebuffer = gl_info->glBindFramebuffer;
2663         gl_info->fbo_ops.glDeleteFramebuffers = gl_info->glDeleteFramebuffers;
2664         gl_info->fbo_ops.glGenFramebuffers = gl_info->glGenFramebuffers;
2665         gl_info->fbo_ops.glCheckFramebufferStatus = gl_info->glCheckFramebufferStatus;
2666         gl_info->fbo_ops.glFramebufferTexture1D = gl_info->glFramebufferTexture1D;
2667         gl_info->fbo_ops.glFramebufferTexture2D = gl_info->glFramebufferTexture2D;
2668         gl_info->fbo_ops.glFramebufferTexture3D = gl_info->glFramebufferTexture3D;
2669         gl_info->fbo_ops.glFramebufferRenderbuffer = gl_info->glFramebufferRenderbuffer;
2670         gl_info->fbo_ops.glGetFramebufferAttachmentParameteriv = gl_info->glGetFramebufferAttachmentParameteriv;
2671         gl_info->fbo_ops.glBlitFramebuffer = gl_info->glBlitFramebuffer;
2672         gl_info->fbo_ops.glGenerateMipmap = gl_info->glGenerateMipmap;
2673     }
2674     else
2675     {
2676         if (gl_info->supported[EXT_FRAMEBUFFER_OBJECT])
2677         {
2678             gl_info->fbo_ops.glIsRenderbuffer = gl_info->glIsRenderbufferEXT;
2679             gl_info->fbo_ops.glBindRenderbuffer = gl_info->glBindRenderbufferEXT;
2680             gl_info->fbo_ops.glDeleteRenderbuffers = gl_info->glDeleteRenderbuffersEXT;
2681             gl_info->fbo_ops.glGenRenderbuffers = gl_info->glGenRenderbuffersEXT;
2682             gl_info->fbo_ops.glRenderbufferStorage = gl_info->glRenderbufferStorageEXT;
2683             gl_info->fbo_ops.glGetRenderbufferParameteriv = gl_info->glGetRenderbufferParameterivEXT;
2684             gl_info->fbo_ops.glIsFramebuffer = gl_info->glIsFramebufferEXT;
2685             gl_info->fbo_ops.glBindFramebuffer = gl_info->glBindFramebufferEXT;
2686             gl_info->fbo_ops.glDeleteFramebuffers = gl_info->glDeleteFramebuffersEXT;
2687             gl_info->fbo_ops.glGenFramebuffers = gl_info->glGenFramebuffersEXT;
2688             gl_info->fbo_ops.glCheckFramebufferStatus = gl_info->glCheckFramebufferStatusEXT;
2689             gl_info->fbo_ops.glFramebufferTexture1D = gl_info->glFramebufferTexture1DEXT;
2690             gl_info->fbo_ops.glFramebufferTexture2D = gl_info->glFramebufferTexture2DEXT;
2691             gl_info->fbo_ops.glFramebufferTexture3D = gl_info->glFramebufferTexture3DEXT;
2692             gl_info->fbo_ops.glFramebufferRenderbuffer = gl_info->glFramebufferRenderbufferEXT;
2693             gl_info->fbo_ops.glGetFramebufferAttachmentParameteriv = gl_info->glGetFramebufferAttachmentParameterivEXT;
2694             gl_info->fbo_ops.glGenerateMipmap = gl_info->glGenerateMipmapEXT;
2695         }
2696         else if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
2697         {
2698             WARN_(d3d_caps)("Framebuffer objects not supported, falling back to backbuffer offscreen rendering mode.\n");
2699             wined3d_settings.offscreen_rendering_mode = ORM_BACKBUFFER;
2700         }
2701         if (gl_info->supported[EXT_FRAMEBUFFER_BLIT])
2702         {
2703             gl_info->fbo_ops.glBlitFramebuffer = gl_info->glBlitFramebufferEXT;
2704         }
2705         if (gl_info->supported[EXT_FRAMEBUFFER_MULTISAMPLE])
2706         {
2707             gl_info->fbo_ops.glRenderbufferStorageMultisample = gl_info->glRenderbufferStorageMultisampleEXT;
2708         }
2709     }
2710
2711     /* MRTs are currently only supported when FBOs are used. */
2712     if (wined3d_settings.offscreen_rendering_mode != ORM_FBO)
2713     {
2714         gl_info->limits.buffers = 1;
2715     }
2716
2717     gl_vendor = wined3d_guess_gl_vendor(gl_info, gl_vendor_str, gl_renderer_str);
2718     card_vendor = wined3d_guess_card_vendor(gl_vendor_str, gl_renderer_str);
2719     TRACE_(d3d_caps)("found GL_VENDOR (%s)->(0x%04x/0x%04x)\n", debugstr_a(gl_vendor_str), gl_vendor, card_vendor);
2720
2721     device = wined3d_guess_card(gl_info, gl_renderer_str, &gl_vendor, &card_vendor);
2722     TRACE_(d3d_caps)("FOUND (fake) card: 0x%x (vendor id), 0x%x (device id)\n", card_vendor, device);
2723
2724     gl_info->wrap_lookup[WINED3DTADDRESS_WRAP - WINED3DTADDRESS_WRAP] = GL_REPEAT;
2725     gl_info->wrap_lookup[WINED3DTADDRESS_MIRROR - WINED3DTADDRESS_WRAP] =
2726             gl_info->supported[ARB_TEXTURE_MIRRORED_REPEAT] ? GL_MIRRORED_REPEAT_ARB : GL_REPEAT;
2727     gl_info->wrap_lookup[WINED3DTADDRESS_CLAMP - WINED3DTADDRESS_WRAP] = GL_CLAMP_TO_EDGE;
2728     gl_info->wrap_lookup[WINED3DTADDRESS_BORDER - WINED3DTADDRESS_WRAP] =
2729             gl_info->supported[ARB_TEXTURE_BORDER_CLAMP] ? GL_CLAMP_TO_BORDER_ARB : GL_REPEAT;
2730     gl_info->wrap_lookup[WINED3DTADDRESS_MIRRORONCE - WINED3DTADDRESS_WRAP] =
2731             gl_info->supported[ATI_TEXTURE_MIRROR_ONCE] ? GL_MIRROR_CLAMP_TO_EDGE_ATI : GL_REPEAT;
2732
2733     /* Make sure there's an active HDC else the WGL extensions will fail */
2734     hdc = pwglGetCurrentDC();
2735     if (hdc) {
2736         /* Not all GL drivers might offer WGL extensions e.g. VirtualBox */
2737         if(GL_EXTCALL(wglGetExtensionsStringARB))
2738             WGL_Extensions = GL_EXTCALL(wglGetExtensionsStringARB(hdc));
2739
2740         if (!WGL_Extensions)
2741         {
2742             ERR("   WGL_Extensions returns NULL\n");
2743         }
2744         else
2745         {
2746             TRACE_(d3d_caps)("WGL_Extensions reported:\n");
2747             while (*WGL_Extensions)
2748             {
2749                 const char *Start;
2750                 char ThisExtn[256];
2751
2752                 while (isspace(*WGL_Extensions)) WGL_Extensions++;
2753                 Start = WGL_Extensions;
2754                 while (!isspace(*WGL_Extensions) && *WGL_Extensions) ++WGL_Extensions;
2755
2756                 len = WGL_Extensions - Start;
2757                 if (!len || len >= sizeof(ThisExtn))
2758                     continue;
2759
2760                 memcpy(ThisExtn, Start, len);
2761                 ThisExtn[len] = '\0';
2762                 TRACE_(d3d_caps)("- %s\n", debugstr_a(ThisExtn));
2763
2764                 if (!strcmp(ThisExtn, "WGL_ARB_pixel_format")) {
2765                     gl_info->supported[WGL_ARB_PIXEL_FORMAT] = TRUE;
2766                     TRACE_(d3d_caps)("FOUND: WGL_ARB_pixel_format support\n");
2767                 }
2768                 if (!strcmp(ThisExtn, "WGL_WINE_pixel_format_passthrough")) {
2769                     gl_info->supported[WGL_WINE_PIXEL_FORMAT_PASSTHROUGH] = TRUE;
2770                     TRACE_(d3d_caps)("FOUND: WGL_WINE_pixel_format_passthrough support\n");
2771                 }
2772             }
2773         }
2774     }
2775
2776     fixup_extensions(gl_info, gl_renderer_str, gl_vendor, card_vendor, device);
2777     init_driver_info(driver_info, card_vendor, device);
2778     add_gl_compat_wrappers(gl_info);
2779
2780     return TRUE;
2781 }
2782
2783 /**********************************************************
2784  * IWineD3D implementation follows
2785  **********************************************************/
2786
2787 static UINT     WINAPI IWineD3DImpl_GetAdapterCount (IWineD3D *iface) {
2788     IWineD3DImpl *This = (IWineD3DImpl *)iface;
2789
2790     TRACE_(d3d_caps)("(%p): Reporting %u adapters\n", This, This->adapter_count);
2791
2792     return This->adapter_count;
2793 }
2794
2795 static HRESULT WINAPI IWineD3DImpl_RegisterSoftwareDevice(IWineD3D *iface, void *init_function)
2796 {
2797     FIXME("iface %p, init_function %p stub!\n", iface, init_function);
2798
2799     return WINED3D_OK;
2800 }
2801
2802 static HMONITOR WINAPI IWineD3DImpl_GetAdapterMonitor(IWineD3D *iface, UINT Adapter) {
2803     IWineD3DImpl *This = (IWineD3DImpl *)iface;
2804
2805     TRACE_(d3d_caps)("(%p)->(%d)\n", This, Adapter);
2806
2807     if (Adapter >= IWineD3DImpl_GetAdapterCount(iface)) {
2808         return NULL;
2809     }
2810
2811     return MonitorFromPoint(This->adapters[Adapter].monitorPoint, MONITOR_DEFAULTTOPRIMARY);
2812 }
2813
2814 /* FIXME: GetAdapterModeCount and EnumAdapterModes currently only returns modes
2815      of the same bpp but different resolutions                                  */
2816
2817 /* Note: dx9 supplies a format. Calls from d3d8 supply WINED3DFMT_UNKNOWN */
2818 static UINT WINAPI IWineD3DImpl_GetAdapterModeCount(IWineD3D *iface, UINT Adapter, enum wined3d_format_id format_id)
2819 {
2820     IWineD3DImpl *This = (IWineD3DImpl *)iface;
2821
2822     TRACE_(d3d_caps)("iface %p, adapter %u, format_id: %s.\n", iface, Adapter, debug_d3dformat(format_id));
2823
2824     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
2825         return 0;
2826     }
2827
2828     /* TODO: Store modes per adapter and read it from the adapter structure */
2829     if (Adapter == 0)
2830     {
2831         const struct wined3d_format *format = wined3d_get_format(&This->adapters[Adapter].gl_info, format_id);
2832         UINT format_bits = format->byte_count * CHAR_BIT;
2833         unsigned int i = 0;
2834         unsigned int j = 0;
2835         DEVMODEW mode;
2836
2837         memset(&mode, 0, sizeof(mode));
2838         mode.dmSize = sizeof(mode);
2839
2840         while (EnumDisplaySettingsExW(NULL, j, &mode, 0))
2841         {
2842             ++j;
2843
2844             if (format_id == WINED3DFMT_UNKNOWN)
2845             {
2846                 /* This is for D3D8, do not enumerate P8 here */
2847                 if (mode.dmBitsPerPel == 32 || mode.dmBitsPerPel == 16) ++i;
2848             }
2849             else if (mode.dmBitsPerPel == format_bits)
2850             {
2851                 ++i;
2852             }
2853         }
2854
2855         TRACE_(d3d_caps)("(%p}->(Adapter: %d) => %d (out of %d)\n", This, Adapter, i, j);
2856         return i;
2857     } else {
2858         FIXME_(d3d_caps)("Adapter not primary display\n");
2859     }
2860     return 0;
2861 }
2862
2863 /* Note: dx9 supplies a format. Calls from d3d8 supply WINED3DFMT_UNKNOWN */
2864 static HRESULT WINAPI IWineD3DImpl_EnumAdapterModes(IWineD3D *iface, UINT Adapter,
2865         enum wined3d_format_id format_id, UINT Mode, WINED3DDISPLAYMODE *pMode)
2866 {
2867     IWineD3DImpl *This = (IWineD3DImpl *)iface;
2868
2869     TRACE_(d3d_caps)("iface %p, adapter_idx %u, format %s, mode_idx %u, mode %p.\n",
2870             iface, Adapter, debug_d3dformat(format_id), Mode, pMode);
2871
2872     /* Validate the parameters as much as possible */
2873     if (!pMode || Adapter >= IWineD3DImpl_GetAdapterCount(iface)
2874             || Mode >= IWineD3DImpl_GetAdapterModeCount(iface, Adapter, format_id))
2875     {
2876         return WINED3DERR_INVALIDCALL;
2877     }
2878
2879     /* TODO: Store modes per adapter and read it from the adapter structure */
2880     if (Adapter == 0)
2881     {
2882         const struct wined3d_format *format = wined3d_get_format(&This->adapters[Adapter].gl_info, format_id);
2883         UINT format_bits = format->byte_count * CHAR_BIT;
2884         DEVMODEW DevModeW;
2885         int ModeIdx = 0;
2886         UINT i = 0;
2887         int j = 0;
2888
2889         ZeroMemory(&DevModeW, sizeof(DevModeW));
2890         DevModeW.dmSize = sizeof(DevModeW);
2891
2892         /* If we are filtering to a specific format (D3D9), then need to skip
2893            all unrelated modes, but if mode is irrelevant (D3D8), then we can
2894            just count through the ones with valid bit depths */
2895         while ((i<=Mode) && EnumDisplaySettingsExW(NULL, j++, &DevModeW, 0))
2896         {
2897             if (format_id == WINED3DFMT_UNKNOWN)
2898             {
2899                 /* This is for D3D8, do not enumerate P8 here */
2900                 if (DevModeW.dmBitsPerPel == 32 || DevModeW.dmBitsPerPel == 16) ++i;
2901             }
2902             else if (DevModeW.dmBitsPerPel == format_bits)
2903             {
2904                 ++i;
2905             }
2906         }
2907
2908         if (!i)
2909         {
2910             TRACE_(d3d_caps)("No modes found for format (%x - %s)\n", format_id, debug_d3dformat(format_id));
2911             return WINED3DERR_INVALIDCALL;
2912         }
2913         ModeIdx = j - 1;
2914
2915         /* Now get the display mode via the calculated index */
2916         if (EnumDisplaySettingsExW(NULL, ModeIdx, &DevModeW, 0)) {
2917             pMode->Width        = DevModeW.dmPelsWidth;
2918             pMode->Height       = DevModeW.dmPelsHeight;
2919             pMode->RefreshRate  = DEFAULT_REFRESH_RATE;
2920             if (DevModeW.dmFields & DM_DISPLAYFREQUENCY)
2921                 pMode->RefreshRate = DevModeW.dmDisplayFrequency;
2922
2923             if (format_id == WINED3DFMT_UNKNOWN)
2924                 pMode->Format = pixelformat_for_depth(DevModeW.dmBitsPerPel);
2925             else
2926                 pMode->Format = format_id;
2927         }
2928         else
2929         {
2930             TRACE_(d3d_caps)("Requested mode out of range %d\n", Mode);
2931             return WINED3DERR_INVALIDCALL;
2932         }
2933
2934         TRACE_(d3d_caps)("W %d H %d rr %d fmt (%x - %s) bpp %u\n", pMode->Width, pMode->Height,
2935                 pMode->RefreshRate, pMode->Format, debug_d3dformat(pMode->Format),
2936                 DevModeW.dmBitsPerPel);
2937
2938     }
2939     else
2940     {
2941         FIXME_(d3d_caps)("Adapter not primary display\n");
2942     }
2943
2944     return WINED3D_OK;
2945 }
2946
2947 static HRESULT WINAPI IWineD3DImpl_GetAdapterDisplayMode(IWineD3D *iface, UINT Adapter, WINED3DDISPLAYMODE *pMode)
2948 {
2949     TRACE("iface %p, adapter_idx %u, display_mode %p.\n", iface, Adapter, pMode);
2950
2951     if (!pMode || Adapter >= IWineD3D_GetAdapterCount(iface))
2952         return WINED3DERR_INVALIDCALL;
2953
2954     if (Adapter == 0) { /* Display */
2955         int bpp = 0;
2956         DEVMODEW DevModeW;
2957
2958         ZeroMemory(&DevModeW, sizeof(DevModeW));
2959         DevModeW.dmSize = sizeof(DevModeW);
2960
2961         EnumDisplaySettingsExW(NULL, ENUM_CURRENT_SETTINGS, &DevModeW, 0);
2962         pMode->Width        = DevModeW.dmPelsWidth;
2963         pMode->Height       = DevModeW.dmPelsHeight;
2964         bpp                 = DevModeW.dmBitsPerPel;
2965         pMode->RefreshRate  = DEFAULT_REFRESH_RATE;
2966         if (DevModeW.dmFields&DM_DISPLAYFREQUENCY)
2967         {
2968             pMode->RefreshRate = DevModeW.dmDisplayFrequency;
2969         }
2970
2971         pMode->Format = pixelformat_for_depth(bpp);
2972     } else {
2973         FIXME_(d3d_caps)("Adapter not primary display\n");
2974     }
2975
2976     TRACE_(d3d_caps)("returning w:%d, h:%d, ref:%d, fmt:%s\n", pMode->Width,
2977           pMode->Height, pMode->RefreshRate, debug_d3dformat(pMode->Format));
2978     return WINED3D_OK;
2979 }
2980
2981 /* NOTE: due to structure differences between dx8 and dx9 D3DADAPTER_IDENTIFIER,
2982    and fields being inserted in the middle, a new structure is used in place    */
2983 static HRESULT WINAPI IWineD3DImpl_GetAdapterIdentifier(IWineD3D *iface, UINT Adapter, DWORD Flags,
2984                                                    WINED3DADAPTER_IDENTIFIER* pIdentifier) {
2985     IWineD3DImpl *This = (IWineD3DImpl *)iface;
2986     struct wined3d_adapter *adapter;
2987     size_t len;
2988
2989     TRACE_(d3d_caps)("(%p}->(Adapter: %d, Flags: %x, pId=%p)\n", This, Adapter, Flags, pIdentifier);
2990
2991     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
2992         return WINED3DERR_INVALIDCALL;
2993     }
2994
2995     adapter = &This->adapters[Adapter];
2996
2997     /* Return the information requested */
2998     TRACE_(d3d_caps)("device/Vendor Name and Version detection using FillGLCaps\n");
2999
3000     if (pIdentifier->driver_size)
3001     {
3002         const char *name = adapter->driver_info.name;
3003         len = min(strlen(name), pIdentifier->driver_size - 1);
3004         memcpy(pIdentifier->driver, name, len);
3005         pIdentifier->driver[len] = '\0';
3006     }
3007
3008     if (pIdentifier->description_size)
3009     {
3010         const char *description = adapter->driver_info.description;
3011         len = min(strlen(description), pIdentifier->description_size - 1);
3012         memcpy(pIdentifier->description, description, len);
3013         pIdentifier->description[len] = '\0';
3014     }
3015
3016     /* Note that d3d8 doesn't supply a device name. */
3017     if (pIdentifier->device_name_size)
3018     {
3019         static const char *device_name = "\\\\.\\DISPLAY1"; /* FIXME: May depend on desktop? */
3020
3021         len = strlen(device_name);
3022         if (len >= pIdentifier->device_name_size)
3023         {
3024             ERR("Device name size too small.\n");
3025             return WINED3DERR_INVALIDCALL;
3026         }
3027
3028         memcpy(pIdentifier->device_name, device_name, len);
3029         pIdentifier->device_name[len] = '\0';
3030     }
3031
3032     pIdentifier->driver_version.u.HighPart = adapter->driver_info.version_high;
3033     pIdentifier->driver_version.u.LowPart = adapter->driver_info.version_low;
3034     pIdentifier->vendor_id = adapter->driver_info.vendor;
3035     pIdentifier->device_id = adapter->driver_info.device;
3036     pIdentifier->subsystem_id = 0;
3037     pIdentifier->revision = 0;
3038     memcpy(&pIdentifier->device_identifier, &IID_D3DDEVICE_D3DUID, sizeof(pIdentifier->device_identifier));
3039     pIdentifier->whql_level = (Flags & WINED3DENUM_NO_WHQL_LEVEL) ? 0 : 1;
3040     memcpy(&pIdentifier->adapter_luid, &adapter->luid, sizeof(pIdentifier->adapter_luid));
3041     pIdentifier->video_memory = adapter->TextureRam;
3042
3043     return WINED3D_OK;
3044 }
3045
3046 static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(const struct wined3d_gl_info *gl_info,
3047         const WineD3D_PixelFormat *cfg, const struct wined3d_format *format)
3048 {
3049     short redSize, greenSize, blueSize, alphaSize, colorBits;
3050
3051     if(!cfg)
3052         return FALSE;
3053
3054     /* Float formats need FBOs. If FBOs are used this function isn't called */
3055     if (format->Flags & WINED3DFMT_FLAG_FLOAT) return FALSE;
3056
3057     if(cfg->iPixelType == WGL_TYPE_RGBA_ARB) { /* Integer RGBA formats */
3058         if (!getColorBits(format, &redSize, &greenSize, &blueSize, &alphaSize, &colorBits))
3059         {
3060             ERR("Unable to check compatibility for format %s.\n", debug_d3dformat(format->id));
3061             return FALSE;
3062         }
3063
3064         if(cfg->redSize < redSize)
3065             return FALSE;
3066
3067         if(cfg->greenSize < greenSize)
3068             return FALSE;
3069
3070         if(cfg->blueSize < blueSize)
3071             return FALSE;
3072
3073         if(cfg->alphaSize < alphaSize)
3074             return FALSE;
3075
3076         return TRUE;
3077     }
3078
3079     /* Probably a RGBA_float or color index mode */
3080     return FALSE;
3081 }
3082
3083 static BOOL IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(const struct wined3d_gl_info *gl_info,
3084         const WineD3D_PixelFormat *cfg, const struct wined3d_format *format)
3085 {
3086     short depthSize, stencilSize;
3087     BOOL lockable = FALSE;
3088
3089     if(!cfg)
3090         return FALSE;
3091
3092     if (!getDepthStencilBits(format, &depthSize, &stencilSize))
3093     {
3094         ERR("Unable to check compatibility for format %s.\n", debug_d3dformat(format->id));
3095         return FALSE;
3096     }
3097
3098     /* Float formats need FBOs. If FBOs are used this function isn't called */
3099     if (format->Flags & WINED3DFMT_FLAG_FLOAT) return FALSE;
3100
3101     if ((format->id == WINED3DFMT_D16_LOCKABLE) || (format->id == WINED3DFMT_D32_FLOAT))
3102         lockable = TRUE;
3103
3104     /* On some modern cards like the Geforce8/9 GLX doesn't offer some dephthstencil formats which D3D9 reports.
3105      * We can safely report 'compatible' formats (e.g. D24 can be used for D16) as long as we aren't dealing with
3106      * a lockable format. This also helps D3D <= 7 as they expect D16 which isn't offered without this on Geforce8 cards. */
3107     if(!(cfg->depthSize == depthSize || (!lockable && cfg->depthSize > depthSize)))
3108         return FALSE;
3109
3110     /* Some cards like Intel i915 ones only offer D24S8 but lots of games also need a format without stencil, so
3111      * allow more stencil bits than requested. */
3112     if(cfg->stencilSize < stencilSize)
3113         return FALSE;
3114
3115     return TRUE;
3116 }
3117
3118 static HRESULT WINAPI IWineD3DImpl_CheckDepthStencilMatch(IWineD3D *iface,
3119         UINT Adapter, WINED3DDEVTYPE DeviceType, enum wined3d_format_id AdapterFormat,
3120         enum wined3d_format_id RenderTargetFormat, enum wined3d_format_id DepthStencilFormat)
3121 {
3122     IWineD3DImpl *This = (IWineD3DImpl *)iface;
3123     int nCfgs;
3124     const WineD3D_PixelFormat *cfgs;
3125     const struct wined3d_adapter *adapter;
3126     const struct wined3d_format *rt_format;
3127     const struct wined3d_format *ds_format;
3128     int it;
3129
3130     WARN_(d3d_caps)("(%p)-> (STUB) (Adptr:%d, DevType:(%x,%s), AdptFmt:(%x,%s), RendrTgtFmt:(%x,%s), DepthStencilFmt:(%x,%s))\n",
3131            This, Adapter,
3132            DeviceType, debug_d3ddevicetype(DeviceType),
3133            AdapterFormat, debug_d3dformat(AdapterFormat),
3134            RenderTargetFormat, debug_d3dformat(RenderTargetFormat),
3135            DepthStencilFormat, debug_d3dformat(DepthStencilFormat));
3136
3137     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
3138         TRACE("(%p) Failed: Atapter (%u) higher than supported adapters (%u) returning WINED3DERR_INVALIDCALL\n", This, Adapter, IWineD3D_GetAdapterCount(iface));
3139         return WINED3DERR_INVALIDCALL;
3140     }
3141
3142     adapter = &This->adapters[Adapter];
3143     rt_format = wined3d_get_format(&adapter->gl_info, RenderTargetFormat);
3144     ds_format = wined3d_get_format(&adapter->gl_info, DepthStencilFormat);
3145     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
3146     {
3147         if ((rt_format->Flags & WINED3DFMT_FLAG_RENDERTARGET)
3148                 && (ds_format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL)))
3149         {
3150             TRACE_(d3d_caps)("(%p) : Formats matched\n", This);
3151             return WINED3D_OK;
3152         }
3153     }
3154     else
3155     {
3156         cfgs = adapter->cfgs;
3157         nCfgs = adapter->nCfgs;
3158         for (it = 0; it < nCfgs; ++it)
3159         {
3160             if (IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info, &cfgs[it], rt_format))
3161             {
3162                 if (IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, &cfgs[it], ds_format))
3163                 {
3164                     TRACE_(d3d_caps)("(%p) : Formats matched\n", This);
3165                     return WINED3D_OK;
3166                 }
3167             }
3168         }
3169     }
3170     WARN_(d3d_caps)("unsupported format pair: %s and %s\n", debug_d3dformat(RenderTargetFormat), debug_d3dformat(DepthStencilFormat));
3171
3172     return WINED3DERR_NOTAVAILABLE;
3173 }
3174
3175 static HRESULT WINAPI IWineD3DImpl_CheckDeviceMultiSampleType(IWineD3D *iface, UINT Adapter,
3176         WINED3DDEVTYPE DeviceType, enum wined3d_format_id SurfaceFormat, BOOL Windowed,
3177         WINED3DMULTISAMPLE_TYPE MultiSampleType, DWORD *pQualityLevels)
3178 {
3179     IWineD3DImpl *This = (IWineD3DImpl *)iface;
3180     const struct wined3d_adapter *adapter;
3181     const struct wined3d_format *format;
3182
3183     TRACE_(d3d_caps)("(%p)-> (Adptr:%d, DevType:(%x,%s), SurfFmt:(%x,%s), Win?%d, MultiSamp:%x, pQual:%p)\n",
3184           This,
3185           Adapter,
3186           DeviceType, debug_d3ddevicetype(DeviceType),
3187           SurfaceFormat, debug_d3dformat(SurfaceFormat),
3188           Windowed,
3189           MultiSampleType,
3190           pQualityLevels);
3191
3192     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
3193         return WINED3DERR_INVALIDCALL;
3194     }
3195
3196     /* TODO: handle Windowed, add more quality levels */
3197
3198     if (WINED3DMULTISAMPLE_NONE == MultiSampleType) {
3199         if(pQualityLevels) *pQualityLevels = 1;
3200         return WINED3D_OK;
3201     }
3202
3203     /* By default multisampling is disabled right now as it causes issues
3204      * on some Nvidia driver versions and it doesn't work well in combination
3205      * with FBOs yet. */
3206     if(!wined3d_settings.allow_multisampling)
3207         return WINED3DERR_NOTAVAILABLE;
3208
3209     adapter = &This->adapters[Adapter];
3210     format = wined3d_get_format(&adapter->gl_info, SurfaceFormat);
3211     if (!format) return WINED3DERR_INVALIDCALL;
3212
3213     if (format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))
3214     {
3215         int i, nCfgs;
3216         const WineD3D_PixelFormat *cfgs;
3217
3218         cfgs = adapter->cfgs;
3219         nCfgs = adapter->nCfgs;
3220         for(i=0; i<nCfgs; i++) {
3221             if(cfgs[i].numSamples != MultiSampleType)
3222                 continue;
3223
3224             if (!IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, &cfgs[i], format))
3225                 continue;
3226
3227             TRACE("Found iPixelFormat=%d to support MultiSampleType=%d for format %s\n", cfgs[i].iPixelFormat, MultiSampleType, debug_d3dformat(SurfaceFormat));
3228
3229             if(pQualityLevels)
3230                 *pQualityLevels = 1; /* Guess at a value! */
3231             return WINED3D_OK;
3232         }
3233     }
3234     else if (format->Flags & WINED3DFMT_FLAG_RENDERTARGET)
3235     {
3236         short redSize, greenSize, blueSize, alphaSize, colorBits;
3237         int i, nCfgs;
3238         const WineD3D_PixelFormat *cfgs;
3239
3240         if (!getColorBits(format, &redSize, &greenSize, &blueSize, &alphaSize, &colorBits))
3241         {
3242             ERR("Unable to color bits for format %#x, can't check multisampling capability!\n", SurfaceFormat);
3243             return WINED3DERR_NOTAVAILABLE;
3244         }
3245
3246         cfgs = adapter->cfgs;
3247         nCfgs = adapter->nCfgs;
3248         for(i=0; i<nCfgs; i++) {
3249             if(cfgs[i].numSamples != MultiSampleType)
3250                 continue;
3251             if(cfgs[i].redSize != redSize)
3252                 continue;
3253             if(cfgs[i].greenSize != greenSize)
3254                 continue;
3255             if(cfgs[i].blueSize != blueSize)
3256                 continue;
3257             /* Not all drivers report alpha-less formats since they use 32-bit anyway, so accept alpha even if we didn't ask for it. */
3258             if(alphaSize && cfgs[i].alphaSize != alphaSize)
3259                 continue;
3260             if (cfgs[i].colorSize != (format->byte_count << 3))
3261                 continue;
3262
3263             TRACE("Found iPixelFormat=%d to support MultiSampleType=%d for format %s\n", cfgs[i].iPixelFormat, MultiSampleType, debug_d3dformat(SurfaceFormat));
3264
3265             if(pQualityLevels)
3266                 *pQualityLevels = 1; /* Guess at a value! */
3267             return WINED3D_OK;
3268         }
3269     }
3270     return WINED3DERR_NOTAVAILABLE;
3271 }
3272
3273 /* Check if we support bumpmapping for a format */
3274 static BOOL CheckBumpMapCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
3275 {
3276     /* Ask the fixed function pipeline implementation if it can deal
3277      * with the conversion. If we've got a GL extension giving native
3278      * support this will be an identity conversion. */
3279     return (format->Flags & WINED3DFMT_FLAG_BUMPMAP)
3280             && adapter->fragment_pipe->color_fixup_supported(format->color_fixup);
3281 }
3282
3283 /* Check if the given DisplayFormat + DepthStencilFormat combination is valid for the Adapter */
3284 static BOOL CheckDepthStencilCapability(struct wined3d_adapter *adapter,
3285         const struct wined3d_format *display_format, const struct wined3d_format *ds_format)
3286 {
3287     int it=0;
3288
3289     /* Only allow depth/stencil formats */
3290     if (!(ds_format->depth_size || ds_format->stencil_size)) return FALSE;
3291
3292     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
3293     {
3294         /* With FBOs WGL limitations do not apply, but the format needs to be FBO attachable */
3295         if (ds_format->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL)) return TRUE;
3296     }
3297     else
3298     {
3299         /* Walk through all WGL pixel formats to find a match */
3300         for (it = 0; it < adapter->nCfgs; ++it)
3301         {
3302             WineD3D_PixelFormat *cfg = &adapter->cfgs[it];
3303             if (IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info, cfg, display_format))
3304             {
3305                 if (IWineD3DImpl_IsPixelFormatCompatibleWithDepthFmt(&adapter->gl_info, cfg, ds_format))
3306                 {
3307                     return TRUE;
3308                 }
3309             }
3310         }
3311     }
3312
3313     return FALSE;
3314 }
3315
3316 static BOOL CheckFilterCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
3317 {
3318     /* The flags entry of a format contains the filtering capability */
3319     if (format->Flags & WINED3DFMT_FLAG_FILTERING) return TRUE;
3320
3321     return FALSE;
3322 }
3323
3324 /* Check the render target capabilities of a format */
3325 static BOOL CheckRenderTargetCapability(struct wined3d_adapter *adapter,
3326         const struct wined3d_format *adapter_format, const struct wined3d_format *check_format)
3327 {
3328     /* Filter out non-RT formats */
3329     if (!(check_format->Flags & WINED3DFMT_FLAG_RENDERTARGET)) return FALSE;
3330     if (wined3d_settings.offscreen_rendering_mode == ORM_BACKBUFFER)
3331     {
3332         WineD3D_PixelFormat *cfgs = adapter->cfgs;
3333         int it;
3334         short AdapterRed, AdapterGreen, AdapterBlue, AdapterAlpha, AdapterTotalSize;
3335         short CheckRed, CheckGreen, CheckBlue, CheckAlpha, CheckTotalSize;
3336
3337         getColorBits(adapter_format, &AdapterRed, &AdapterGreen, &AdapterBlue, &AdapterAlpha, &AdapterTotalSize);
3338         getColorBits(check_format, &CheckRed, &CheckGreen, &CheckBlue, &CheckAlpha, &CheckTotalSize);
3339
3340         /* In backbuffer mode the front and backbuffer share the same WGL pixelformat.
3341          * The format must match in RGB, alpha is allowed to be different. (Only the backbuffer can have alpha) */
3342         if(!((AdapterRed == CheckRed) && (AdapterGreen == CheckGreen) && (AdapterBlue == CheckBlue))) {
3343             TRACE_(d3d_caps)("[FAILED]\n");
3344             return FALSE;
3345         }
3346
3347         /* Check if there is a WGL pixel format matching the requirements, the format should also be window
3348          * drawable (not offscreen; e.g. Nvidia offers R5G6B5 for pbuffers even when X is running at 24bit) */
3349         for (it = 0; it < adapter->nCfgs; ++it)
3350         {
3351             if (cfgs[it].windowDrawable && IWineD3DImpl_IsPixelFormatCompatibleWithRenderFmt(&adapter->gl_info,
3352                     &cfgs[it], check_format))
3353             {
3354                 TRACE_(d3d_caps)("Pixel format %d is compatible with format %s.\n",
3355                         cfgs[it].iPixelFormat, debug_d3dformat(check_format->id));
3356                 return TRUE;
3357             }
3358         }
3359     }
3360     else if(wined3d_settings.offscreen_rendering_mode == ORM_FBO)
3361     {
3362         /* For now return TRUE for FBOs until we have some proper checks.
3363          * Note that this function will only be called when the format is around for texturing. */
3364         return TRUE;
3365     }
3366     return FALSE;
3367 }
3368
3369 static BOOL CheckSrgbReadCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
3370 {
3371     return adapter->gl_info.supported[EXT_TEXTURE_SRGB] && (format->Flags & WINED3DFMT_FLAG_SRGB_READ);
3372 }
3373
3374 static BOOL CheckSrgbWriteCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
3375 {
3376     /* Only offer SRGB writing on X8R8G8B8/A8R8G8B8 when we use ARB or GLSL shaders as we are
3377      * doing the color fixup in shaders.
3378      * Note Windows drivers (at least on the Geforce 8800) also offer this on R5G6B5. */
3379     if (format->Flags & WINED3DFMT_FLAG_SRGB_WRITE)
3380     {
3381         int vs_selected_mode;
3382         int ps_selected_mode;
3383         select_shader_mode(&adapter->gl_info, &ps_selected_mode, &vs_selected_mode);
3384
3385         if((ps_selected_mode == SHADER_ARB) || (ps_selected_mode == SHADER_GLSL)) {
3386             TRACE_(d3d_caps)("[OK]\n");
3387             return TRUE;
3388         }
3389     }
3390
3391     TRACE_(d3d_caps)("[FAILED] - sRGB writes not supported by format %s.\n", debug_d3dformat(format->id));
3392     return FALSE;
3393 }
3394
3395 /* Check if a format support blending in combination with pixel shaders */
3396 static BOOL CheckPostPixelShaderBlendingCapability(struct wined3d_adapter *adapter,
3397         const struct wined3d_format *format)
3398 {
3399     /* The flags entry of a format contains the post pixel shader blending capability */
3400     if (format->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING) return TRUE;
3401
3402     return FALSE;
3403 }
3404
3405 static BOOL CheckWrapAndMipCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
3406 {
3407     /* OpenGL supports mipmapping on all formats basically. Wrapping is unsupported,
3408      * but we have to report mipmapping so we cannot reject this flag. Tests show that
3409      * windows reports WRAPANDMIP on unfilterable surfaces as well, apparently to show
3410      * that wrapping is supported. The lack of filtering will sort out the mipmapping
3411      * capability anyway.
3412      *
3413      * For now lets report this on all formats, but in the future we may want to
3414      * restrict it to some should games need that
3415      */
3416     return TRUE;
3417 }
3418
3419 /* Check if a texture format is supported on the given adapter */
3420 static BOOL CheckTextureCapability(struct wined3d_adapter *adapter, const struct wined3d_format *format)
3421 {
3422     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
3423
3424     switch (format->id)
3425     {
3426         /*****
3427          *  supported: RGB(A) formats
3428          */
3429         case WINED3DFMT_B8G8R8_UNORM: /* Enable for dx7, blacklisted for 8 and 9 above */
3430         case WINED3DFMT_B8G8R8A8_UNORM:
3431         case WINED3DFMT_B8G8R8X8_UNORM:
3432         case WINED3DFMT_B5G6R5_UNORM:
3433         case WINED3DFMT_B5G5R5X1_UNORM:
3434         case WINED3DFMT_B5G5R5A1_UNORM:
3435         case WINED3DFMT_B4G4R4A4_UNORM:
3436         case WINED3DFMT_A8_UNORM:
3437         case WINED3DFMT_B4G4R4X4_UNORM:
3438         case WINED3DFMT_R8G8B8A8_UNORM:
3439         case WINED3DFMT_R8G8B8X8_UNORM:
3440         case WINED3DFMT_B10G10R10A2_UNORM:
3441         case WINED3DFMT_R10G10B10A2_UNORM:
3442         case WINED3DFMT_R16G16_UNORM:
3443             TRACE_(d3d_caps)("[OK]\n");
3444             return TRUE;
3445
3446         case WINED3DFMT_B2G3R3_UNORM:
3447             TRACE_(d3d_caps)("[FAILED] - Not supported on Windows\n");
3448             return FALSE;
3449
3450         /*****
3451          *  Not supported: Palettized
3452          *  Only some Geforce/Voodoo3/G400 cards offer 8-bit textures in case of <=Direct3D7.
3453          *  Since it is not widely available, don't offer it. Further no Windows driver offers
3454          *  WINED3DFMT_P8_UINT_A8_NORM, so don't offer it either.
3455          */
3456         case WINED3DFMT_P8_UINT:
3457         case WINED3DFMT_P8_UINT_A8_UNORM:
3458             return FALSE;
3459
3460         /*****
3461          *  Supported: (Alpha)-Luminance
3462          */
3463         case WINED3DFMT_L8_UNORM:
3464         case WINED3DFMT_L8A8_UNORM:
3465         case WINED3DFMT_L16_UNORM:
3466             TRACE_(d3d_caps)("[OK]\n");
3467             return TRUE;
3468
3469         /* Not supported on Windows, thus disabled */
3470         case WINED3DFMT_L4A4_UNORM:
3471             TRACE_(d3d_caps)("[FAILED] - not supported on windows\n");
3472             return FALSE;
3473
3474         /*****
3475          *  Supported: Depth/Stencil formats
3476          */
3477         case WINED3DFMT_D16_LOCKABLE:
3478         case WINED3DFMT_D16_UNORM:
3479         case WINED3DFMT_S1_UINT_D15_UNORM:
3480         case WINED3DFMT_X8D24_UNORM:
3481         case WINED3DFMT_S4X4_UINT_D24_UNORM:
3482         case WINED3DFMT_D24_UNORM_S8_UINT:
3483         case WINED3DFMT_S8_UINT_D24_FLOAT:
3484         case WINED3DFMT_D32_UNORM:
3485         case WINED3DFMT_D32_FLOAT:
3486             return TRUE;
3487
3488         case WINED3DFMT_INTZ:
3489             if (gl_info->supported[EXT_PACKED_DEPTH_STENCIL]
3490                     || gl_info->supported[ARB_FRAMEBUFFER_OBJECT])
3491                 return TRUE;
3492             return FALSE;
3493
3494         /*****
3495          *  Not supported everywhere(depends on GL_ATI_envmap_bumpmap or
3496          *  GL_NV_texture_shader). Emulated by shaders
3497          */
3498         case WINED3DFMT_R8G8_SNORM:
3499         case WINED3DFMT_R8G8_SNORM_L8X8_UNORM:
3500         case WINED3DFMT_R5G5_SNORM_L6_UNORM:
3501         case WINED3DFMT_R8G8B8A8_SNORM:
3502         case WINED3DFMT_R16G16_SNORM:
3503             /* Ask the shader backend if it can deal with the conversion. If
3504              * we've got a GL extension giving native support this will be an
3505              * identity conversion. */
3506             if (adapter->shader_backend->shader_color_fixup_supported(format->color_fixup))
3507             {
3508                 TRACE_(d3d_caps)("[OK]\n");
3509                 return TRUE;
3510             }
3511             TRACE_(d3d_caps)("[FAILED]\n");
3512             return FALSE;
3513
3514         case WINED3DFMT_DXT1:
3515         case WINED3DFMT_DXT2:
3516         case WINED3DFMT_DXT3:
3517         case WINED3DFMT_DXT4:
3518         case WINED3DFMT_DXT5:
3519             if (gl_info->supported[EXT_TEXTURE_COMPRESSION_S3TC])
3520             {
3521                 TRACE_(d3d_caps)("[OK]\n");
3522                 return TRUE;
3523             }
3524             TRACE_(d3d_caps)("[FAILED]\n");
3525             return FALSE;
3526
3527
3528         /*****
3529          *  Odd formats - not supported
3530          */
3531         case WINED3DFMT_VERTEXDATA:
3532         case WINED3DFMT_R16_UINT:
3533         case WINED3DFMT_R32_UINT:
3534         case WINED3DFMT_R16G16B16A16_SNORM:
3535         case WINED3DFMT_R10G10B10_SNORM_A2_UNORM:
3536         case WINED3DFMT_R10G11B11_SNORM:
3537             TRACE_(d3d_caps)("[FAILED]\n"); /* Enable when implemented */
3538             return FALSE;
3539
3540         /*****
3541          *  WINED3DFMT_R8G8_SNORM_Cx: Not supported right now
3542          */
3543         case WINED3DFMT_R8G8_SNORM_Cx:
3544             TRACE_(d3d_caps)("[FAILED]\n"); /* Enable when implemented */
3545             return FALSE;
3546
3547         /* YUV formats */
3548         case WINED3DFMT_UYVY:
3549         case WINED3DFMT_YUY2:
3550             if (gl_info->supported[APPLE_YCBCR_422])
3551             {
3552                 TRACE_(d3d_caps)("[OK]\n");
3553                 return TRUE;
3554             }
3555             TRACE_(d3d_caps)("[FAILED]\n");
3556             return FALSE;
3557         case WINED3DFMT_YV12:
3558             TRACE_(d3d_caps)("[FAILED]\n");
3559             return FALSE;
3560
3561             /* Not supported */
3562         case WINED3DFMT_R16G16B16A16_UNORM:
3563         case WINED3DFMT_B2G3R3A8_UNORM:
3564             TRACE_(d3d_caps)("[FAILED]\n"); /* Enable when implemented */
3565             return FALSE;
3566
3567             /* Floating point formats */
3568         case WINED3DFMT_R16_FLOAT:
3569         case WINED3DFMT_R16G16_FLOAT:
3570         case WINED3DFMT_R16G16B16A16_FLOAT:
3571             if (gl_info->supported[ARB_TEXTURE_FLOAT] && gl_info->supported[ARB_HALF_FLOAT_PIXEL])
3572             {
3573                 TRACE_(d3d_caps)("[OK]\n");
3574                 return TRUE;
3575             }
3576             TRACE_(d3d_caps)("[FAILED]\n");
3577             return FALSE;
3578
3579         case WINED3DFMT_R32_FLOAT:
3580         case WINED3DFMT_R32G32_FLOAT:
3581         case WINED3DFMT_R32G32B32A32_FLOAT:
3582             if (gl_info->supported[ARB_TEXTURE_FLOAT])
3583             {
3584                 TRACE_(d3d_caps)("[OK]\n");
3585                 return TRUE;
3586             }
3587             TRACE_(d3d_caps)("[FAILED]\n");
3588             return FALSE;
3589
3590         /* ATI instancing hack: Although ATI cards do not support Shader Model 3.0, they support
3591          * instancing. To query if the card supports instancing CheckDeviceFormat with the special format
3592          * MAKEFOURCC('I','N','S','T') is used. Should a (broken) app check for this provide a proper return value.
3593          * We can do instancing with all shader versions, but we need vertex shaders.
3594          *
3595          * Additionally applications have to set the D3DRS_POINTSIZE render state to MAKEFOURCC('I','N','S','T') once
3596          * to enable instancing. WineD3D doesn't need that and just ignores it.
3597          *
3598          * With Shader Model 3.0 capable cards Instancing 'just works' in Windows.
3599          */
3600         case WINED3DFMT_INST:
3601             TRACE("ATI Instancing check hack\n");
3602             if (gl_info->supported[ARB_VERTEX_PROGRAM] || gl_info->supported[ARB_VERTEX_SHADER])
3603             {
3604                 TRACE_(d3d_caps)("[OK]\n");
3605                 return TRUE;
3606             }
3607             TRACE_(d3d_caps)("[FAILED]\n");
3608             return FALSE;
3609
3610         /* Some weird FOURCC formats */
3611         case WINED3DFMT_R8G8_B8G8:
3612         case WINED3DFMT_G8R8_G8B8:
3613         case WINED3DFMT_MULTI2_ARGB8:
3614             TRACE_(d3d_caps)("[FAILED]\n");
3615             return FALSE;
3616
3617         /* Vendor specific formats */
3618         case WINED3DFMT_ATI2N:
3619             if (gl_info->supported[ATI_TEXTURE_COMPRESSION_3DC]
3620                     || gl_info->supported[ARB_TEXTURE_COMPRESSION_RGTC])
3621             {
3622                 if (adapter->shader_backend->shader_color_fixup_supported(format->color_fixup)
3623                         && adapter->fragment_pipe->color_fixup_supported(format->color_fixup))
3624                 {
3625                     TRACE_(d3d_caps)("[OK]\n");
3626                     return TRUE;
3627                 }
3628
3629                 TRACE_(d3d_caps)("[OK]\n");
3630                 return TRUE;
3631             }
3632             TRACE_(d3d_caps)("[FAILED]\n");
3633             return FALSE;
3634
3635         /* Depth bound test. To query if the card supports it CheckDeviceFormat with the special
3636          * format MAKEFOURCC('N','V','D','B') is used.
3637          * It is enabled by setting D3DRS_ADAPTIVETESS_X render state to MAKEFOURCC('N','V','D','B') and
3638          * then controlled by setting D3DRS_ADAPTIVETESS_Z (zMin) and D3DRS_ADAPTIVETESS_W (zMax)
3639          * to test value.
3640          */
3641         case WINED3DFMT_NVDB:
3642             if (gl_info->supported[EXT_DEPTH_BOUNDS_TEST])
3643             {
3644                 TRACE_(d3d_caps)("[OK]\n");
3645                 return TRUE;
3646             }
3647             TRACE_(d3d_caps)("[FAILED]\n");
3648             return FALSE;
3649
3650         case WINED3DFMT_NVHU:
3651         case WINED3DFMT_NVHS:
3652             /* These formats seem to be similar to the HILO formats in GL_NV_texture_shader. NVHU
3653              * is said to be GL_UNSIGNED_HILO16, NVHS GL_SIGNED_HILO16. Rumours say that d3d computes
3654              * a 3rd channel similarly to D3DFMT_CxV8U8(So NVHS could be called D3DFMT_CxV16U16).
3655              * ATI refused to support formats which can easilly be emulated with pixel shaders, so
3656              * Applications have to deal with not having NVHS and NVHU.
3657              */
3658             TRACE_(d3d_caps)("[FAILED]\n");
3659             return FALSE;
3660
3661         case WINED3DFMT_UNKNOWN:
3662             return FALSE;
3663
3664         default:
3665             ERR("Unhandled format %s.\n", debug_d3dformat(format->id));
3666             break;
3667     }
3668     return FALSE;
3669 }
3670
3671 static BOOL CheckSurfaceCapability(struct wined3d_adapter *adapter,
3672         const struct wined3d_format *adapter_format,
3673         const struct wined3d_format *check_format,
3674         WINED3DSURFTYPE SurfaceType)
3675 {
3676     if (SurfaceType == SURFACE_GDI)
3677     {
3678         switch (check_format->id)
3679         {
3680             case WINED3DFMT_B8G8R8_UNORM:
3681             case WINED3DFMT_B8G8R8A8_UNORM:
3682             case WINED3DFMT_B8G8R8X8_UNORM:
3683             case WINED3DFMT_B5G6R5_UNORM:
3684             case WINED3DFMT_B5G5R5X1_UNORM:
3685             case WINED3DFMT_B5G5R5A1_UNORM:
3686             case WINED3DFMT_B4G4R4A4_UNORM:
3687             case WINED3DFMT_B2G3R3_UNORM:
3688             case WINED3DFMT_A8_UNORM:
3689             case WINED3DFMT_B2G3R3A8_UNORM:
3690             case WINED3DFMT_B4G4R4X4_UNORM:
3691             case WINED3DFMT_R10G10B10A2_UNORM:
3692             case WINED3DFMT_R8G8B8A8_UNORM:
3693             case WINED3DFMT_R8G8B8X8_UNORM:
3694             case WINED3DFMT_R16G16_UNORM:
3695             case WINED3DFMT_B10G10R10A2_UNORM:
3696             case WINED3DFMT_R16G16B16A16_UNORM:
3697             case WINED3DFMT_P8_UINT:
3698                 TRACE_(d3d_caps)("[OK]\n");
3699                 return TRUE;
3700             default:
3701                 TRACE_(d3d_caps)("[FAILED] - not available on GDI surfaces\n");
3702                 return FALSE;
3703         }
3704     }
3705
3706     /* All format that are supported for textures are supported for surfaces as well */
3707     if (CheckTextureCapability(adapter, check_format)) return TRUE;
3708     /* All depth stencil formats are supported on surfaces */
3709     if (CheckDepthStencilCapability(adapter, adapter_format, check_format)) return TRUE;
3710
3711     /* If opengl can't process the format natively, the blitter may be able to convert it */
3712     if (adapter->blitter->blit_supported(&adapter->gl_info, BLIT_OP_BLIT,
3713             NULL, WINED3DPOOL_DEFAULT, 0, check_format,
3714             NULL, WINED3DPOOL_DEFAULT, 0, adapter_format))
3715     {
3716         TRACE_(d3d_caps)("[OK]\n");
3717         return TRUE;
3718     }
3719
3720     /* Reject other formats */
3721     TRACE_(d3d_caps)("[FAILED]\n");
3722     return FALSE;
3723 }
3724
3725 static BOOL CheckVertexTextureCapability(struct wined3d_adapter *adapter,
3726         const struct wined3d_format *format)
3727 {
3728     return adapter->gl_info.limits.vertex_samplers && (format->Flags & WINED3DFMT_FLAG_VTF);
3729 }
3730
3731 static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormat(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType,
3732         enum wined3d_format_id AdapterFormat, DWORD Usage, WINED3DRESOURCETYPE RType,
3733         enum wined3d_format_id CheckFormat, WINED3DSURFTYPE SurfaceType)
3734 {
3735     IWineD3DImpl *This = (IWineD3DImpl *)iface;
3736     struct wined3d_adapter *adapter = &This->adapters[Adapter];
3737     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
3738     const struct wined3d_format *format = wined3d_get_format(gl_info, CheckFormat);
3739     const struct wined3d_format *adapter_format = wined3d_get_format(gl_info, AdapterFormat);
3740     DWORD UsageCaps = 0;
3741
3742     TRACE_(d3d_caps)("(%p)-> (STUB) (Adptr:%d, DevType:(%u,%s), AdptFmt:(%u,%s), Use:(%u,%s,%s), ResTyp:(%x,%s), CheckFmt:(%u,%s))\n",
3743           This,
3744           Adapter,
3745           DeviceType, debug_d3ddevicetype(DeviceType),
3746           AdapterFormat, debug_d3dformat(AdapterFormat),
3747           Usage, debug_d3dusage(Usage), debug_d3dusagequery(Usage),
3748           RType, debug_d3dresourcetype(RType),
3749           CheckFormat, debug_d3dformat(CheckFormat));
3750
3751     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
3752         return WINED3DERR_INVALIDCALL;
3753     }
3754
3755     switch (RType)
3756     {
3757         case WINED3DRTYPE_CUBETEXTURE:
3758             /* Cubetexture allows:
3759              *      - WINED3DUSAGE_AUTOGENMIPMAP
3760              *      - WINED3DUSAGE_DEPTHSTENCIL
3761              *      - WINED3DUSAGE_DYNAMIC
3762              *      - WINED3DUSAGE_NONSECURE (d3d9ex)
3763              *      - WINED3DUSAGE_RENDERTARGET
3764              *      - WINED3DUSAGE_SOFTWAREPROCESSING
3765              *      - WINED3DUSAGE_QUERY_WRAPANDMIP
3766              */
3767             if (SurfaceType != SURFACE_OPENGL)
3768             {
3769                 TRACE_(d3d_caps)("[FAILED]\n");
3770                 return WINED3DERR_NOTAVAILABLE;
3771             }
3772
3773             if (!gl_info->supported[ARB_TEXTURE_CUBE_MAP])
3774             {
3775                 TRACE_(d3d_caps)("[FAILED] - No cube texture support\n");
3776                 return WINED3DERR_NOTAVAILABLE;
3777             }
3778
3779             if (!CheckTextureCapability(adapter, format))
3780             {
3781                 TRACE_(d3d_caps)("[FAILED] - Cube texture format not supported\n");
3782                 return WINED3DERR_NOTAVAILABLE;
3783             }
3784
3785             if (Usage & WINED3DUSAGE_AUTOGENMIPMAP)
3786             {
3787                 if (!gl_info->supported[SGIS_GENERATE_MIPMAP])
3788                     /* When autogenmipmap isn't around continue and return
3789                      * WINED3DOK_NOAUTOGEN instead of D3D_OK. */
3790                     TRACE_(d3d_caps)("[FAILED] - No autogenmipmap support, but continuing\n");
3791                 else
3792                     UsageCaps |= WINED3DUSAGE_AUTOGENMIPMAP;
3793             }
3794
3795             /* Always report dynamic locking. */
3796             if (Usage & WINED3DUSAGE_DYNAMIC)
3797                 UsageCaps |= WINED3DUSAGE_DYNAMIC;
3798
3799             if (Usage & WINED3DUSAGE_RENDERTARGET)
3800             {
3801                 if (!CheckRenderTargetCapability(adapter, adapter_format, format))
3802                 {
3803                     TRACE_(d3d_caps)("[FAILED] - No rendertarget support\n");
3804                     return WINED3DERR_NOTAVAILABLE;
3805                 }
3806                 UsageCaps |= WINED3DUSAGE_RENDERTARGET;
3807             }
3808
3809             /* Always report software processing. */
3810             if (Usage & WINED3DUSAGE_SOFTWAREPROCESSING)
3811                 UsageCaps |= WINED3DUSAGE_SOFTWAREPROCESSING;
3812
3813             if (Usage & WINED3DUSAGE_QUERY_FILTER)
3814             {
3815                 if (!CheckFilterCapability(adapter, format))
3816                 {
3817                     TRACE_(d3d_caps)("[FAILED] - No query filter support\n");
3818                     return WINED3DERR_NOTAVAILABLE;
3819                 }
3820                 UsageCaps |= WINED3DUSAGE_QUERY_FILTER;
3821             }
3822
3823             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
3824             {
3825                 if (!CheckPostPixelShaderBlendingCapability(adapter, format))
3826                 {
3827                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
3828                     return WINED3DERR_NOTAVAILABLE;
3829                 }
3830                 UsageCaps |= WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING;
3831             }
3832
3833             if (Usage & WINED3DUSAGE_QUERY_SRGBREAD)
3834             {
3835                 if (!CheckSrgbReadCapability(adapter, format))
3836                 {
3837                     TRACE_(d3d_caps)("[FAILED] - No query srgbread support\n");
3838                     return WINED3DERR_NOTAVAILABLE;
3839                 }
3840                 UsageCaps |= WINED3DUSAGE_QUERY_SRGBREAD;
3841             }
3842
3843             if (Usage & WINED3DUSAGE_QUERY_SRGBWRITE)
3844             {
3845                 if (!CheckSrgbWriteCapability(adapter, format))
3846                 {
3847                     TRACE_(d3d_caps)("[FAILED] - No query srgbwrite support\n");
3848                     return WINED3DERR_NOTAVAILABLE;
3849                 }
3850                 UsageCaps |= WINED3DUSAGE_QUERY_SRGBWRITE;
3851             }
3852
3853             if (Usage & WINED3DUSAGE_QUERY_VERTEXTEXTURE)
3854             {
3855                 if (!CheckVertexTextureCapability(adapter, format))
3856                 {
3857                     TRACE_(d3d_caps)("[FAILED] - No query vertextexture support\n");
3858                     return WINED3DERR_NOTAVAILABLE;
3859                 }
3860                 UsageCaps |= WINED3DUSAGE_QUERY_VERTEXTEXTURE;
3861             }
3862
3863             if (Usage & WINED3DUSAGE_QUERY_WRAPANDMIP)
3864             {
3865                 if (!CheckWrapAndMipCapability(adapter, format))
3866                 {
3867                     TRACE_(d3d_caps)("[FAILED] - No wrapping and mipmapping support\n");
3868                     return WINED3DERR_NOTAVAILABLE;
3869                 }
3870                 UsageCaps |= WINED3DUSAGE_QUERY_WRAPANDMIP;
3871             }
3872             break;
3873
3874         case WINED3DRTYPE_SURFACE:
3875             /* Surface allows:
3876              *      - WINED3DUSAGE_DEPTHSTENCIL
3877              *      - WINED3DUSAGE_NONSECURE (d3d9ex)
3878              *      - WINED3DUSAGE_RENDERTARGET
3879              */
3880             if (!CheckSurfaceCapability(adapter, adapter_format, format, SurfaceType))
3881             {
3882                 TRACE_(d3d_caps)("[FAILED] - Not supported for plain surfaces\n");
3883                 return WINED3DERR_NOTAVAILABLE;
3884             }
3885
3886             if (Usage & WINED3DUSAGE_DEPTHSTENCIL)
3887             {
3888                 if (!CheckDepthStencilCapability(adapter, adapter_format, format))
3889                 {
3890                     TRACE_(d3d_caps)("[FAILED] - No depthstencil support\n");
3891                     return WINED3DERR_NOTAVAILABLE;
3892                 }
3893                 UsageCaps |= WINED3DUSAGE_DEPTHSTENCIL;
3894             }
3895
3896             if (Usage & WINED3DUSAGE_RENDERTARGET)
3897             {
3898                 if (!CheckRenderTargetCapability(adapter, adapter_format, format))
3899                 {
3900                     TRACE_(d3d_caps)("[FAILED] - No rendertarget support\n");
3901                     return WINED3DERR_NOTAVAILABLE;
3902                 }
3903                 UsageCaps |= WINED3DUSAGE_RENDERTARGET;
3904             }
3905
3906             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
3907             {
3908                 if (!CheckPostPixelShaderBlendingCapability(adapter, format))
3909                 {
3910                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
3911                     return WINED3DERR_NOTAVAILABLE;
3912                 }
3913                 UsageCaps |= WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING;
3914             }
3915             break;
3916
3917         case WINED3DRTYPE_TEXTURE:
3918             /* Texture allows:
3919              *      - WINED3DUSAGE_AUTOGENMIPMAP
3920              *      - WINED3DUSAGE_DEPTHSTENCIL
3921              *      - WINED3DUSAGE_DMAP
3922              *      - WINED3DUSAGE_DYNAMIC
3923              *      - WINED3DUSAGE_NONSECURE (d3d9ex)
3924              *      - WINED3DUSAGE_RENDERTARGET
3925              *      - WINED3DUSAGE_SOFTWAREPROCESSING
3926              *      - WINED3DUSAGE_TEXTAPI (d3d9ex)
3927              *      - WINED3DUSAGE_QUERY_WRAPANDMIP
3928              */
3929             if (SurfaceType != SURFACE_OPENGL)
3930             {
3931                 TRACE_(d3d_caps)("[FAILED]\n");
3932                 return WINED3DERR_NOTAVAILABLE;
3933             }
3934
3935             if (!CheckTextureCapability(adapter, format))
3936             {
3937                 TRACE_(d3d_caps)("[FAILED] - Texture format not supported\n");
3938                 return WINED3DERR_NOTAVAILABLE;
3939             }
3940
3941             if (Usage & WINED3DUSAGE_AUTOGENMIPMAP)
3942             {
3943                 if (!gl_info->supported[SGIS_GENERATE_MIPMAP])
3944                     /* When autogenmipmap isn't around continue and return
3945                      * WINED3DOK_NOAUTOGEN instead of D3D_OK. */
3946                     TRACE_(d3d_caps)("[FAILED] - No autogenmipmap support, but continuing\n");
3947                 else
3948                     UsageCaps |= WINED3DUSAGE_AUTOGENMIPMAP;
3949             }
3950
3951             /* Always report dynamic locking. */
3952             if (Usage & WINED3DUSAGE_DYNAMIC)
3953                 UsageCaps |= WINED3DUSAGE_DYNAMIC;
3954
3955             if (Usage & WINED3DUSAGE_RENDERTARGET)
3956             {
3957                 if (!CheckRenderTargetCapability(adapter, adapter_format, format))
3958                 {
3959                     TRACE_(d3d_caps)("[FAILED] - No rendertarget support\n");
3960                     return WINED3DERR_NOTAVAILABLE;
3961                 }
3962                 UsageCaps |= WINED3DUSAGE_RENDERTARGET;
3963             }
3964
3965             /* Always report software processing. */
3966             if (Usage & WINED3DUSAGE_SOFTWAREPROCESSING)
3967                 UsageCaps |= WINED3DUSAGE_SOFTWAREPROCESSING;
3968
3969             if (Usage & WINED3DUSAGE_QUERY_FILTER)
3970             {
3971                 if (!CheckFilterCapability(adapter, format))
3972                 {
3973                     TRACE_(d3d_caps)("[FAILED] - No query filter support\n");
3974                     return WINED3DERR_NOTAVAILABLE;
3975                 }
3976                 UsageCaps |= WINED3DUSAGE_QUERY_FILTER;
3977             }
3978
3979             if (Usage & WINED3DUSAGE_QUERY_LEGACYBUMPMAP)
3980             {
3981                 if (!CheckBumpMapCapability(adapter, format))
3982                 {
3983                     TRACE_(d3d_caps)("[FAILED] - No legacy bumpmap support\n");
3984                     return WINED3DERR_NOTAVAILABLE;
3985                 }
3986                 UsageCaps |= WINED3DUSAGE_QUERY_LEGACYBUMPMAP;
3987             }
3988
3989             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
3990             {
3991                 if (!CheckPostPixelShaderBlendingCapability(adapter, format))
3992                 {
3993                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
3994                     return WINED3DERR_NOTAVAILABLE;
3995                 }
3996                 UsageCaps |= WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING;
3997             }
3998
3999             if (Usage & WINED3DUSAGE_QUERY_SRGBREAD)
4000             {
4001                 if (!CheckSrgbReadCapability(adapter, format))
4002                 {
4003                     TRACE_(d3d_caps)("[FAILED] - No query srgbread support\n");
4004                     return WINED3DERR_NOTAVAILABLE;
4005                 }
4006                 UsageCaps |= WINED3DUSAGE_QUERY_SRGBREAD;
4007             }
4008
4009             if (Usage & WINED3DUSAGE_QUERY_SRGBWRITE)
4010             {
4011                 if (!CheckSrgbWriteCapability(adapter, format))
4012                 {
4013                     TRACE_(d3d_caps)("[FAILED] - No query srgbwrite support\n");
4014                     return WINED3DERR_NOTAVAILABLE;
4015                 }
4016                 UsageCaps |= WINED3DUSAGE_QUERY_SRGBWRITE;
4017             }
4018
4019             if (Usage & WINED3DUSAGE_QUERY_VERTEXTEXTURE)
4020             {
4021                 if (!CheckVertexTextureCapability(adapter, format))
4022                 {
4023                     TRACE_(d3d_caps)("[FAILED] - No query vertextexture support\n");
4024                     return WINED3DERR_NOTAVAILABLE;
4025                 }
4026                 UsageCaps |= WINED3DUSAGE_QUERY_VERTEXTEXTURE;
4027             }
4028
4029             if (Usage & WINED3DUSAGE_QUERY_WRAPANDMIP)
4030             {
4031                 if (!CheckWrapAndMipCapability(adapter, format))
4032                 {
4033                     TRACE_(d3d_caps)("[FAILED] - No wrapping and mipmapping support\n");
4034                     return WINED3DERR_NOTAVAILABLE;
4035                 }
4036                 UsageCaps |= WINED3DUSAGE_QUERY_WRAPANDMIP;
4037             }
4038
4039             if (Usage & WINED3DUSAGE_DEPTHSTENCIL)
4040             {
4041                 if (!CheckDepthStencilCapability(adapter, adapter_format, format))
4042                 {
4043                     TRACE_(d3d_caps)("[FAILED] - No depth stencil support\n");
4044                     return WINED3DERR_NOTAVAILABLE;
4045                 }
4046                 if ((format->Flags & WINED3DFMT_FLAG_SHADOW) && !gl_info->supported[ARB_SHADOW])
4047                 {
4048                     TRACE_(d3d_caps)("[FAILED] - No shadow sampler support.\n");
4049                     return WINED3DERR_NOTAVAILABLE;
4050                 }
4051                 UsageCaps |= WINED3DUSAGE_DEPTHSTENCIL;
4052             }
4053             break;
4054
4055         case WINED3DRTYPE_VOLUMETEXTURE:
4056         case WINED3DRTYPE_VOLUME:
4057             /* Volume is to VolumeTexture what Surface is to Texture, but its
4058              * usage caps are not documented. Most driver seem to offer
4059              * (nearly) the same on Volume and VolumeTexture, so do that too.
4060              *
4061              * Volumetexture allows:
4062              *      - D3DUSAGE_DYNAMIC
4063              *      - D3DUSAGE_NONSECURE (d3d9ex)
4064              *      - D3DUSAGE_SOFTWAREPROCESSING
4065              *      - D3DUSAGE_QUERY_WRAPANDMIP
4066              */
4067             if (SurfaceType != SURFACE_OPENGL)
4068             {
4069                 TRACE_(d3d_caps)("[FAILED]\n");
4070                 return WINED3DERR_NOTAVAILABLE;
4071             }
4072
4073             if (!gl_info->supported[EXT_TEXTURE3D])
4074             {
4075                 TRACE_(d3d_caps)("[FAILED] - No volume texture support\n");
4076                 return WINED3DERR_NOTAVAILABLE;
4077             }
4078
4079             if (!CheckTextureCapability(adapter, format))
4080             {
4081                 TRACE_(d3d_caps)("[FAILED] - Format not supported\n");
4082                 return WINED3DERR_NOTAVAILABLE;
4083             }
4084
4085             /* Filter formats that need conversion; For one part, this
4086              * conversion is unimplemented, and volume textures are huge, so
4087              * it would be a big performance hit. Unless we hit an application
4088              * needing one of those formats, don't advertize them to avoid
4089              * leading applications into temptation. The windows drivers don't
4090              * support most of those formats on volumes anyway, except for
4091              * WINED3DFMT_R32_FLOAT. */
4092             switch (CheckFormat)
4093             {
4094                 case WINED3DFMT_P8_UINT:
4095                 case WINED3DFMT_L4A4_UNORM:
4096                 case WINED3DFMT_R32_FLOAT:
4097                 case WINED3DFMT_R16_FLOAT:
4098                 case WINED3DFMT_R8G8_SNORM_L8X8_UNORM:
4099                 case WINED3DFMT_R5G5_SNORM_L6_UNORM:
4100                 case WINED3DFMT_R16G16_UNORM:
4101                     TRACE_(d3d_caps)("[FAILED] - No converted formats on volumes\n");
4102                     return WINED3DERR_NOTAVAILABLE;
4103
4104                 case WINED3DFMT_R8G8B8A8_SNORM:
4105                 case WINED3DFMT_R16G16_SNORM:
4106                     if (!gl_info->supported[NV_TEXTURE_SHADER])
4107                     {
4108                         TRACE_(d3d_caps)("[FAILED] - No converted formats on volumes\n");
4109                         return WINED3DERR_NOTAVAILABLE;
4110                     }
4111                     break;
4112
4113                 case WINED3DFMT_R8G8_SNORM:
4114                     if (!gl_info->supported[NV_TEXTURE_SHADER])
4115                     {
4116                         TRACE_(d3d_caps)("[FAILED] - No converted formats on volumes\n");
4117                         return WINED3DERR_NOTAVAILABLE;
4118                     }
4119                     break;
4120
4121                 case WINED3DFMT_DXT1:
4122                 case WINED3DFMT_DXT2:
4123                 case WINED3DFMT_DXT3:
4124                 case WINED3DFMT_DXT4:
4125                 case WINED3DFMT_DXT5:
4126                     /* The GL_EXT_texture_compression_s3tc spec requires that
4127                      * loading an s3tc compressed texture results in an error.
4128                      * While the D3D refrast does support s3tc volumes, at
4129                      * least the nvidia windows driver does not, so we're free
4130                      * not to support this format. */
4131                     TRACE_(d3d_caps)("[FAILED] - DXTn does not support 3D textures\n");
4132                     return WINED3DERR_NOTAVAILABLE;
4133
4134                 default:
4135                     /* Do nothing, continue with checking the format below */
4136                     break;
4137             }
4138
4139             /* Always report dynamic locking. */
4140             if (Usage & WINED3DUSAGE_DYNAMIC)
4141                 UsageCaps |= WINED3DUSAGE_DYNAMIC;
4142
4143             /* Always report software processing. */
4144             if (Usage & WINED3DUSAGE_SOFTWAREPROCESSING)
4145                 UsageCaps |= WINED3DUSAGE_SOFTWAREPROCESSING;
4146
4147             if (Usage & WINED3DUSAGE_QUERY_FILTER)
4148             {
4149                 if (!CheckFilterCapability(adapter, format))
4150                 {
4151                     TRACE_(d3d_caps)("[FAILED] - No query filter support\n");
4152                     return WINED3DERR_NOTAVAILABLE;
4153                 }
4154                 UsageCaps |= WINED3DUSAGE_QUERY_FILTER;
4155             }
4156
4157             if (Usage & WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING)
4158             {
4159                 if (!CheckPostPixelShaderBlendingCapability(adapter, format))
4160                 {
4161                     TRACE_(d3d_caps)("[FAILED] - No query post pixelshader blending support\n");
4162                     return WINED3DERR_NOTAVAILABLE;
4163                 }
4164                 UsageCaps |= WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING;
4165             }
4166
4167             if (Usage & WINED3DUSAGE_QUERY_SRGBREAD)
4168             {
4169                 if (!CheckSrgbReadCapability(adapter, format))
4170                 {
4171                     TRACE_(d3d_caps)("[FAILED] - No query srgbread support\n");
4172                     return WINED3DERR_NOTAVAILABLE;
4173                 }
4174                 UsageCaps |= WINED3DUSAGE_QUERY_SRGBREAD;
4175             }
4176
4177             if (Usage & WINED3DUSAGE_QUERY_SRGBWRITE)
4178             {
4179                 if (!CheckSrgbWriteCapability(adapter, format))
4180                 {
4181                     TRACE_(d3d_caps)("[FAILED] - No query srgbwrite support\n");
4182                     return WINED3DERR_NOTAVAILABLE;
4183                 }
4184                 UsageCaps |= WINED3DUSAGE_QUERY_SRGBWRITE;
4185             }
4186
4187             if (Usage & WINED3DUSAGE_QUERY_VERTEXTEXTURE)
4188             {
4189                 if (!CheckVertexTextureCapability(adapter, format))
4190                 {
4191                     TRACE_(d3d_caps)("[FAILED] - No query vertextexture support\n");
4192                     return WINED3DERR_NOTAVAILABLE;
4193                 }
4194                 UsageCaps |= WINED3DUSAGE_QUERY_VERTEXTEXTURE;
4195             }
4196
4197             if (Usage & WINED3DUSAGE_QUERY_WRAPANDMIP)
4198             {
4199                 if (!CheckWrapAndMipCapability(adapter, format))
4200                 {
4201                     TRACE_(d3d_caps)("[FAILED] - No wrapping and mipmapping support\n");
4202                     return WINED3DERR_NOTAVAILABLE;
4203                 }
4204                 UsageCaps |= WINED3DUSAGE_QUERY_WRAPANDMIP;
4205             }
4206             break;
4207
4208         default:
4209             FIXME_(d3d_caps)("Unhandled resource type %s.\n", debug_d3dresourcetype(RType));
4210             return WINED3DERR_NOTAVAILABLE;
4211     }
4212
4213     /* When the UsageCaps exactly matches Usage return WINED3D_OK except for
4214      * the situation in which WINED3DUSAGE_AUTOGENMIPMAP isn't around, then
4215      * WINED3DOK_NOAUTOGEN is returned if all the other usage flags match. */
4216     if (UsageCaps == Usage)
4217         return WINED3D_OK;
4218     if (UsageCaps == (Usage & ~WINED3DUSAGE_AUTOGENMIPMAP))
4219         return WINED3DOK_NOAUTOGEN;
4220
4221     TRACE_(d3d_caps)("[FAILED] - Usage %#x requested for CheckFormat %s and RType %s but only %#x is available\n",
4222             Usage, debug_d3dformat(CheckFormat), debug_d3dresourcetype(RType), UsageCaps);
4223
4224     return WINED3DERR_NOTAVAILABLE;
4225 }
4226
4227 static HRESULT WINAPI IWineD3DImpl_CheckDeviceFormatConversion(IWineD3D *iface, UINT adapter_idx,
4228         WINED3DDEVTYPE device_type, enum wined3d_format_id src_format, enum wined3d_format_id dst_format)
4229 {
4230     FIXME("iface %p, adapter_idx %u, device_type %s, src_format %s, dst_format %s stub!\n",
4231             iface, adapter_idx, debug_d3ddevicetype(device_type), debug_d3dformat(src_format),
4232             debug_d3dformat(dst_format));
4233
4234     return WINED3D_OK;
4235 }
4236
4237 static HRESULT WINAPI IWineD3DImpl_CheckDeviceType(IWineD3D *iface, UINT adapter_idx, WINED3DDEVTYPE device_type,
4238         enum wined3d_format_id display_format, enum wined3d_format_id backbuffer_format, BOOL windowed)
4239 {
4240     UINT mode_count;
4241     HRESULT hr;
4242
4243     TRACE("iface %p, adapter_idx %u, device_type %s, display_format %s, backbuffer_format %s, windowed %#x.\n",
4244             iface, adapter_idx, debug_d3ddevicetype(device_type), debug_d3dformat(display_format),
4245             debug_d3dformat(backbuffer_format), windowed);
4246
4247     if (adapter_idx >= IWineD3D_GetAdapterCount(iface))
4248     {
4249         WARN_(d3d_caps)("adapter_idx >= IWineD3D_GetAdapterCount(iface), returning WINED3DERR_INVALIDCALL\n");
4250         return WINED3DERR_INVALIDCALL;
4251     }
4252
4253     /* The task of this function is to check whether a certain display / backbuffer format
4254      * combination is available on the given adapter. In fullscreen mode microsoft specified
4255      * that the display format shouldn't provide alpha and that ignoring alpha the backbuffer
4256      * and display format should match exactly.
4257      * In windowed mode format conversion can occur and this depends on the driver. When format
4258      * conversion is done, this function should nevertheless fail and applications need to use
4259      * CheckDeviceFormatConversion.
4260      * At the moment we assume that fullscreen and windowed have the same capabilities. */
4261
4262     /* There are only 4 display formats. */
4263     if (!(display_format == WINED3DFMT_B5G6R5_UNORM
4264             || display_format == WINED3DFMT_B5G5R5X1_UNORM
4265             || display_format == WINED3DFMT_B8G8R8X8_UNORM
4266             || display_format == WINED3DFMT_B10G10R10A2_UNORM))
4267     {
4268         TRACE_(d3d_caps)("Format %s is not supported as display format.\n", debug_d3dformat(display_format));
4269         return WINED3DERR_NOTAVAILABLE;
4270     }
4271
4272     /* If the requested display format is not available, don't continue. */
4273     mode_count = IWineD3DImpl_GetAdapterModeCount(iface, adapter_idx, display_format);
4274     if (!mode_count)
4275     {
4276         TRACE_(d3d_caps)("No available modes for display format %s.\n", debug_d3dformat(display_format));
4277         return WINED3DERR_NOTAVAILABLE;
4278     }
4279
4280     /* Windowed mode allows you to specify WINED3DFMT_UNKNOWN for the backbuffer format,
4281      * it means 'reuse' the display format for the backbuffer. */
4282     if (!windowed && backbuffer_format == WINED3DFMT_UNKNOWN)
4283     {
4284         TRACE_(d3d_caps)("backbuffer_format WINED3FMT_UNKNOWN only available in windowed mode.\n");
4285         return WINED3DERR_NOTAVAILABLE;
4286     }
4287
4288     /* In FULLSCREEN mode WINED3DFMT_B5G6R5_UNORM can only be mixed with
4289      * backbuffer format WINED3DFMT_B5G6R5_UNORM. */
4290     if (display_format == WINED3DFMT_B5G6R5_UNORM && backbuffer_format != WINED3DFMT_B5G6R5_UNORM)
4291     {
4292         TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
4293                 debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
4294         return WINED3DERR_NOTAVAILABLE;
4295     }
4296
4297     /* In FULLSCREEN mode WINED3DFMT_B5G5R5X1_UNORM can only be mixed with
4298      * backbuffer formats WINED3DFMT_B5G5R5X1_UNORM and
4299      * WINED3DFMT_B5G5R5A1_UNORM. */
4300     if (display_format == WINED3DFMT_B5G5R5X1_UNORM
4301             && !(backbuffer_format == WINED3DFMT_B5G5R5X1_UNORM || backbuffer_format == WINED3DFMT_B5G5R5A1_UNORM))
4302     {
4303         TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
4304                 debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
4305         return WINED3DERR_NOTAVAILABLE;
4306     }
4307
4308     /* In FULLSCREEN mode WINED3DFMT_B8G8R8X8_UNORM can only be mixed with
4309      * backbuffer formats WINED3DFMT_B8G8R8X8_UNORM and
4310      * WINED3DFMT_B8G8R8A8_UNORM. */
4311     if (display_format == WINED3DFMT_B8G8R8X8_UNORM
4312             && !(backbuffer_format == WINED3DFMT_B8G8R8X8_UNORM || backbuffer_format == WINED3DFMT_B8G8R8A8_UNORM))
4313     {
4314         TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
4315                 debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
4316         return WINED3DERR_NOTAVAILABLE;
4317     }
4318
4319     /* WINED3DFMT_B10G10R10A2_UNORM is only allowed in fullscreen mode and it
4320      * can only be mixed with backbuffer format WINED3DFMT_B10G10R10A2_UNORM. */
4321     if (display_format == WINED3DFMT_B10G10R10A2_UNORM
4322             && (backbuffer_format != WINED3DFMT_B10G10R10A2_UNORM || windowed))
4323     {
4324         TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
4325                 debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
4326         return WINED3DERR_NOTAVAILABLE;
4327     }
4328
4329     /* Use CheckDeviceFormat to see if the backbuffer_format is usable with the given display_format */
4330     hr = IWineD3DImpl_CheckDeviceFormat(iface, adapter_idx, device_type, display_format,
4331             WINED3DUSAGE_RENDERTARGET, WINED3DRTYPE_SURFACE, backbuffer_format, SURFACE_OPENGL);
4332     if (FAILED(hr))
4333         TRACE_(d3d_caps)("Unsupported display/backbuffer format combination %s / %s.\n",
4334                 debug_d3dformat(display_format), debug_d3dformat(backbuffer_format));
4335
4336     return hr;
4337 }
4338
4339 /* Note: d3d8 passes in a pointer to a D3DCAPS8 structure, which is a true
4340       subset of a D3DCAPS9 structure. However, it has to come via a void *
4341       as the d3d8 interface cannot import the d3d9 header                  */
4342 static HRESULT WINAPI IWineD3DImpl_GetDeviceCaps(IWineD3D *iface, UINT Adapter, WINED3DDEVTYPE DeviceType, WINED3DCAPS* pCaps) {
4343
4344     IWineD3DImpl    *This = (IWineD3DImpl *)iface;
4345     struct wined3d_adapter *adapter = &This->adapters[Adapter];
4346     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
4347     int vs_selected_mode;
4348     int ps_selected_mode;
4349     struct shader_caps shader_caps;
4350     struct fragment_caps fragment_caps;
4351     DWORD ckey_caps, blit_caps, fx_caps, pal_caps;
4352
4353     TRACE_(d3d_caps)("(%p)->(Adptr:%d, DevType: %x, pCaps: %p)\n", This, Adapter, DeviceType, pCaps);
4354
4355     if (Adapter >= IWineD3D_GetAdapterCount(iface)) {
4356         return WINED3DERR_INVALIDCALL;
4357     }
4358
4359     select_shader_mode(&adapter->gl_info, &ps_selected_mode, &vs_selected_mode);
4360
4361     /* ------------------------------------------------
4362        The following fields apply to both d3d8 and d3d9
4363        ------------------------------------------------ */
4364     pCaps->DeviceType              = (DeviceType == WINED3DDEVTYPE_HAL) ? WINED3DDEVTYPE_HAL : WINED3DDEVTYPE_REF;  /* Not quite true, but use h/w supported by opengl I suppose */
4365     pCaps->AdapterOrdinal          = Adapter;
4366
4367     pCaps->Caps                    = 0;
4368     pCaps->Caps2                   = WINED3DCAPS2_CANRENDERWINDOWED |
4369                                      WINED3DCAPS2_FULLSCREENGAMMA |
4370                                      WINED3DCAPS2_DYNAMICTEXTURES;
4371     if (gl_info->supported[SGIS_GENERATE_MIPMAP])
4372     {
4373         pCaps->Caps2 |= WINED3DCAPS2_CANAUTOGENMIPMAP;
4374     }
4375
4376     pCaps->Caps3                   = WINED3DCAPS3_ALPHA_FULLSCREEN_FLIP_OR_DISCARD |
4377                                      WINED3DCAPS3_COPY_TO_VIDMEM                   |
4378                                      WINED3DCAPS3_COPY_TO_SYSTEMMEM;
4379
4380     pCaps->PresentationIntervals   = WINED3DPRESENT_INTERVAL_IMMEDIATE  |
4381                                      WINED3DPRESENT_INTERVAL_ONE;
4382
4383     pCaps->CursorCaps              = WINED3DCURSORCAPS_COLOR            |
4384                                      WINED3DCURSORCAPS_LOWRES;
4385
4386     pCaps->DevCaps                 = WINED3DDEVCAPS_FLOATTLVERTEX       |
4387                                      WINED3DDEVCAPS_EXECUTESYSTEMMEMORY |
4388                                      WINED3DDEVCAPS_TLVERTEXSYSTEMMEMORY|
4389                                      WINED3DDEVCAPS_TLVERTEXVIDEOMEMORY |
4390                                      WINED3DDEVCAPS_DRAWPRIMTLVERTEX    |
4391                                      WINED3DDEVCAPS_HWTRANSFORMANDLIGHT |
4392                                      WINED3DDEVCAPS_EXECUTEVIDEOMEMORY  |
4393                                      WINED3DDEVCAPS_PUREDEVICE          |
4394                                      WINED3DDEVCAPS_HWRASTERIZATION     |
4395                                      WINED3DDEVCAPS_TEXTUREVIDEOMEMORY  |
4396                                      WINED3DDEVCAPS_TEXTURESYSTEMMEMORY |
4397                                      WINED3DDEVCAPS_CANRENDERAFTERFLIP  |
4398                                      WINED3DDEVCAPS_DRAWPRIMITIVES2     |
4399                                      WINED3DDEVCAPS_DRAWPRIMITIVES2EX   |
4400                                      WINED3DDEVCAPS_RTPATCHES;
4401
4402     pCaps->PrimitiveMiscCaps       = WINED3DPMISCCAPS_CULLNONE              |
4403                                      WINED3DPMISCCAPS_CULLCCW               |
4404                                      WINED3DPMISCCAPS_CULLCW                |
4405                                      WINED3DPMISCCAPS_COLORWRITEENABLE      |
4406                                      WINED3DPMISCCAPS_CLIPTLVERTS           |
4407                                      WINED3DPMISCCAPS_CLIPPLANESCALEDPOINTS |
4408                                      WINED3DPMISCCAPS_MASKZ                 |
4409                                      WINED3DPMISCCAPS_BLENDOP               |
4410                                      WINED3DPMISCCAPS_MRTPOSTPIXELSHADERBLENDING;
4411                                     /* TODO:
4412                                         WINED3DPMISCCAPS_NULLREFERENCE
4413                                         WINED3DPMISCCAPS_FOGANDSPECULARALPHA
4414                                         WINED3DPMISCCAPS_MRTINDEPENDENTBITDEPTHS
4415                                         WINED3DPMISCCAPS_FOGVERTEXCLAMPED */
4416
4417     if (gl_info->supported[EXT_BLEND_EQUATION_SEPARATE] && gl_info->supported[EXT_BLEND_FUNC_SEPARATE])
4418         pCaps->PrimitiveMiscCaps |= WINED3DPMISCCAPS_SEPARATEALPHABLEND;
4419     if (gl_info->supported[EXT_DRAW_BUFFERS2])
4420         pCaps->PrimitiveMiscCaps |= WINED3DPMISCCAPS_INDEPENDENTWRITEMASKS;
4421
4422     pCaps->RasterCaps              = WINED3DPRASTERCAPS_DITHER    |
4423                                      WINED3DPRASTERCAPS_PAT       |
4424                                      WINED3DPRASTERCAPS_WFOG      |
4425                                      WINED3DPRASTERCAPS_ZFOG      |
4426                                      WINED3DPRASTERCAPS_FOGVERTEX |
4427                                      WINED3DPRASTERCAPS_FOGTABLE  |
4428                                      WINED3DPRASTERCAPS_STIPPLE   |
4429                                      WINED3DPRASTERCAPS_SUBPIXEL  |
4430                                      WINED3DPRASTERCAPS_ZTEST     |
4431                                      WINED3DPRASTERCAPS_SCISSORTEST   |
4432                                      WINED3DPRASTERCAPS_SLOPESCALEDEPTHBIAS |
4433                                      WINED3DPRASTERCAPS_DEPTHBIAS;
4434
4435     if (gl_info->supported[EXT_TEXTURE_FILTER_ANISOTROPIC])
4436     {
4437         pCaps->RasterCaps |= WINED3DPRASTERCAPS_ANISOTROPY    |
4438                              WINED3DPRASTERCAPS_ZBIAS         |
4439                              WINED3DPRASTERCAPS_MIPMAPLODBIAS;
4440     }
4441     if (gl_info->supported[NV_FOG_DISTANCE])
4442     {
4443         pCaps->RasterCaps         |= WINED3DPRASTERCAPS_FOGRANGE;
4444     }
4445                         /* FIXME Add:
4446                            WINED3DPRASTERCAPS_COLORPERSPECTIVE
4447                            WINED3DPRASTERCAPS_STRETCHBLTMULTISAMPLE
4448                            WINED3DPRASTERCAPS_ANTIALIASEDGES
4449                            WINED3DPRASTERCAPS_ZBUFFERLESSHSR
4450                            WINED3DPRASTERCAPS_WBUFFER */
4451
4452     pCaps->ZCmpCaps = WINED3DPCMPCAPS_ALWAYS       |
4453                       WINED3DPCMPCAPS_EQUAL        |
4454                       WINED3DPCMPCAPS_GREATER      |
4455                       WINED3DPCMPCAPS_GREATEREQUAL |
4456                       WINED3DPCMPCAPS_LESS         |
4457                       WINED3DPCMPCAPS_LESSEQUAL    |
4458                       WINED3DPCMPCAPS_NEVER        |
4459                       WINED3DPCMPCAPS_NOTEQUAL;
4460
4461     pCaps->SrcBlendCaps  = WINED3DPBLENDCAPS_BOTHINVSRCALPHA |
4462                            WINED3DPBLENDCAPS_BOTHSRCALPHA    |
4463                            WINED3DPBLENDCAPS_DESTALPHA       |
4464                            WINED3DPBLENDCAPS_DESTCOLOR       |
4465                            WINED3DPBLENDCAPS_INVDESTALPHA    |
4466                            WINED3DPBLENDCAPS_INVDESTCOLOR    |
4467                            WINED3DPBLENDCAPS_INVSRCALPHA     |
4468                            WINED3DPBLENDCAPS_INVSRCCOLOR     |
4469                            WINED3DPBLENDCAPS_ONE             |
4470                            WINED3DPBLENDCAPS_SRCALPHA        |
4471                            WINED3DPBLENDCAPS_SRCALPHASAT     |
4472                            WINED3DPBLENDCAPS_SRCCOLOR        |
4473                            WINED3DPBLENDCAPS_ZERO;
4474
4475     pCaps->DestBlendCaps = WINED3DPBLENDCAPS_DESTALPHA       |
4476                            WINED3DPBLENDCAPS_DESTCOLOR       |
4477                            WINED3DPBLENDCAPS_INVDESTALPHA    |
4478                            WINED3DPBLENDCAPS_INVDESTCOLOR    |
4479                            WINED3DPBLENDCAPS_INVSRCALPHA     |
4480                            WINED3DPBLENDCAPS_INVSRCCOLOR     |
4481                            WINED3DPBLENDCAPS_ONE             |
4482                            WINED3DPBLENDCAPS_SRCALPHA        |
4483                            WINED3DPBLENDCAPS_SRCCOLOR        |
4484                            WINED3DPBLENDCAPS_ZERO;
4485     /* NOTE: WINED3DPBLENDCAPS_SRCALPHASAT is not supported as dest blend factor,
4486      * according to the glBlendFunc manpage
4487      *
4488      * WINED3DPBLENDCAPS_BOTHINVSRCALPHA and WINED3DPBLENDCAPS_BOTHSRCALPHA are
4489      * legacy settings for srcblend only
4490      */
4491
4492     if (gl_info->supported[EXT_BLEND_COLOR])
4493     {
4494         pCaps->SrcBlendCaps |= WINED3DPBLENDCAPS_BLENDFACTOR;
4495         pCaps->DestBlendCaps |= WINED3DPBLENDCAPS_BLENDFACTOR;
4496     }
4497
4498
4499     pCaps->AlphaCmpCaps = WINED3DPCMPCAPS_ALWAYS       |
4500                           WINED3DPCMPCAPS_EQUAL        |
4501                           WINED3DPCMPCAPS_GREATER      |
4502                           WINED3DPCMPCAPS_GREATEREQUAL |
4503                           WINED3DPCMPCAPS_LESS         |
4504                           WINED3DPCMPCAPS_LESSEQUAL    |
4505                           WINED3DPCMPCAPS_NEVER        |
4506                           WINED3DPCMPCAPS_NOTEQUAL;
4507
4508     pCaps->ShadeCaps     = WINED3DPSHADECAPS_SPECULARGOURAUDRGB |
4509                            WINED3DPSHADECAPS_COLORGOURAUDRGB    |
4510                            WINED3DPSHADECAPS_ALPHAFLATBLEND     |
4511                            WINED3DPSHADECAPS_ALPHAGOURAUDBLEND  |
4512                            WINED3DPSHADECAPS_COLORFLATRGB       |
4513                            WINED3DPSHADECAPS_FOGFLAT            |
4514                            WINED3DPSHADECAPS_FOGGOURAUD         |
4515                            WINED3DPSHADECAPS_SPECULARFLATRGB;
4516
4517     pCaps->TextureCaps =  WINED3DPTEXTURECAPS_ALPHA              |
4518                           WINED3DPTEXTURECAPS_ALPHAPALETTE       |
4519                           WINED3DPTEXTURECAPS_TRANSPARENCY       |
4520                           WINED3DPTEXTURECAPS_BORDER             |
4521                           WINED3DPTEXTURECAPS_MIPMAP             |
4522                           WINED3DPTEXTURECAPS_PROJECTED          |
4523                           WINED3DPTEXTURECAPS_PERSPECTIVE;
4524
4525     if (!gl_info->supported[ARB_TEXTURE_NON_POWER_OF_TWO])
4526     {
4527         pCaps->TextureCaps |= WINED3DPTEXTURECAPS_POW2 |
4528                               WINED3DPTEXTURECAPS_NONPOW2CONDITIONAL;
4529     }
4530
4531     if (gl_info->supported[EXT_TEXTURE3D])
4532     {
4533         pCaps->TextureCaps |=  WINED3DPTEXTURECAPS_VOLUMEMAP      |
4534                                WINED3DPTEXTURECAPS_MIPVOLUMEMAP   |
4535                                WINED3DPTEXTURECAPS_VOLUMEMAP_POW2;
4536     }
4537
4538     if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
4539     {
4540         pCaps->TextureCaps |= WINED3DPTEXTURECAPS_CUBEMAP     |
4541                               WINED3DPTEXTURECAPS_MIPCUBEMAP    |
4542                               WINED3DPTEXTURECAPS_CUBEMAP_POW2;
4543
4544     }
4545
4546     pCaps->TextureFilterCaps = WINED3DPTFILTERCAPS_MAGFLINEAR       |
4547                                WINED3DPTFILTERCAPS_MAGFPOINT        |
4548                                WINED3DPTFILTERCAPS_MINFLINEAR       |
4549                                WINED3DPTFILTERCAPS_MINFPOINT        |
4550                                WINED3DPTFILTERCAPS_MIPFLINEAR       |
4551                                WINED3DPTFILTERCAPS_MIPFPOINT        |
4552                                WINED3DPTFILTERCAPS_LINEAR           |
4553                                WINED3DPTFILTERCAPS_LINEARMIPLINEAR  |
4554                                WINED3DPTFILTERCAPS_LINEARMIPNEAREST |
4555                                WINED3DPTFILTERCAPS_MIPLINEAR        |
4556                                WINED3DPTFILTERCAPS_MIPNEAREST       |
4557                                WINED3DPTFILTERCAPS_NEAREST;
4558
4559     if (gl_info->supported[EXT_TEXTURE_FILTER_ANISOTROPIC])
4560     {
4561         pCaps->TextureFilterCaps |= WINED3DPTFILTERCAPS_MAGFANISOTROPIC |
4562                                     WINED3DPTFILTERCAPS_MINFANISOTROPIC;
4563     }
4564
4565     if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
4566     {
4567         pCaps->CubeTextureFilterCaps = WINED3DPTFILTERCAPS_MAGFLINEAR       |
4568                                        WINED3DPTFILTERCAPS_MAGFPOINT        |
4569                                        WINED3DPTFILTERCAPS_MINFLINEAR       |
4570                                        WINED3DPTFILTERCAPS_MINFPOINT        |
4571                                        WINED3DPTFILTERCAPS_MIPFLINEAR       |
4572                                        WINED3DPTFILTERCAPS_MIPFPOINT        |
4573                                        WINED3DPTFILTERCAPS_LINEAR           |
4574                                        WINED3DPTFILTERCAPS_LINEARMIPLINEAR  |
4575                                        WINED3DPTFILTERCAPS_LINEARMIPNEAREST |
4576                                        WINED3DPTFILTERCAPS_MIPLINEAR        |
4577                                        WINED3DPTFILTERCAPS_MIPNEAREST       |
4578                                        WINED3DPTFILTERCAPS_NEAREST;
4579
4580         if (gl_info->supported[EXT_TEXTURE_FILTER_ANISOTROPIC])
4581         {
4582             pCaps->CubeTextureFilterCaps |= WINED3DPTFILTERCAPS_MAGFANISOTROPIC |
4583                                             WINED3DPTFILTERCAPS_MINFANISOTROPIC;
4584         }
4585     } else
4586         pCaps->CubeTextureFilterCaps = 0;
4587
4588     if (gl_info->supported[EXT_TEXTURE3D])
4589     {
4590         pCaps->VolumeTextureFilterCaps = WINED3DPTFILTERCAPS_MAGFLINEAR       |
4591                                          WINED3DPTFILTERCAPS_MAGFPOINT        |
4592                                          WINED3DPTFILTERCAPS_MINFLINEAR       |
4593                                          WINED3DPTFILTERCAPS_MINFPOINT        |
4594                                          WINED3DPTFILTERCAPS_MIPFLINEAR       |
4595                                          WINED3DPTFILTERCAPS_MIPFPOINT        |
4596                                          WINED3DPTFILTERCAPS_LINEAR           |
4597                                          WINED3DPTFILTERCAPS_LINEARMIPLINEAR  |
4598                                          WINED3DPTFILTERCAPS_LINEARMIPNEAREST |
4599                                          WINED3DPTFILTERCAPS_MIPLINEAR        |
4600                                          WINED3DPTFILTERCAPS_MIPNEAREST       |
4601                                          WINED3DPTFILTERCAPS_NEAREST;
4602     } else
4603         pCaps->VolumeTextureFilterCaps = 0;
4604
4605     pCaps->TextureAddressCaps =  WINED3DPTADDRESSCAPS_INDEPENDENTUV |
4606                                  WINED3DPTADDRESSCAPS_CLAMP  |
4607                                  WINED3DPTADDRESSCAPS_WRAP;
4608
4609     if (gl_info->supported[ARB_TEXTURE_BORDER_CLAMP])
4610     {
4611         pCaps->TextureAddressCaps |= WINED3DPTADDRESSCAPS_BORDER;
4612     }
4613     if (gl_info->supported[ARB_TEXTURE_MIRRORED_REPEAT])
4614     {
4615         pCaps->TextureAddressCaps |= WINED3DPTADDRESSCAPS_MIRROR;
4616     }
4617     if (gl_info->supported[ATI_TEXTURE_MIRROR_ONCE])
4618     {
4619         pCaps->TextureAddressCaps |= WINED3DPTADDRESSCAPS_MIRRORONCE;
4620     }
4621
4622     if (gl_info->supported[EXT_TEXTURE3D])
4623     {
4624         pCaps->VolumeTextureAddressCaps =  WINED3DPTADDRESSCAPS_INDEPENDENTUV |
4625                                            WINED3DPTADDRESSCAPS_CLAMP  |
4626                                            WINED3DPTADDRESSCAPS_WRAP;
4627         if (gl_info->supported[ARB_TEXTURE_BORDER_CLAMP])
4628         {
4629             pCaps->VolumeTextureAddressCaps |= WINED3DPTADDRESSCAPS_BORDER;
4630         }
4631         if (gl_info->supported[ARB_TEXTURE_MIRRORED_REPEAT])
4632         {
4633             pCaps->VolumeTextureAddressCaps |= WINED3DPTADDRESSCAPS_MIRROR;
4634         }
4635         if (gl_info->supported[ATI_TEXTURE_MIRROR_ONCE])
4636         {
4637             pCaps->VolumeTextureAddressCaps |= WINED3DPTADDRESSCAPS_MIRRORONCE;
4638         }
4639     } else
4640         pCaps->VolumeTextureAddressCaps = 0;
4641
4642     pCaps->LineCaps = WINED3DLINECAPS_TEXTURE       |
4643                       WINED3DLINECAPS_ZTEST         |
4644                       WINED3DLINECAPS_BLEND         |
4645                       WINED3DLINECAPS_ALPHACMP      |
4646                       WINED3DLINECAPS_FOG;
4647     /* WINED3DLINECAPS_ANTIALIAS is not supported on Windows, and dx and gl seem to have a different
4648      * idea how generating the smoothing alpha values works; the result is different
4649      */
4650
4651     pCaps->MaxTextureWidth = gl_info->limits.texture_size;
4652     pCaps->MaxTextureHeight = gl_info->limits.texture_size;
4653
4654     if (gl_info->supported[EXT_TEXTURE3D])
4655         pCaps->MaxVolumeExtent = gl_info->limits.texture3d_size;
4656     else
4657         pCaps->MaxVolumeExtent = 0;
4658
4659     pCaps->MaxTextureRepeat = 32768;
4660     pCaps->MaxTextureAspectRatio = gl_info->limits.texture_size;
4661     pCaps->MaxVertexW = 1.0f;
4662
4663     pCaps->GuardBandLeft = 0.0f;
4664     pCaps->GuardBandTop = 0.0f;
4665     pCaps->GuardBandRight = 0.0f;
4666     pCaps->GuardBandBottom = 0.0f;
4667
4668     pCaps->ExtentsAdjust = 0.0f;
4669
4670     pCaps->StencilCaps =  WINED3DSTENCILCAPS_DECRSAT |
4671                           WINED3DSTENCILCAPS_INCRSAT |
4672                           WINED3DSTENCILCAPS_INVERT  |
4673                           WINED3DSTENCILCAPS_KEEP    |
4674                           WINED3DSTENCILCAPS_REPLACE |
4675                           WINED3DSTENCILCAPS_ZERO;
4676     if (gl_info->supported[EXT_STENCIL_WRAP])
4677     {
4678         pCaps->StencilCaps |= WINED3DSTENCILCAPS_DECR  |
4679                               WINED3DSTENCILCAPS_INCR;
4680     }
4681     if (gl_info->supported[EXT_STENCIL_TWO_SIDE] || gl_info->supported[ATI_SEPARATE_STENCIL])
4682     {
4683         pCaps->StencilCaps |= WINED3DSTENCILCAPS_TWOSIDED;
4684     }
4685
4686     pCaps->FVFCaps = WINED3DFVFCAPS_PSIZE | 0x0008; /* 8 texture coords */
4687
4688     pCaps->MaxUserClipPlanes = gl_info->limits.clipplanes;
4689     pCaps->MaxActiveLights = gl_info->limits.lights;
4690
4691     pCaps->MaxVertexBlendMatrices = gl_info->limits.blends;
4692     pCaps->MaxVertexBlendMatrixIndex   = 0;
4693
4694     pCaps->MaxAnisotropy = gl_info->limits.anisotropy;
4695     pCaps->MaxPointSize = gl_info->limits.pointsize_max;
4696
4697
4698     /* FIXME: Add D3DVTXPCAPS_TWEENING, D3DVTXPCAPS_TEXGEN_SPHEREMAP */
4699     pCaps->VertexProcessingCaps = WINED3DVTXPCAPS_DIRECTIONALLIGHTS |
4700                                   WINED3DVTXPCAPS_MATERIALSOURCE7   |
4701                                   WINED3DVTXPCAPS_POSITIONALLIGHTS  |
4702                                   WINED3DVTXPCAPS_LOCALVIEWER       |
4703                                   WINED3DVTXPCAPS_VERTEXFOG         |
4704                                   WINED3DVTXPCAPS_TEXGEN;
4705
4706     pCaps->MaxPrimitiveCount   = 0xFFFFF; /* For now set 2^20-1 which is used by most >=Geforce3/Radeon8500 cards */
4707     pCaps->MaxVertexIndex      = 0xFFFFF;
4708     pCaps->MaxStreams          = MAX_STREAMS;
4709     pCaps->MaxStreamStride     = 1024;
4710
4711     /* d3d9.dll sets D3DDEVCAPS2_CAN_STRETCHRECT_FROM_TEXTURES here because StretchRects is implemented in d3d9 */
4712     pCaps->DevCaps2                          = WINED3DDEVCAPS2_STREAMOFFSET |
4713                                                WINED3DDEVCAPS2_VERTEXELEMENTSCANSHARESTREAMOFFSET;
4714     pCaps->MaxNpatchTessellationLevel        = 0;
4715     pCaps->MasterAdapterOrdinal              = 0;
4716     pCaps->AdapterOrdinalInGroup             = 0;
4717     pCaps->NumberOfAdaptersInGroup           = 1;
4718
4719     pCaps->NumSimultaneousRTs = gl_info->limits.buffers;
4720
4721     pCaps->StretchRectFilterCaps             = WINED3DPTFILTERCAPS_MINFPOINT  |
4722                                                 WINED3DPTFILTERCAPS_MAGFPOINT  |
4723                                                 WINED3DPTFILTERCAPS_MINFLINEAR |
4724                                                 WINED3DPTFILTERCAPS_MAGFLINEAR;
4725     pCaps->VertexTextureFilterCaps           = 0;
4726
4727     adapter->shader_backend->shader_get_caps(&adapter->gl_info, &shader_caps);
4728     adapter->fragment_pipe->get_caps(&adapter->gl_info, &fragment_caps);
4729
4730     /* Add shader misc caps. Only some of them belong to the shader parts of the pipeline */
4731     pCaps->PrimitiveMiscCaps |= fragment_caps.PrimitiveMiscCaps;
4732
4733     /* This takes care for disabling vertex shader or pixel shader caps while leaving the other one enabled.
4734      * Ignore shader model capabilities if disabled in config
4735      */
4736     if(vs_selected_mode == SHADER_NONE) {
4737         TRACE_(d3d_caps)("Vertex shader disabled in config, reporting version 0.0\n");
4738         pCaps->VertexShaderVersion          = WINED3DVS_VERSION(0,0);
4739         pCaps->MaxVertexShaderConst         = 0;
4740     } else {
4741         pCaps->VertexShaderVersion          = shader_caps.VertexShaderVersion;
4742         pCaps->MaxVertexShaderConst         = shader_caps.MaxVertexShaderConst;
4743     }
4744
4745     if(ps_selected_mode == SHADER_NONE) {
4746         TRACE_(d3d_caps)("Pixel shader disabled in config, reporting version 0.0\n");
4747         pCaps->PixelShaderVersion           = WINED3DPS_VERSION(0,0);
4748         pCaps->PixelShader1xMaxValue        = 0.0f;
4749     } else {
4750         pCaps->PixelShaderVersion           = shader_caps.PixelShaderVersion;
4751         pCaps->PixelShader1xMaxValue        = shader_caps.PixelShader1xMaxValue;
4752     }
4753
4754     pCaps->TextureOpCaps                    = fragment_caps.TextureOpCaps;
4755     pCaps->MaxTextureBlendStages            = fragment_caps.MaxTextureBlendStages;
4756     pCaps->MaxSimultaneousTextures          = fragment_caps.MaxSimultaneousTextures;
4757
4758     /* The following caps are shader specific, but they are things we cannot detect, or which
4759      * are the same among all shader models. So to avoid code duplication set the shader version
4760      * specific, but otherwise constant caps here
4761      */
4762     if(pCaps->VertexShaderVersion == WINED3DVS_VERSION(3,0)) {
4763         /* Where possible set the caps based on OpenGL extensions and if they aren't set (in case of software rendering)
4764         use the VS 3.0 from MSDN or else if there's OpenGL spec use a hardcoded value minimum VS3.0 value. */
4765         pCaps->VS20Caps.Caps                     = WINED3DVS20CAPS_PREDICATION;
4766         pCaps->VS20Caps.DynamicFlowControlDepth  = WINED3DVS20_MAX_DYNAMICFLOWCONTROLDEPTH; /* VS 3.0 requires MAX_DYNAMICFLOWCONTROLDEPTH (24) */
4767         pCaps->VS20Caps.NumTemps = max(32, adapter->gl_info.limits.arb_vs_temps);
4768         pCaps->VS20Caps.StaticFlowControlDepth   = WINED3DVS20_MAX_STATICFLOWCONTROLDEPTH ; /* level of nesting in loops / if-statements; VS 3.0 requires MAX (4) */
4769
4770         pCaps->MaxVShaderInstructionsExecuted    = 65535; /* VS 3.0 needs at least 65535, some cards even use 2^32-1 */
4771         pCaps->MaxVertexShader30InstructionSlots = max(512, adapter->gl_info.limits.arb_vs_instructions);
4772     }
4773     else if (pCaps->VertexShaderVersion == WINED3DVS_VERSION(2,0))
4774     {
4775         pCaps->VS20Caps.Caps                     = 0;
4776         pCaps->VS20Caps.DynamicFlowControlDepth  = WINED3DVS20_MIN_DYNAMICFLOWCONTROLDEPTH;
4777         pCaps->VS20Caps.NumTemps = max(12, adapter->gl_info.limits.arb_vs_temps);
4778         pCaps->VS20Caps.StaticFlowControlDepth   = 1;
4779
4780         pCaps->MaxVShaderInstructionsExecuted    = 65535;
4781         pCaps->MaxVertexShader30InstructionSlots = 0;
4782     } else { /* VS 1.x */
4783         pCaps->VS20Caps.Caps                     = 0;
4784         pCaps->VS20Caps.DynamicFlowControlDepth  = 0;
4785         pCaps->VS20Caps.NumTemps                 = 0;
4786         pCaps->VS20Caps.StaticFlowControlDepth   = 0;
4787
4788         pCaps->MaxVShaderInstructionsExecuted    = 0;
4789         pCaps->MaxVertexShader30InstructionSlots = 0;
4790     }
4791
4792     if(pCaps->PixelShaderVersion == WINED3DPS_VERSION(3,0)) {
4793         /* Where possible set the caps based on OpenGL extensions and if they aren't set (in case of software rendering)
4794         use the PS 3.0 from MSDN or else if there's OpenGL spec use a hardcoded value minimum PS 3.0 value. */
4795
4796         /* Caps is more or less undocumented on MSDN but it appears to be used for PS20Caps based on results from R9600/FX5900/Geforce6800 cards from Windows */
4797         pCaps->PS20Caps.Caps                     = WINED3DPS20CAPS_ARBITRARYSWIZZLE     |
4798                 WINED3DPS20CAPS_GRADIENTINSTRUCTIONS |
4799                 WINED3DPS20CAPS_PREDICATION          |
4800                 WINED3DPS20CAPS_NODEPENDENTREADLIMIT |
4801                 WINED3DPS20CAPS_NOTEXINSTRUCTIONLIMIT;
4802         pCaps->PS20Caps.DynamicFlowControlDepth  = WINED3DPS20_MAX_DYNAMICFLOWCONTROLDEPTH; /* PS 3.0 requires MAX_DYNAMICFLOWCONTROLDEPTH (24) */
4803         pCaps->PS20Caps.NumTemps = max(32, adapter->gl_info.limits.arb_ps_temps);
4804         pCaps->PS20Caps.StaticFlowControlDepth   = WINED3DPS20_MAX_STATICFLOWCONTROLDEPTH; /* PS 3.0 requires MAX_STATICFLOWCONTROLDEPTH (4) */
4805         pCaps->PS20Caps.NumInstructionSlots      = WINED3DPS20_MAX_NUMINSTRUCTIONSLOTS; /* PS 3.0 requires MAX_NUMINSTRUCTIONSLOTS (512) */
4806
4807         pCaps->MaxPShaderInstructionsExecuted    = 65535;
4808         pCaps->MaxPixelShader30InstructionSlots = max(WINED3DMIN30SHADERINSTRUCTIONS,
4809                 adapter->gl_info.limits.arb_ps_instructions);
4810     }
4811     else if(pCaps->PixelShaderVersion == WINED3DPS_VERSION(2,0))
4812     {
4813         /* Below we assume PS2.0 specs, not extended 2.0a(GeforceFX)/2.0b(Radeon R3xx) ones */
4814         pCaps->PS20Caps.Caps                     = 0;
4815         pCaps->PS20Caps.DynamicFlowControlDepth  = 0; /* WINED3DVS20_MIN_DYNAMICFLOWCONTROLDEPTH = 0 */
4816         pCaps->PS20Caps.NumTemps = max(12, adapter->gl_info.limits.arb_ps_temps);
4817         pCaps->PS20Caps.StaticFlowControlDepth   = WINED3DPS20_MIN_STATICFLOWCONTROLDEPTH; /* Minimum: 1 */
4818         pCaps->PS20Caps.NumInstructionSlots      = WINED3DPS20_MIN_NUMINSTRUCTIONSLOTS; /* Minimum number (64 ALU + 32 Texture), a GeforceFX uses 512 */
4819
4820         pCaps->MaxPShaderInstructionsExecuted    = 512; /* Minimum value, a GeforceFX uses 1024 */
4821         pCaps->MaxPixelShader30InstructionSlots  = 0;
4822     } else { /* PS 1.x */
4823         pCaps->PS20Caps.Caps                     = 0;
4824         pCaps->PS20Caps.DynamicFlowControlDepth  = 0;
4825         pCaps->PS20Caps.NumTemps                 = 0;
4826         pCaps->PS20Caps.StaticFlowControlDepth   = 0;
4827         pCaps->PS20Caps.NumInstructionSlots      = 0;
4828
4829         pCaps->MaxPShaderInstructionsExecuted    = 0;
4830         pCaps->MaxPixelShader30InstructionSlots  = 0;
4831     }
4832
4833     if(pCaps->VertexShaderVersion >= WINED3DVS_VERSION(2,0)) {
4834         /* OpenGL supports all the formats below, perhaps not always
4835          * without conversion, but it supports them.
4836          * Further GLSL doesn't seem to have an official unsigned type so
4837          * don't advertise it yet as I'm not sure how we handle it.
4838          * We might need to add some clamping in the shader engine to
4839          * support it.
4840          * TODO: WINED3DDTCAPS_USHORT2N, WINED3DDTCAPS_USHORT4N, WINED3DDTCAPS_UDEC3, WINED3DDTCAPS_DEC3N */
4841         pCaps->DeclTypes = WINED3DDTCAPS_UBYTE4    |
4842                            WINED3DDTCAPS_UBYTE4N   |
4843                            WINED3DDTCAPS_SHORT2N   |
4844                            WINED3DDTCAPS_SHORT4N;
4845         if (gl_info->supported[ARB_HALF_FLOAT_VERTEX])
4846         {
4847             pCaps->DeclTypes |= WINED3DDTCAPS_FLOAT16_2 |
4848                                 WINED3DDTCAPS_FLOAT16_4;
4849         }
4850     } else
4851         pCaps->DeclTypes                         = 0;
4852
4853     /* Set DirectDraw helper Caps */
4854     ckey_caps =                         WINEDDCKEYCAPS_DESTBLT              |
4855                                         WINEDDCKEYCAPS_SRCBLT;
4856     fx_caps =                           WINEDDFXCAPS_BLTALPHA               |
4857                                         WINEDDFXCAPS_BLTMIRRORLEFTRIGHT     |
4858                                         WINEDDFXCAPS_BLTMIRRORUPDOWN        |
4859                                         WINEDDFXCAPS_BLTROTATION90          |
4860                                         WINEDDFXCAPS_BLTSHRINKX             |
4861                                         WINEDDFXCAPS_BLTSHRINKXN            |
4862                                         WINEDDFXCAPS_BLTSHRINKY             |
4863                                         WINEDDFXCAPS_BLTSHRINKXN            |
4864                                         WINEDDFXCAPS_BLTSTRETCHX            |
4865                                         WINEDDFXCAPS_BLTSTRETCHXN           |
4866                                         WINEDDFXCAPS_BLTSTRETCHY            |
4867                                         WINEDDFXCAPS_BLTSTRETCHYN;
4868     blit_caps =                         WINEDDCAPS_BLT                      |
4869                                         WINEDDCAPS_BLTCOLORFILL             |
4870                                         WINEDDCAPS_BLTDEPTHFILL             |
4871                                         WINEDDCAPS_BLTSTRETCH               |
4872                                         WINEDDCAPS_CANBLTSYSMEM             |
4873                                         WINEDDCAPS_CANCLIP                  |
4874                                         WINEDDCAPS_CANCLIPSTRETCHED         |
4875                                         WINEDDCAPS_COLORKEY                 |
4876                                         WINEDDCAPS_COLORKEYHWASSIST         |
4877                                         WINEDDCAPS_ALIGNBOUNDARYSRC;
4878     pal_caps =                          WINEDDPCAPS_8BIT                    |
4879                                         WINEDDPCAPS_PRIMARYSURFACE;
4880
4881     /* Fill the ddraw caps structure */
4882     pCaps->DirectDrawCaps.Caps =        WINEDDCAPS_GDI                      |
4883                                         WINEDDCAPS_PALETTE                  |
4884                                         blit_caps;
4885     pCaps->DirectDrawCaps.Caps2 =       WINEDDCAPS2_CERTIFIED                |
4886                                         WINEDDCAPS2_NOPAGELOCKREQUIRED       |
4887                                         WINEDDCAPS2_PRIMARYGAMMA             |
4888                                         WINEDDCAPS2_WIDESURFACES             |
4889                                         WINEDDCAPS2_CANRENDERWINDOWED;
4890     pCaps->DirectDrawCaps.CKeyCaps =    ckey_caps;
4891     pCaps->DirectDrawCaps.FXCaps =      fx_caps;
4892     pCaps->DirectDrawCaps.PalCaps =     pal_caps;
4893     pCaps->DirectDrawCaps.SVBCaps =     blit_caps;
4894     pCaps->DirectDrawCaps.SVBCKeyCaps = ckey_caps;
4895     pCaps->DirectDrawCaps.SVBFXCaps =   fx_caps;
4896     pCaps->DirectDrawCaps.VSBCaps =     blit_caps;
4897     pCaps->DirectDrawCaps.VSBCKeyCaps = ckey_caps;
4898     pCaps->DirectDrawCaps.VSBFXCaps =   fx_caps;
4899     pCaps->DirectDrawCaps.SSBCaps =     blit_caps;
4900     pCaps->DirectDrawCaps.SSBCKeyCaps = ckey_caps;
4901     pCaps->DirectDrawCaps.SSBFXCaps =   fx_caps;
4902
4903     pCaps->DirectDrawCaps.ddsCaps =     WINEDDSCAPS_ALPHA                   |
4904                                         WINEDDSCAPS_BACKBUFFER              |
4905                                         WINEDDSCAPS_FLIP                    |
4906                                         WINEDDSCAPS_FRONTBUFFER             |
4907                                         WINEDDSCAPS_OFFSCREENPLAIN          |
4908                                         WINEDDSCAPS_PALETTE                 |
4909                                         WINEDDSCAPS_PRIMARYSURFACE          |
4910                                         WINEDDSCAPS_SYSTEMMEMORY            |
4911                                         WINEDDSCAPS_VIDEOMEMORY             |
4912                                         WINEDDSCAPS_VISIBLE;
4913     pCaps->DirectDrawCaps.StrideAlign = DDRAW_PITCH_ALIGNMENT;
4914
4915     /* Set D3D caps if OpenGL is available. */
4916     if (adapter->opengl)
4917     {
4918         pCaps->DirectDrawCaps.ddsCaps |=WINEDDSCAPS_3DDEVICE                |
4919                                         WINEDDSCAPS_MIPMAP                  |
4920                                         WINEDDSCAPS_TEXTURE                 |
4921                                         WINEDDSCAPS_ZBUFFER;
4922         pCaps->DirectDrawCaps.Caps |=   WINEDDCAPS_3D;
4923     }
4924
4925     return WINED3D_OK;
4926 }
4927
4928 static HRESULT WINAPI IWineD3DImpl_CreateDevice(IWineD3D *iface, UINT adapter_idx, WINED3DDEVTYPE device_type,
4929         HWND focus_window, DWORD flags, IWineD3DDeviceParent *device_parent, IWineD3DDevice **device)
4930 {
4931     IWineD3DImpl *This = (IWineD3DImpl *)iface;
4932     IWineD3DDeviceImpl *object;
4933     HRESULT hr;
4934
4935     TRACE("iface %p, adapter_idx %u, device_type %#x, focus_window %p, flags %#x, device_parent %p, device %p.\n",
4936             iface, adapter_idx, device_type, focus_window, flags, device_parent, device);
4937
4938     /* Validate the adapter number. If no adapters are available(no GL), ignore the adapter
4939      * number and create a device without a 3D adapter for 2D only operation. */
4940     if (IWineD3D_GetAdapterCount(iface) && adapter_idx >= IWineD3D_GetAdapterCount(iface))
4941     {
4942         return WINED3DERR_INVALIDCALL;
4943     }
4944
4945     object = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*object));
4946     if (!object)
4947     {
4948         ERR("Failed to allocate device memory.\n");
4949         return E_OUTOFMEMORY;
4950     }
4951
4952     hr = device_init(object, This, adapter_idx, device_type, focus_window, flags, device_parent);
4953     if (FAILED(hr))
4954     {
4955         WARN("Failed to initialize device, hr %#x.\n", hr);
4956         HeapFree(GetProcessHeap(), 0, object);
4957         return hr;
4958     }
4959
4960     TRACE("Created device %p.\n", object);
4961     *device = (IWineD3DDevice *)object;
4962
4963     IWineD3DDeviceParent_WineD3DDeviceCreated(device_parent, *device);
4964
4965     return WINED3D_OK;
4966 }
4967
4968 static void * WINAPI IWineD3DImpl_GetParent(IWineD3D *iface)
4969 {
4970     TRACE("iface %p.\n", iface);
4971
4972     return ((IWineD3DImpl *)iface)->parent;
4973 }
4974
4975 static void WINE_GLAPI invalid_func(const void *data)
4976 {
4977     ERR("Invalid vertex attribute function called\n");
4978     DebugBreak();
4979 }
4980
4981 static void WINE_GLAPI invalid_texcoord_func(GLenum unit, const void *data)
4982 {
4983     ERR("Invalid texcoord function called\n");
4984     DebugBreak();
4985 }
4986
4987 /* Helper functions for providing vertex data to opengl. The arrays are initialized based on
4988  * the extension detection and are used in drawStridedSlow
4989  */
4990 static void WINE_GLAPI position_d3dcolor(const void *data)
4991 {
4992     DWORD pos = *((const DWORD *)data);
4993
4994     FIXME("Add a test for fixed function position from d3dcolor type\n");
4995     glVertex4s(D3DCOLOR_B_R(pos),
4996                D3DCOLOR_B_G(pos),
4997                D3DCOLOR_B_B(pos),
4998                D3DCOLOR_B_A(pos));
4999 }
5000
5001 static void WINE_GLAPI position_float4(const void *data)
5002 {
5003     const GLfloat *pos = data;
5004
5005     if (pos[3] != 0.0f && pos[3] != 1.0f)
5006     {
5007         float w = 1.0f / pos[3];
5008
5009         glVertex4f(pos[0] * w, pos[1] * w, pos[2] * w, w);
5010     }
5011     else
5012     {
5013         glVertex3fv(pos);
5014     }
5015 }
5016
5017 static void WINE_GLAPI diffuse_d3dcolor(const void *data)
5018 {
5019     DWORD diffuseColor = *((const DWORD *)data);
5020
5021     glColor4ub(D3DCOLOR_B_R(diffuseColor),
5022                D3DCOLOR_B_G(diffuseColor),
5023                D3DCOLOR_B_B(diffuseColor),
5024                D3DCOLOR_B_A(diffuseColor));
5025 }
5026
5027 static void WINE_GLAPI specular_d3dcolor(const void *data)
5028 {
5029     DWORD specularColor = *((const DWORD *)data);
5030     GLbyte d[] = {D3DCOLOR_B_R(specularColor),
5031             D3DCOLOR_B_G(specularColor),
5032             D3DCOLOR_B_B(specularColor)};
5033
5034     specular_func_3ubv(d);
5035 }
5036
5037 static void WINE_GLAPI warn_no_specular_func(const void *data)
5038 {
5039     WARN("GL_EXT_secondary_color not supported\n");
5040 }
5041
5042 static void fillGLAttribFuncs(const struct wined3d_gl_info *gl_info)
5043 {
5044     position_funcs[WINED3D_FFP_EMIT_FLOAT1]      = invalid_func;
5045     position_funcs[WINED3D_FFP_EMIT_FLOAT2]      = invalid_func;
5046     position_funcs[WINED3D_FFP_EMIT_FLOAT3]      = (glAttribFunc)glVertex3fv;
5047     position_funcs[WINED3D_FFP_EMIT_FLOAT4]      = position_float4;
5048     position_funcs[WINED3D_FFP_EMIT_D3DCOLOR]    = position_d3dcolor;
5049     position_funcs[WINED3D_FFP_EMIT_UBYTE4]      = invalid_func;
5050     position_funcs[WINED3D_FFP_EMIT_SHORT2]      = invalid_func;
5051     position_funcs[WINED3D_FFP_EMIT_SHORT4]      = (glAttribFunc)glVertex2sv;
5052     position_funcs[WINED3D_FFP_EMIT_UBYTE4N]     = invalid_func;
5053     position_funcs[WINED3D_FFP_EMIT_SHORT2N]     = invalid_func;
5054     position_funcs[WINED3D_FFP_EMIT_SHORT4N]     = invalid_func;
5055     position_funcs[WINED3D_FFP_EMIT_USHORT2N]    = invalid_func;
5056     position_funcs[WINED3D_FFP_EMIT_USHORT4N]    = invalid_func;
5057     position_funcs[WINED3D_FFP_EMIT_UDEC3]       = invalid_func;
5058     position_funcs[WINED3D_FFP_EMIT_DEC3N]       = invalid_func;
5059     position_funcs[WINED3D_FFP_EMIT_FLOAT16_2]   = invalid_func;
5060     position_funcs[WINED3D_FFP_EMIT_FLOAT16_4]   = invalid_func;
5061
5062     diffuse_funcs[WINED3D_FFP_EMIT_FLOAT1]       = invalid_func;
5063     diffuse_funcs[WINED3D_FFP_EMIT_FLOAT2]       = invalid_func;
5064     diffuse_funcs[WINED3D_FFP_EMIT_FLOAT3]       = (glAttribFunc)glColor3fv;
5065     diffuse_funcs[WINED3D_FFP_EMIT_FLOAT4]       = (glAttribFunc)glColor4fv;
5066     diffuse_funcs[WINED3D_FFP_EMIT_D3DCOLOR]     = diffuse_d3dcolor;
5067     diffuse_funcs[WINED3D_FFP_EMIT_UBYTE4]       = invalid_func;
5068     diffuse_funcs[WINED3D_FFP_EMIT_SHORT2]       = invalid_func;
5069     diffuse_funcs[WINED3D_FFP_EMIT_SHORT4]       = invalid_func;
5070     diffuse_funcs[WINED3D_FFP_EMIT_UBYTE4N]      = (glAttribFunc)glColor4ubv;
5071     diffuse_funcs[WINED3D_FFP_EMIT_SHORT2N]      = invalid_func;
5072     diffuse_funcs[WINED3D_FFP_EMIT_SHORT4N]      = (glAttribFunc)glColor4sv;
5073     diffuse_funcs[WINED3D_FFP_EMIT_USHORT2N]     = invalid_func;
5074     diffuse_funcs[WINED3D_FFP_EMIT_USHORT4N]     = (glAttribFunc)glColor4usv;
5075     diffuse_funcs[WINED3D_FFP_EMIT_UDEC3]        = invalid_func;
5076     diffuse_funcs[WINED3D_FFP_EMIT_DEC3N]        = invalid_func;
5077     diffuse_funcs[WINED3D_FFP_EMIT_FLOAT16_2]    = invalid_func;
5078     diffuse_funcs[WINED3D_FFP_EMIT_FLOAT16_4]    = invalid_func;
5079
5080     /* No 4 component entry points here */
5081     specular_funcs[WINED3D_FFP_EMIT_FLOAT1]      = invalid_func;
5082     specular_funcs[WINED3D_FFP_EMIT_FLOAT2]      = invalid_func;
5083     if (gl_info->supported[EXT_SECONDARY_COLOR])
5084     {
5085         specular_funcs[WINED3D_FFP_EMIT_FLOAT3]  = (glAttribFunc)GL_EXTCALL(glSecondaryColor3fvEXT);
5086     }
5087     else
5088     {
5089         specular_funcs[WINED3D_FFP_EMIT_FLOAT3]  = warn_no_specular_func;
5090     }
5091     specular_funcs[WINED3D_FFP_EMIT_FLOAT4]      = invalid_func;
5092     if (gl_info->supported[EXT_SECONDARY_COLOR])
5093     {
5094         specular_func_3ubv = (glAttribFunc)GL_EXTCALL(glSecondaryColor3ubvEXT);
5095         specular_funcs[WINED3D_FFP_EMIT_D3DCOLOR] = specular_d3dcolor;
5096     }
5097     else
5098     {
5099         specular_funcs[WINED3D_FFP_EMIT_D3DCOLOR] = warn_no_specular_func;
5100     }
5101     specular_funcs[WINED3D_FFP_EMIT_UBYTE4]      = invalid_func;
5102     specular_funcs[WINED3D_FFP_EMIT_SHORT2]      = invalid_func;
5103     specular_funcs[WINED3D_FFP_EMIT_SHORT4]      = invalid_func;
5104     specular_funcs[WINED3D_FFP_EMIT_UBYTE4N]     = invalid_func;
5105     specular_funcs[WINED3D_FFP_EMIT_SHORT2N]     = invalid_func;
5106     specular_funcs[WINED3D_FFP_EMIT_SHORT4N]     = invalid_func;
5107     specular_funcs[WINED3D_FFP_EMIT_USHORT2N]    = invalid_func;
5108     specular_funcs[WINED3D_FFP_EMIT_USHORT4N]    = invalid_func;
5109     specular_funcs[WINED3D_FFP_EMIT_UDEC3]       = invalid_func;
5110     specular_funcs[WINED3D_FFP_EMIT_DEC3N]       = invalid_func;
5111     specular_funcs[WINED3D_FFP_EMIT_FLOAT16_2]   = invalid_func;
5112     specular_funcs[WINED3D_FFP_EMIT_FLOAT16_4]   = invalid_func;
5113
5114     /* Only 3 component entry points here. Test how others behave. Float4 normals are used
5115      * by one of our tests, trying to pass it to the pixel shader, which fails on Windows.
5116      */
5117     normal_funcs[WINED3D_FFP_EMIT_FLOAT1]         = invalid_func;
5118     normal_funcs[WINED3D_FFP_EMIT_FLOAT2]         = invalid_func;
5119     normal_funcs[WINED3D_FFP_EMIT_FLOAT3]         = (glAttribFunc)glNormal3fv;
5120     normal_funcs[WINED3D_FFP_EMIT_FLOAT4]         = (glAttribFunc)glNormal3fv; /* Just ignore the 4th value */
5121     normal_funcs[WINED3D_FFP_EMIT_D3DCOLOR]       = invalid_func;
5122     normal_funcs[WINED3D_FFP_EMIT_UBYTE4]         = invalid_func;
5123     normal_funcs[WINED3D_FFP_EMIT_SHORT2]         = invalid_func;
5124     normal_funcs[WINED3D_FFP_EMIT_SHORT4]         = invalid_func;
5125     normal_funcs[WINED3D_FFP_EMIT_UBYTE4N]        = invalid_func;
5126     normal_funcs[WINED3D_FFP_EMIT_SHORT2N]        = invalid_func;
5127     normal_funcs[WINED3D_FFP_EMIT_SHORT4N]        = invalid_func;
5128     normal_funcs[WINED3D_FFP_EMIT_USHORT2N]       = invalid_func;
5129     normal_funcs[WINED3D_FFP_EMIT_USHORT4N]       = invalid_func;
5130     normal_funcs[WINED3D_FFP_EMIT_UDEC3]          = invalid_func;
5131     normal_funcs[WINED3D_FFP_EMIT_DEC3N]          = invalid_func;
5132     normal_funcs[WINED3D_FFP_EMIT_FLOAT16_2]      = invalid_func;
5133     normal_funcs[WINED3D_FFP_EMIT_FLOAT16_4]      = invalid_func;
5134
5135     multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT1]    = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord1fvARB);
5136     multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT2]    = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord2fvARB);
5137     multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT3]    = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord3fvARB);
5138     multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT4]    = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord4fvARB);
5139     multi_texcoord_funcs[WINED3D_FFP_EMIT_D3DCOLOR]  = invalid_texcoord_func;
5140     multi_texcoord_funcs[WINED3D_FFP_EMIT_UBYTE4]    = invalid_texcoord_func;
5141     multi_texcoord_funcs[WINED3D_FFP_EMIT_SHORT2]    = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord2svARB);
5142     multi_texcoord_funcs[WINED3D_FFP_EMIT_SHORT4]    = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord4svARB);
5143     multi_texcoord_funcs[WINED3D_FFP_EMIT_UBYTE4N]   = invalid_texcoord_func;
5144     multi_texcoord_funcs[WINED3D_FFP_EMIT_SHORT2N]   = invalid_texcoord_func;
5145     multi_texcoord_funcs[WINED3D_FFP_EMIT_SHORT4N]   = invalid_texcoord_func;
5146     multi_texcoord_funcs[WINED3D_FFP_EMIT_USHORT2N]  = invalid_texcoord_func;
5147     multi_texcoord_funcs[WINED3D_FFP_EMIT_USHORT4N]  = invalid_texcoord_func;
5148     multi_texcoord_funcs[WINED3D_FFP_EMIT_UDEC3]     = invalid_texcoord_func;
5149     multi_texcoord_funcs[WINED3D_FFP_EMIT_DEC3N]     = invalid_texcoord_func;
5150     if (gl_info->supported[NV_HALF_FLOAT])
5151     {
5152         /* Not supported by ARB_HALF_FLOAT_VERTEX, so check for NV_HALF_FLOAT */
5153         multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT16_2] = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord2hvNV);
5154         multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT16_4] = (glMultiTexCoordFunc)GL_EXTCALL(glMultiTexCoord4hvNV);
5155     } else {
5156         multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT16_2] = invalid_texcoord_func;
5157         multi_texcoord_funcs[WINED3D_FFP_EMIT_FLOAT16_4] = invalid_texcoord_func;
5158     }
5159 }
5160
5161 /* Do not call while under the GL lock. */
5162 static BOOL InitAdapters(IWineD3DImpl *This)
5163 {
5164     static HMODULE mod_gl;
5165     BOOL ret;
5166     int ps_selected_mode, vs_selected_mode;
5167
5168     /* No need to hold any lock. The calling library makes sure only one thread calls
5169      * wined3d simultaneously
5170      */
5171
5172     TRACE("Initializing adapters\n");
5173
5174     if(!mod_gl) {
5175 #ifdef USE_WIN32_OPENGL
5176 #define USE_GL_FUNC(pfn) pfn = (void*)GetProcAddress(mod_gl, #pfn);
5177         mod_gl = LoadLibraryA("opengl32.dll");
5178         if(!mod_gl) {
5179             ERR("Can't load opengl32.dll!\n");
5180             goto nogl_adapter;
5181         }
5182 #else
5183 #define USE_GL_FUNC(pfn) pfn = (void*)pwglGetProcAddress(#pfn);
5184         /* To bypass the opengl32 thunks load wglGetProcAddress from gdi32 (glXGetProcAddress wrapper) instead of opengl32's */
5185         mod_gl = GetModuleHandleA("gdi32.dll");
5186 #endif
5187     }
5188
5189 /* Load WGL core functions from opengl32.dll */
5190 #define USE_WGL_FUNC(pfn) p##pfn = (void*)GetProcAddress(mod_gl, #pfn);
5191     WGL_FUNCS_GEN;
5192 #undef USE_WGL_FUNC
5193
5194     if(!pwglGetProcAddress) {
5195         ERR("Unable to load wglGetProcAddress!\n");
5196         goto nogl_adapter;
5197     }
5198
5199 /* Dynamically load all GL core functions */
5200     GL_FUNCS_GEN;
5201 #undef USE_GL_FUNC
5202
5203     /* Load glFinish and glFlush from opengl32.dll even if we're not using WIN32 opengl
5204      * otherwise because we have to use winex11.drv's override
5205      */
5206 #ifdef USE_WIN32_OPENGL
5207     wglFinish = (void*)GetProcAddress(mod_gl, "glFinish");
5208     wglFlush = (void*)GetProcAddress(mod_gl, "glFlush");
5209 #else
5210     wglFinish = (void*)pwglGetProcAddress("wglFinish");
5211     wglFlush = (void*)pwglGetProcAddress("wglFlush");
5212 #endif
5213
5214     glEnableWINE = glEnable;
5215     glDisableWINE = glDisable;
5216
5217     /* For now only one default adapter */
5218     {
5219         struct wined3d_adapter *adapter = &This->adapters[0];
5220         const struct wined3d_gl_info *gl_info = &adapter->gl_info;
5221         struct wined3d_fake_gl_ctx fake_gl_ctx = {0};
5222         int iPixelFormat;
5223         int res;
5224         int i;
5225         WineD3D_PixelFormat *cfgs;
5226         DISPLAY_DEVICEW DisplayDevice;
5227         HDC hdc;
5228
5229         TRACE("Initializing default adapter\n");
5230         adapter->ordinal = 0;
5231         adapter->monitorPoint.x = -1;
5232         adapter->monitorPoint.y = -1;
5233
5234         if (!AllocateLocallyUniqueId(&adapter->luid))
5235         {
5236             DWORD err = GetLastError();
5237             ERR("Failed to set adapter LUID (%#x).\n", err);
5238             goto nogl_adapter;
5239         }
5240         TRACE("Allocated LUID %08x:%08x for adapter.\n",
5241                 adapter->luid.HighPart, adapter->luid.LowPart);
5242
5243         if (!WineD3D_CreateFakeGLContext(&fake_gl_ctx))
5244         {
5245             ERR("Failed to get a gl context for default adapter\n");
5246             goto nogl_adapter;
5247         }
5248
5249         ret = IWineD3DImpl_FillGLCaps(adapter);
5250         if(!ret) {
5251             ERR("Failed to initialize gl caps for default adapter\n");
5252             WineD3D_ReleaseFakeGLContext(&fake_gl_ctx);
5253             goto nogl_adapter;
5254         }
5255         ret = initPixelFormats(&adapter->gl_info, adapter->driver_info.vendor);
5256         if(!ret) {
5257             ERR("Failed to init gl formats\n");
5258             WineD3D_ReleaseFakeGLContext(&fake_gl_ctx);
5259             goto nogl_adapter;
5260         }
5261
5262         hdc = fake_gl_ctx.dc;
5263
5264         adapter->TextureRam = adapter->driver_info.vidmem;
5265         adapter->UsedTextureRam = 0;
5266         TRACE("Emulating %dMB of texture ram\n", adapter->TextureRam/(1024*1024));
5267
5268         /* Initialize the Adapter's DeviceName which is required for ChangeDisplaySettings and friends */
5269         DisplayDevice.cb = sizeof(DisplayDevice);
5270         EnumDisplayDevicesW(NULL, 0 /* Adapter 0 = iDevNum 0 */, &DisplayDevice, 0);
5271         TRACE("DeviceName: %s\n", debugstr_w(DisplayDevice.DeviceName));
5272         strcpyW(adapter->DeviceName, DisplayDevice.DeviceName);
5273
5274         if (gl_info->supported[WGL_ARB_PIXEL_FORMAT])
5275         {
5276             int attribute;
5277             int attribs[11];
5278             int values[11];
5279             int nAttribs = 0;
5280
5281             attribute = WGL_NUMBER_PIXEL_FORMATS_ARB;
5282             GL_EXTCALL(wglGetPixelFormatAttribivARB(hdc, 0, 0, 1, &attribute, &adapter->nCfgs));
5283
5284             adapter->cfgs = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, adapter->nCfgs *sizeof(WineD3D_PixelFormat));
5285             cfgs = adapter->cfgs;
5286             attribs[nAttribs++] = WGL_RED_BITS_ARB;
5287             attribs[nAttribs++] = WGL_GREEN_BITS_ARB;
5288             attribs[nAttribs++] = WGL_BLUE_BITS_ARB;
5289             attribs[nAttribs++] = WGL_ALPHA_BITS_ARB;
5290             attribs[nAttribs++] = WGL_COLOR_BITS_ARB;
5291             attribs[nAttribs++] = WGL_DEPTH_BITS_ARB;
5292             attribs[nAttribs++] = WGL_STENCIL_BITS_ARB;
5293             attribs[nAttribs++] = WGL_DRAW_TO_WINDOW_ARB;
5294             attribs[nAttribs++] = WGL_PIXEL_TYPE_ARB;
5295             attribs[nAttribs++] = WGL_DOUBLE_BUFFER_ARB;
5296             attribs[nAttribs++] = WGL_AUX_BUFFERS_ARB;
5297
5298             for (iPixelFormat=1; iPixelFormat <= adapter->nCfgs; ++iPixelFormat)
5299             {
5300                 res = GL_EXTCALL(wglGetPixelFormatAttribivARB(hdc, iPixelFormat, 0, nAttribs, attribs, values));
5301
5302                 if(!res)
5303                     continue;
5304
5305                 /* Cache the pixel format */
5306                 cfgs->iPixelFormat = iPixelFormat;
5307                 cfgs->redSize = values[0];
5308                 cfgs->greenSize = values[1];
5309                 cfgs->blueSize = values[2];
5310                 cfgs->alphaSize = values[3];
5311                 cfgs->colorSize = values[4];
5312                 cfgs->depthSize = values[5];
5313                 cfgs->stencilSize = values[6];
5314                 cfgs->windowDrawable = values[7];
5315                 cfgs->iPixelType = values[8];
5316                 cfgs->doubleBuffer = values[9];
5317                 cfgs->auxBuffers = values[10];
5318
5319                 cfgs->numSamples = 0;
5320                 /* Check multisample support */
5321                 if (gl_info->supported[ARB_MULTISAMPLE])
5322                 {
5323                     int attrib[2] = {WGL_SAMPLE_BUFFERS_ARB, WGL_SAMPLES_ARB};
5324                     int value[2];
5325                     if(GL_EXTCALL(wglGetPixelFormatAttribivARB(hdc, iPixelFormat, 0, 2, attrib, value))) {
5326                         /* value[0] = WGL_SAMPLE_BUFFERS_ARB which tells whether multisampling is supported.
5327                         * value[1] = number of multi sample buffers*/
5328                         if(value[0])
5329                             cfgs->numSamples = value[1];
5330                     }
5331                 }
5332
5333                 TRACE("iPixelFormat=%d, iPixelType=%#x, doubleBuffer=%d, RGBA=%d/%d/%d/%d, "
5334                         "depth=%d, stencil=%d, samples=%d, windowDrawable=%d\n",
5335                         cfgs->iPixelFormat, cfgs->iPixelType, cfgs->doubleBuffer,
5336                         cfgs->redSize, cfgs->greenSize, cfgs->blueSize, cfgs->alphaSize,
5337                         cfgs->depthSize, cfgs->stencilSize, cfgs->numSamples, cfgs->windowDrawable);
5338                 cfgs++;
5339             }
5340         }
5341         else
5342         {
5343             int nCfgs = DescribePixelFormat(hdc, 0, 0, 0);
5344             adapter->cfgs = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, nCfgs*sizeof(WineD3D_PixelFormat));
5345             adapter->nCfgs = 0; /* We won't accept all formats e.g. software accelerated ones will be skipped */
5346
5347             cfgs = adapter->cfgs;
5348             for(iPixelFormat=1; iPixelFormat<=nCfgs; iPixelFormat++)
5349             {
5350                 PIXELFORMATDESCRIPTOR ppfd;
5351
5352                 res = DescribePixelFormat(hdc, iPixelFormat, sizeof(PIXELFORMATDESCRIPTOR), &ppfd);
5353                 if(!res)
5354                     continue;
5355
5356                 /* We only want HW acceleration using an OpenGL ICD driver.
5357                  * PFD_GENERIC_FORMAT = slow opengl 1.1 gdi software rendering
5358                  * PFD_GENERIC_ACCELERATED = partial hw acceleration using a MCD driver (e.g. 3dfx minigl)
5359                  */
5360                 if(ppfd.dwFlags & (PFD_GENERIC_FORMAT | PFD_GENERIC_ACCELERATED))
5361                 {
5362                     TRACE("Skipping iPixelFormat=%d because it isn't ICD accelerated\n", iPixelFormat);
5363                     continue;
5364                 }
5365
5366                 cfgs->iPixelFormat = iPixelFormat;
5367                 cfgs->redSize = ppfd.cRedBits;
5368                 cfgs->greenSize = ppfd.cGreenBits;
5369                 cfgs->blueSize = ppfd.cBlueBits;
5370                 cfgs->alphaSize = ppfd.cAlphaBits;
5371                 cfgs->colorSize = ppfd.cColorBits;
5372                 cfgs->depthSize = ppfd.cDepthBits;
5373                 cfgs->stencilSize = ppfd.cStencilBits;
5374                 cfgs->windowDrawable = (ppfd.dwFlags & PFD_DRAW_TO_WINDOW) ? 1 : 0;
5375                 cfgs->iPixelType = (ppfd.iPixelType == PFD_TYPE_RGBA) ? WGL_TYPE_RGBA_ARB : WGL_TYPE_COLORINDEX_ARB;
5376                 cfgs->doubleBuffer = (ppfd.dwFlags & PFD_DOUBLEBUFFER) ? 1 : 0;
5377                 cfgs->auxBuffers = ppfd.cAuxBuffers;
5378                 cfgs->numSamples = 0;
5379
5380                 TRACE("iPixelFormat=%d, iPixelType=%#x, doubleBuffer=%d, RGBA=%d/%d/%d/%d, "
5381                         "depth=%d, stencil=%d, windowDrawable=%d\n",
5382                         cfgs->iPixelFormat, cfgs->iPixelType, cfgs->doubleBuffer,
5383                         cfgs->redSize, cfgs->greenSize, cfgs->blueSize, cfgs->alphaSize,
5384                         cfgs->depthSize, cfgs->stencilSize, cfgs->windowDrawable);
5385                 cfgs++;
5386                 adapter->nCfgs++;
5387             }
5388
5389             /* Yikes we haven't found any suitable formats. This should only happen in case of GDI software rendering which we can't use anyway as its 3D functionality is very, very limited */
5390             if(!adapter->nCfgs)
5391             {
5392                 ERR("Disabling Direct3D because no hardware accelerated pixel formats have been found!\n");
5393
5394                 WineD3D_ReleaseFakeGLContext(&fake_gl_ctx);
5395                 HeapFree(GetProcessHeap(), 0, adapter->cfgs);
5396                 goto nogl_adapter;
5397             }
5398         }
5399
5400         /* D16, D24X8 and D24S8 are common depth / depth+stencil formats. All drivers support them though this doesn't
5401          * mean that the format is offered in hardware. For instance Geforce8 cards don't have offer D16 in hardware
5402          * but just fake it using D24(X8?) which is fine. D3D also allows that.
5403          * Some display drivers (i915 on Linux) only report mixed depth+stencil formats like D24S8. MSDN clearly mentions
5404          * that only on lockable formats (e.g. D16_locked) the bit order is guaranteed and that on other formats the
5405          * driver is allowed to consume more bits EXCEPT for stencil bits.
5406          *
5407          * Mark an adapter with this broken stencil behavior.
5408          */
5409         adapter->brokenStencil = TRUE;
5410         for (i = 0, cfgs = adapter->cfgs; i < adapter->nCfgs; ++i)
5411         {
5412             /* Nearly all drivers offer depth formats without stencil, only on i915 this if-statement won't be entered. */
5413             if(cfgs[i].depthSize && !cfgs[i].stencilSize) {
5414                 adapter->brokenStencil = FALSE;
5415                 break;
5416             }
5417         }
5418
5419         WineD3D_ReleaseFakeGLContext(&fake_gl_ctx);
5420
5421         select_shader_mode(&adapter->gl_info, &ps_selected_mode, &vs_selected_mode);
5422         fillGLAttribFuncs(&adapter->gl_info);
5423         adapter->opengl = TRUE;
5424     }
5425     This->adapter_count = 1;
5426     TRACE("%u adapters successfully initialized\n", This->adapter_count);
5427
5428     return TRUE;
5429
5430 nogl_adapter:
5431     /* Initialize an adapter for ddraw-only memory counting */
5432     memset(This->adapters, 0, sizeof(This->adapters));
5433     This->adapters[0].ordinal = 0;
5434     This->adapters[0].opengl = FALSE;
5435     This->adapters[0].monitorPoint.x = -1;
5436     This->adapters[0].monitorPoint.y = -1;
5437
5438     This->adapters[0].driver_info.name = "Display";
5439     This->adapters[0].driver_info.description = "WineD3D DirectDraw Emulation";
5440     if(wined3d_settings.emulated_textureram) {
5441         This->adapters[0].TextureRam = wined3d_settings.emulated_textureram;
5442     } else {
5443         This->adapters[0].TextureRam = 8 * 1024 * 1024; /* This is plenty for a DDraw-only card */
5444     }
5445
5446     initPixelFormatsNoGL(&This->adapters[0].gl_info);
5447
5448     This->adapter_count = 1;
5449     return FALSE;
5450 }
5451
5452 /**********************************************************
5453  * IWineD3D VTbl follows
5454  **********************************************************/
5455
5456 static const struct IWineD3DVtbl IWineD3D_Vtbl =
5457 {
5458     /* IUnknown */
5459     IWineD3DImpl_QueryInterface,
5460     IWineD3DImpl_AddRef,
5461     IWineD3DImpl_Release,
5462     /* IWineD3D */
5463     IWineD3DImpl_GetParent,
5464     IWineD3DImpl_GetAdapterCount,
5465     IWineD3DImpl_RegisterSoftwareDevice,
5466     IWineD3DImpl_GetAdapterMonitor,
5467     IWineD3DImpl_GetAdapterModeCount,
5468     IWineD3DImpl_EnumAdapterModes,
5469     IWineD3DImpl_GetAdapterDisplayMode,
5470     IWineD3DImpl_GetAdapterIdentifier,
5471     IWineD3DImpl_CheckDeviceMultiSampleType,
5472     IWineD3DImpl_CheckDepthStencilMatch,
5473     IWineD3DImpl_CheckDeviceType,
5474     IWineD3DImpl_CheckDeviceFormat,
5475     IWineD3DImpl_CheckDeviceFormatConversion,
5476     IWineD3DImpl_GetDeviceCaps,
5477     IWineD3DImpl_CreateDevice
5478 };
5479
5480 static void STDMETHODCALLTYPE wined3d_null_wined3d_object_destroyed(void *parent) {}
5481
5482 const struct wined3d_parent_ops wined3d_null_parent_ops =
5483 {
5484     wined3d_null_wined3d_object_destroyed,
5485 };
5486
5487 /* Do not call while under the GL lock. */
5488 HRESULT wined3d_init(IWineD3DImpl *wined3d, UINT version, void *parent)
5489 {
5490     wined3d->lpVtbl = &IWineD3D_Vtbl;
5491     wined3d->dxVersion = version;
5492     wined3d->ref = 1;
5493     wined3d->parent = parent;
5494
5495     if (!InitAdapters(wined3d))
5496     {
5497         WARN("Failed to initialize adapters.\n");
5498         if (version > 7)
5499         {
5500             MESSAGE("Direct3D%u is not available without OpenGL.\n", version);
5501             return E_FAIL;
5502         }
5503     }
5504
5505     return WINED3D_OK;
5506 }