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