wintrust: Fix copy-paste error.
[wine] / dlls / wined3d / utils.c
1 /*
2  * Utility functions for the WineD3D Library
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 2006-2008 Henri Verbeet
9  * Copyright 2007-2008 Stefan Dösinger for CodeWeavers
10  * Copyright 2009 Henri Verbeet for CodeWeavers
11  *
12  * This library is free software; you can redistribute it and/or
13  * modify it under the terms of the GNU Lesser General Public
14  * License as published by the Free Software Foundation; either
15  * version 2.1 of the License, or (at your option) any later version.
16  *
17  * This library is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
20  * Lesser General Public License for more details.
21  *
22  * You should have received a copy of the GNU Lesser General Public
23  * License along with this library; if not, write to the Free Software
24  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
25  */
26
27 #include "config.h"
28 #include "wined3d_private.h"
29
30 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
31
32 struct StaticPixelFormatDesc
33 {
34     WINED3DFORMAT format;
35     DWORD alphaMask, redMask, greenMask, blueMask;
36     UINT bpp;
37     short depthSize, stencilSize;
38 };
39
40 /*****************************************************************************
41  * Pixel format array
42  *
43  * For the formats WINED3DFMT_A32B32G32R32F, WINED3DFMT_A16B16G16R16F,
44  * and WINED3DFMT_A16B16G16R16 do not have correct alpha masks, because the
45  * high masks do not fit into the 32 bit values needed for ddraw. It is only
46  * used for ddraw mostly, and to figure out if the format has alpha at all, so
47  * setting a mask like 0x1 for those surfaces is correct. The 64 and 128 bit
48  * formats are not usable in 2D rendering because ddraw doesn't support them.
49  */
50 static const struct StaticPixelFormatDesc formats[] =
51 {
52   /* WINED3DFORMAT                       alphamask    redmask    greenmask    bluemask     bpp    depth  stencil */
53     {WINED3DFMT_UNKNOWN,                    0x0,        0x0,        0x0,        0x0,        0,      0,      0},
54     /* FourCC formats */
55     {WINED3DFMT_UYVY,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
56     {WINED3DFMT_YUY2,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
57     {WINED3DFMT_YV12,                       0x0,        0x0,        0x0,        0x0,        1,      0,      0},
58     {WINED3DFMT_DXT1,                       0x0,        0x0,        0x0,        0x0,        1,      0,      0},
59     {WINED3DFMT_DXT2,                       0x0,        0x0,        0x0,        0x0,        1,      0,      0},
60     {WINED3DFMT_DXT3,                       0x0,        0x0,        0x0,        0x0,        1,      0,      0},
61     {WINED3DFMT_DXT4,                       0x0,        0x0,        0x0,        0x0,        1,      0,      0},
62     {WINED3DFMT_DXT5,                       0x0,        0x0,        0x0,        0x0,        1,      0,      0},
63     {WINED3DFMT_MULTI2_ARGB8,               0x0,        0x0,        0x0,        0x0,        1/*?*/, 0,      0},
64     {WINED3DFMT_G8R8_G8B8,                  0x0,        0x0,        0x0,        0x0,        1/*?*/, 0,      0},
65     {WINED3DFMT_R8G8_B8G8,                  0x0,        0x0,        0x0,        0x0,        1/*?*/, 0,      0},
66     /* IEEE formats */
67     {WINED3DFMT_R32_FLOAT,                  0x0,        0x0,        0x0,        0x0,        4,      0,      0},
68     {WINED3DFMT_R32G32_FLOAT,               0x0,        0x0,        0x0,        0x0,        8,      0,      0},
69     {WINED3DFMT_R32G32B32_FLOAT,            0x0,        0x0,        0x0,        0x0,        12,     0,      0},
70     {WINED3DFMT_R32G32B32A32_FLOAT,         0x1,        0x0,        0x0,        0x0,        16,     0,      0},
71     /* Hmm? */
72     {WINED3DFMT_R8G8_SNORM_Cx,              0x0,        0x0,        0x0,        0x0,        2,      0,      0},
73     /* Float */
74     {WINED3DFMT_R16_FLOAT,                  0x0,        0x0,        0x0,        0x0,        2,      0,      0},
75     {WINED3DFMT_R16G16_FLOAT,               0x0,        0x0,        0x0,        0x0,        4,      0,      0},
76     {WINED3DFMT_R16G16_SINT,                0x0,        0x0,        0x0,        0x0,        4,      0,      0},
77     {WINED3DFMT_R16G16B16A16_FLOAT,         0x1,        0x0,        0x0,        0x0,        8,      0,      0},
78     {WINED3DFMT_R16G16B16A16_SINT,          0x1,        0x0,        0x0,        0x0,        8,      0,      0},
79     /* Palettized formats */
80     {WINED3DFMT_P8_UINT_A8_UNORM,           0x0000ff00, 0x0,        0x0,        0x0,        2,      0,      0},
81     {WINED3DFMT_P8_UINT,                    0x0,        0x0,        0x0,        0x0,        1,      0,      0},
82     /* Standard ARGB formats. */
83     {WINED3DFMT_B8G8R8_UNORM,               0x0,        0x00ff0000, 0x0000ff00, 0x000000ff, 3,      0,      0},
84     {WINED3DFMT_B8G8R8A8_UNORM,             0xff000000, 0x00ff0000, 0x0000ff00, 0x000000ff, 4,      0,      0},
85     {WINED3DFMT_B8G8R8X8_UNORM,             0x0,        0x00ff0000, 0x0000ff00, 0x000000ff, 4,      0,      0},
86     {WINED3DFMT_B5G6R5_UNORM,               0x0,        0x0000f800, 0x000007e0, 0x0000001f, 2,      0,      0},
87     {WINED3DFMT_B5G5R5X1_UNORM,             0x0,        0x00007c00, 0x000003e0, 0x0000001f, 2,      0,      0},
88     {WINED3DFMT_B5G5R5A1_UNORM,             0x00008000, 0x00007c00, 0x000003e0, 0x0000001f, 2,      0,      0},
89     {WINED3DFMT_B4G4R4A4_UNORM,             0x0000f000, 0x00000f00, 0x000000f0, 0x0000000f, 2,      0,      0},
90     {WINED3DFMT_B2G3R3_UNORM,               0x0,        0x000000e0, 0x0000001c, 0x00000003, 1,      0,      0},
91     {WINED3DFMT_A8_UNORM,                   0x000000ff, 0x0,        0x0,        0x0,        1,      0,      0},
92     {WINED3DFMT_B2G3R3A8_UNORM,             0x0000ff00, 0x000000e0, 0x0000001c, 0x00000003, 2,      0,      0},
93     {WINED3DFMT_B4G4R4X4_UNORM,             0x0,        0x00000f00, 0x000000f0, 0x0000000f, 2,      0,      0},
94     {WINED3DFMT_R10G10B10A2_UNORM,          0xc0000000, 0x000003ff, 0x000ffc00, 0x3ff00000, 4,      0,      0},
95     {WINED3DFMT_R10G10B10A2_UINT,           0xc0000000, 0x000003ff, 0x000ffc00, 0x3ff00000, 4,      0,      0},
96     {WINED3DFMT_R10G10B10A2_SNORM,          0xc0000000, 0x000003ff, 0x000ffc00, 0x3ff00000, 4,      0,      0},
97     {WINED3DFMT_R8G8B8A8_UNORM,             0xff000000, 0x000000ff, 0x0000ff00, 0x00ff0000, 4,      0,      0},
98     {WINED3DFMT_R8G8B8A8_UINT,              0xff000000, 0x000000ff, 0x0000ff00, 0x00ff0000, 4,      0,      0},
99     {WINED3DFMT_R8G8B8X8_UNORM,             0x0,        0x000000ff, 0x0000ff00, 0x00ff0000, 4,      0,      0},
100     {WINED3DFMT_R16G16_UNORM,               0x0,        0x0000ffff, 0xffff0000, 0x0,        4,      0,      0},
101     {WINED3DFMT_B10G10R10A2_UNORM,          0xc0000000, 0x3ff00000, 0x000ffc00, 0x000003ff, 4,      0,      0},
102     {WINED3DFMT_R16G16B16A16_UNORM,         0x1,        0x0000ffff, 0xffff0000, 0x0,        8,      0,      0},
103     /* Luminance */
104     {WINED3DFMT_L8_UNORM,                   0x0,        0x0,        0x0,        0x0,        1,      0,      0},
105     {WINED3DFMT_L8A8_UNORM,                 0x0000ff00, 0x0,        0x0,        0x0,        2,      0,      0},
106     {WINED3DFMT_L4A4_UNORM,                 0x000000f0, 0x0,        0x0,        0x0,        1,      0,      0},
107     {WINED3DFMT_L16_UNORM,                  0x0,        0x0,        0x0,        0x0,        2,      16,     0},
108     /* Bump mapping stuff */
109     {WINED3DFMT_R8G8_SNORM,                 0x0,        0x0,        0x0,        0x0,        2,      0,      0},
110     {WINED3DFMT_R5G5_SNORM_L6_UNORM,        0x0,        0x0,        0x0,        0x0,        2,      0,      0},
111     {WINED3DFMT_R8G8_SNORM_L8X8_UNORM,      0x0,        0x0,        0x0,        0x0,        4,      0,      0},
112     {WINED3DFMT_R8G8B8A8_SNORM,             0x0,        0x0,        0x0,        0x0,        4,      0,      0},
113     {WINED3DFMT_R16G16_SNORM,               0x0,        0x0,        0x0,        0x0,        4,      0,      0},
114     {WINED3DFMT_R10G11B11_SNORM,            0x0,        0x0,        0x0,        0x0,        4,      0,      0},
115     {WINED3DFMT_R10G10B10_SNORM_A2_UNORM,   0xb0000000, 0x0,        0x0,        0x0,        4,      0,      0},
116     /* Depth stencil formats */
117     {WINED3DFMT_D16_LOCKABLE,               0x0,        0x0,        0x0,        0x0,        2,      16,     0},
118     {WINED3DFMT_D32_UNORM,                  0x0,        0x0,        0x0,        0x0,        4,      32,     0},
119     {WINED3DFMT_S1_UINT_D15_UNORM,          0x0,        0x0,        0x0,        0x0,        2,      15,     1},
120     {WINED3DFMT_D24_UNORM_S8_UINT,          0x0,        0x0,        0x0,        0x0,        4,      24,     8},
121     {WINED3DFMT_X8D24_UNORM,                0x0,        0x0,        0x0,        0x0,        4,      24,     0},
122     {WINED3DFMT_S4X4_UINT_D24_UNORM,        0x0,        0x0,        0x0,        0x0,        4,      24,     4},
123     {WINED3DFMT_D16_UNORM,                  0x0,        0x0,        0x0,        0x0,        2,      16,     0},
124     {WINED3DFMT_D32_FLOAT,                  0x0,        0x0,        0x0,        0x0,        4,      32,     0},
125     {WINED3DFMT_S8_UINT_D24_FLOAT,          0x0,        0x0,        0x0,        0x0,        4,      24,     8},
126     {WINED3DFMT_VERTEXDATA,                 0x0,        0x0,        0x0,        0x0,        0,      0,      0},
127     {WINED3DFMT_R16_UINT,                   0x0,        0x0,        0x0,        0x0,        2,      0,      0},
128     {WINED3DFMT_R32_UINT,                   0x0,        0x0,        0x0,        0x0,        4,      0,      0},
129     {WINED3DFMT_R16G16B16A16_SNORM,         0x0,        0x0,        0x0,        0x0,        8,      0,      0},
130     /* Vendor-specific formats */
131     {WINED3DFMT_ATI2N,                      0x0,        0x0,        0x0,        0x0,        1,      0,      0},
132     {WINED3DFMT_NVHU,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
133     {WINED3DFMT_NVHS,                       0x0,        0x0,        0x0,        0x0,        2,      0,      0},
134 };
135
136 struct wined3d_format_base_flags
137 {
138     WINED3DFORMAT format;
139     DWORD flags;
140 };
141
142 static const struct wined3d_format_base_flags format_base_flags[] =
143 {
144     {WINED3DFMT_UYVY,           WINED3DFMT_FLAG_FOURCC},
145     {WINED3DFMT_YUY2,           WINED3DFMT_FLAG_FOURCC},
146     {WINED3DFMT_YV12,           WINED3DFMT_FLAG_FOURCC},
147     {WINED3DFMT_DXT1,           WINED3DFMT_FLAG_FOURCC},
148     {WINED3DFMT_DXT2,           WINED3DFMT_FLAG_FOURCC},
149     {WINED3DFMT_DXT3,           WINED3DFMT_FLAG_FOURCC},
150     {WINED3DFMT_DXT4,           WINED3DFMT_FLAG_FOURCC},
151     {WINED3DFMT_DXT5,           WINED3DFMT_FLAG_FOURCC},
152     {WINED3DFMT_MULTI2_ARGB8,   WINED3DFMT_FLAG_FOURCC},
153     {WINED3DFMT_G8R8_G8B8,      WINED3DFMT_FLAG_FOURCC},
154     {WINED3DFMT_R8G8_B8G8,      WINED3DFMT_FLAG_FOURCC},
155     {WINED3DFMT_P8_UINT,        WINED3DFMT_FLAG_GETDC},
156     {WINED3DFMT_B8G8R8_UNORM,   WINED3DFMT_FLAG_GETDC},
157     {WINED3DFMT_B8G8R8A8_UNORM, WINED3DFMT_FLAG_GETDC},
158     {WINED3DFMT_B8G8R8X8_UNORM, WINED3DFMT_FLAG_GETDC},
159     {WINED3DFMT_B5G6R5_UNORM,   WINED3DFMT_FLAG_GETDC},
160     {WINED3DFMT_B5G5R5X1_UNORM, WINED3DFMT_FLAG_GETDC},
161     {WINED3DFMT_B5G5R5A1_UNORM, WINED3DFMT_FLAG_GETDC},
162     {WINED3DFMT_B4G4R4A4_UNORM, WINED3DFMT_FLAG_GETDC},
163     {WINED3DFMT_B4G4R4X4_UNORM, WINED3DFMT_FLAG_GETDC},
164     {WINED3DFMT_R8G8B8A8_UNORM, WINED3DFMT_FLAG_GETDC},
165     {WINED3DFMT_R8G8B8X8_UNORM, WINED3DFMT_FLAG_GETDC},
166     {WINED3DFMT_ATI2N,          WINED3DFMT_FLAG_FOURCC},
167     {WINED3DFMT_NVHU,           WINED3DFMT_FLAG_FOURCC},
168     {WINED3DFMT_NVHS,           WINED3DFMT_FLAG_FOURCC},
169 };
170
171 struct wined3d_format_compression_info
172 {
173     WINED3DFORMAT format;
174     UINT block_width;
175     UINT block_height;
176     UINT block_byte_count;
177 };
178
179 static const struct wined3d_format_compression_info format_compression_info[] =
180 {
181     {WINED3DFMT_DXT1,   4,  4,  8},
182     {WINED3DFMT_DXT2,   4,  4,  16},
183     {WINED3DFMT_DXT3,   4,  4,  16},
184     {WINED3DFMT_DXT4,   4,  4,  16},
185     {WINED3DFMT_DXT5,   4,  4,  16},
186     {WINED3DFMT_ATI2N,  4,  4,  16},
187 };
188
189 struct wined3d_format_vertex_info
190 {
191     WINED3DFORMAT format;
192     enum wined3d_ffp_emit_idx emit_idx;
193     GLint component_count;
194     GLenum gl_vtx_type;
195     GLint gl_vtx_format;
196     GLboolean gl_normalized;
197     unsigned int component_size;
198 };
199
200 static const struct wined3d_format_vertex_info format_vertex_info[] =
201 {
202     {WINED3DFMT_R32_FLOAT,          WINED3D_FFP_EMIT_FLOAT1,    1, GL_FLOAT,          1, GL_FALSE, sizeof(float)},
203     {WINED3DFMT_R32G32_FLOAT,       WINED3D_FFP_EMIT_FLOAT2,    2, GL_FLOAT,          2, GL_FALSE, sizeof(float)},
204     {WINED3DFMT_R32G32B32_FLOAT,    WINED3D_FFP_EMIT_FLOAT3,    3, GL_FLOAT,          3, GL_FALSE, sizeof(float)},
205     {WINED3DFMT_R32G32B32A32_FLOAT, WINED3D_FFP_EMIT_FLOAT4,    4, GL_FLOAT,          4, GL_FALSE, sizeof(float)},
206     {WINED3DFMT_B8G8R8A8_UNORM,     WINED3D_FFP_EMIT_D3DCOLOR,  4, GL_UNSIGNED_BYTE,  4, GL_TRUE,  sizeof(BYTE)},
207     {WINED3DFMT_R8G8B8A8_UINT,      WINED3D_FFP_EMIT_UBYTE4,    4, GL_UNSIGNED_BYTE,  4, GL_FALSE, sizeof(BYTE)},
208     {WINED3DFMT_R16G16_SINT,        WINED3D_FFP_EMIT_SHORT2,    2, GL_SHORT,          2, GL_FALSE, sizeof(short int)},
209     {WINED3DFMT_R16G16B16A16_SINT,  WINED3D_FFP_EMIT_SHORT4,    4, GL_SHORT,          4, GL_FALSE, sizeof(short int)},
210     {WINED3DFMT_R8G8B8A8_UNORM,     WINED3D_FFP_EMIT_UBYTE4N,   4, GL_UNSIGNED_BYTE,  4, GL_TRUE,  sizeof(BYTE)},
211     {WINED3DFMT_R16G16_SNORM,       WINED3D_FFP_EMIT_SHORT2N,   2, GL_SHORT,          2, GL_TRUE,  sizeof(short int)},
212     {WINED3DFMT_R16G16B16A16_SNORM, WINED3D_FFP_EMIT_SHORT4N,   4, GL_SHORT,          4, GL_TRUE,  sizeof(short int)},
213     {WINED3DFMT_R16G16_UNORM,       WINED3D_FFP_EMIT_USHORT2N,  2, GL_UNSIGNED_SHORT, 2, GL_TRUE,  sizeof(short int)},
214     {WINED3DFMT_R16G16B16A16_UNORM, WINED3D_FFP_EMIT_USHORT4N,  4, GL_UNSIGNED_SHORT, 4, GL_TRUE,  sizeof(short int)},
215     {WINED3DFMT_R10G10B10A2_UINT,   WINED3D_FFP_EMIT_UDEC3,     3, GL_UNSIGNED_SHORT, 3, GL_FALSE, sizeof(short int)},
216     {WINED3DFMT_R10G10B10A2_SNORM,  WINED3D_FFP_EMIT_DEC3N,     3, GL_SHORT,          3, GL_TRUE,  sizeof(short int)},
217     {WINED3DFMT_R16G16_FLOAT,       WINED3D_FFP_EMIT_FLOAT16_2, 2, GL_FLOAT,          2, GL_FALSE, sizeof(GLhalfNV)},
218     {WINED3DFMT_R16G16B16A16_FLOAT, WINED3D_FFP_EMIT_FLOAT16_4, 4, GL_FLOAT,          4, GL_FALSE, sizeof(GLhalfNV)}
219 };
220
221 typedef struct {
222     WINED3DFORMAT           fmt;
223     GLint                   glInternal, glGammaInternal, rtInternal, glFormat, glType;
224     unsigned int            Flags;
225     GL_SupportedExt extension;
226 } GlPixelFormatDescTemplate;
227
228 /*****************************************************************************
229  * OpenGL format template. Contains unexciting formats which do not need
230  * extension checks. The order in this table is independent of the order in
231  * the table StaticPixelFormatDesc above. Not all formats have to be in this
232  * table.
233  */
234 static const GlPixelFormatDescTemplate gl_formats_template[] = {
235     /* WINED3DFORMAT                    internal                          srgbInternal                       rtInternal
236             format                      type
237             flags
238             extension */
239     /* FourCC formats */
240     /* GL_APPLE_ycbcr_422 claims that its '2YUV' format, which is supported via the UNSIGNED_SHORT_8_8_REV_APPLE type
241      * is equivalent to 'UYVY' format on Windows, and the 'YUVS' via UNSIGNED_SHORT_8_8_APPLE equates to 'YUY2'. The
242      * d3d9 test however shows that the opposite is true. Since the extension is from 2002, it predates the x86 based
243      * Macs, so probably the endianess differs. This could be tested as soon as we have a Windows and MacOS on a big
244      * endian machine
245      */
246     {WINED3DFMT_UYVY,                   GL_LUMINANCE_ALPHA,               GL_LUMINANCE_ALPHA,                     0,
247             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,
248             WINED3DFMT_FLAG_FILTERING,
249             WINED3D_GL_EXT_NONE},
250     {WINED3DFMT_UYVY,                   GL_RGB,                           GL_RGB,                                 0,
251             GL_YCBCR_422_APPLE,         UNSIGNED_SHORT_8_8_APPLE,
252             WINED3DFMT_FLAG_FILTERING,
253             APPLE_YCBCR_422},
254     {WINED3DFMT_YUY2,                   GL_LUMINANCE_ALPHA,               GL_LUMINANCE_ALPHA,                     0,
255             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,
256             WINED3DFMT_FLAG_FILTERING,
257             WINED3D_GL_EXT_NONE},
258     {WINED3DFMT_YUY2,                   GL_RGB,                           GL_RGB,                                 0,
259             GL_YCBCR_422_APPLE,         UNSIGNED_SHORT_8_8_REV_APPLE,
260             WINED3DFMT_FLAG_FILTERING,
261             APPLE_YCBCR_422},
262     {WINED3DFMT_YV12,                   GL_ALPHA,                         GL_ALPHA,                               0,
263             GL_ALPHA,                   GL_UNSIGNED_BYTE,
264             WINED3DFMT_FLAG_FILTERING,
265             WINED3D_GL_EXT_NONE},
266     {WINED3DFMT_DXT1,                   GL_COMPRESSED_RGBA_S3TC_DXT1_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT, 0,
267             GL_RGBA,                    GL_UNSIGNED_BYTE,
268             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
269             EXT_TEXTURE_COMPRESSION_S3TC},
270     {WINED3DFMT_DXT2,                   GL_COMPRESSED_RGBA_S3TC_DXT3_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT, 0,
271             GL_RGBA,                    GL_UNSIGNED_BYTE,
272             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
273             EXT_TEXTURE_COMPRESSION_S3TC},
274     {WINED3DFMT_DXT3,                   GL_COMPRESSED_RGBA_S3TC_DXT3_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT, 0,
275             GL_RGBA,                    GL_UNSIGNED_BYTE,
276             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
277             EXT_TEXTURE_COMPRESSION_S3TC},
278     {WINED3DFMT_DXT4,                   GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, 0,
279             GL_RGBA,                    GL_UNSIGNED_BYTE,
280             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
281             EXT_TEXTURE_COMPRESSION_S3TC},
282     {WINED3DFMT_DXT5,                   GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, 0,
283             GL_RGBA,                    GL_UNSIGNED_BYTE,
284             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
285             EXT_TEXTURE_COMPRESSION_S3TC},
286     /* IEEE formats */
287     {WINED3DFMT_R32_FLOAT,              GL_RGB32F_ARB,                    GL_RGB32F_ARB,                          0,
288             GL_RED,                     GL_FLOAT,
289             WINED3DFMT_FLAG_RENDERTARGET,
290             ARB_TEXTURE_FLOAT},
291     {WINED3DFMT_R32_FLOAT,              GL_R32F,                          GL_R32F,                                0,
292             GL_RED,                     GL_FLOAT,
293             WINED3DFMT_FLAG_RENDERTARGET,
294             ARB_TEXTURE_RG},
295     {WINED3DFMT_R32G32_FLOAT,           GL_RGB32F_ARB,                    GL_RGB32F_ARB,                          0,
296             GL_RGB,                     GL_FLOAT,
297             WINED3DFMT_FLAG_RENDERTARGET,
298             ARB_TEXTURE_FLOAT},
299     {WINED3DFMT_R32G32_FLOAT,           GL_RG32F,                         GL_RG32F,                               0,
300             GL_RG,                      GL_FLOAT,
301             WINED3DFMT_FLAG_RENDERTARGET,
302             ARB_TEXTURE_RG},
303     {WINED3DFMT_R32G32B32A32_FLOAT,     GL_RGBA32F_ARB,                   GL_RGBA32F_ARB,                         0,
304             GL_RGBA,                    GL_FLOAT,
305             WINED3DFMT_FLAG_RENDERTARGET,
306             ARB_TEXTURE_FLOAT},
307     /* Float */
308     {WINED3DFMT_R16_FLOAT,              GL_RGB16F_ARB,                    GL_RGB16F_ARB,                          0,
309             GL_RED,                     GL_HALF_FLOAT_ARB,
310             WINED3DFMT_FLAG_RENDERTARGET,
311             ARB_TEXTURE_FLOAT},
312     {WINED3DFMT_R16_FLOAT,              GL_R16F,                          GL_R16F,                                0,
313             GL_RED,                     GL_HALF_FLOAT_ARB,
314             WINED3DFMT_FLAG_RENDERTARGET,
315             ARB_TEXTURE_RG},
316     {WINED3DFMT_R16G16_FLOAT,           GL_RGB16F_ARB,                    GL_RGB16F_ARB,                          0,
317             GL_RGB,                     GL_HALF_FLOAT_ARB,
318             WINED3DFMT_FLAG_RENDERTARGET,
319             ARB_TEXTURE_FLOAT},
320     {WINED3DFMT_R16G16_FLOAT,           GL_RG16F,                         GL_RG16F,                               0,
321             GL_RG,                      GL_HALF_FLOAT_ARB,
322             WINED3DFMT_FLAG_RENDERTARGET,
323             ARB_TEXTURE_RG},
324     {WINED3DFMT_R16G16B16A16_FLOAT,     GL_RGBA16F_ARB,                   GL_RGBA16F_ARB,                         0,
325             GL_RGBA,                    GL_HALF_FLOAT_ARB,
326             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_RENDERTARGET,
327             ARB_TEXTURE_FLOAT},
328     /* Palettized formats */
329     {WINED3DFMT_P8_UINT,                GL_RGBA,                          GL_RGBA,                                0,
330             GL_RGBA,                    GL_UNSIGNED_BYTE,
331             0,
332             ARB_FRAGMENT_PROGRAM},
333     {WINED3DFMT_P8_UINT,                GL_COLOR_INDEX8_EXT,              GL_COLOR_INDEX8_EXT,                    0,
334             GL_COLOR_INDEX,             GL_UNSIGNED_BYTE,
335             0,
336             EXT_PALETTED_TEXTURE},
337     /* Standard ARGB formats */
338     {WINED3DFMT_B8G8R8_UNORM,           GL_RGB8,                          GL_RGB8,                                0,
339             GL_BGR,                     GL_UNSIGNED_BYTE,
340             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
341             WINED3D_GL_EXT_NONE},
342     {WINED3DFMT_B8G8R8A8_UNORM,         GL_RGBA8,                         GL_SRGB8_ALPHA8_EXT,                    0,
343             GL_BGRA,                    GL_UNSIGNED_INT_8_8_8_8_REV,
344             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
345             WINED3D_GL_EXT_NONE},
346     {WINED3DFMT_B8G8R8X8_UNORM,         GL_RGB8,                          GL_SRGB8_EXT,                           0,
347             GL_BGRA,                    GL_UNSIGNED_INT_8_8_8_8_REV,
348             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
349             WINED3D_GL_EXT_NONE},
350     {WINED3DFMT_B5G6R5_UNORM,           GL_RGB5,                          GL_RGB5,                          GL_RGB8,
351             GL_RGB,                     GL_UNSIGNED_SHORT_5_6_5,
352             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
353             WINED3D_GL_EXT_NONE},
354     {WINED3DFMT_B5G5R5X1_UNORM,         GL_RGB5,                          GL_RGB5_A1,                             0,
355             GL_BGRA,                    GL_UNSIGNED_SHORT_1_5_5_5_REV,
356             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
357             WINED3D_GL_EXT_NONE},
358     {WINED3DFMT_B5G5R5A1_UNORM,         GL_RGB5_A1,                       GL_RGB5_A1,                             0,
359             GL_BGRA,                    GL_UNSIGNED_SHORT_1_5_5_5_REV,
360             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
361             WINED3D_GL_EXT_NONE},
362     {WINED3DFMT_B4G4R4A4_UNORM,         GL_RGBA4,                         GL_SRGB8_ALPHA8_EXT,                    0,
363             GL_BGRA,                    GL_UNSIGNED_SHORT_4_4_4_4_REV,
364             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
365             WINED3D_GL_EXT_NONE},
366     {WINED3DFMT_B2G3R3_UNORM,           GL_R3_G3_B2,                      GL_R3_G3_B2,                            0,
367             GL_RGB,                     GL_UNSIGNED_BYTE_3_3_2,
368             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING,
369             WINED3D_GL_EXT_NONE},
370     {WINED3DFMT_A8_UNORM,               GL_ALPHA8,                        GL_ALPHA8,                              0,
371             GL_ALPHA,                   GL_UNSIGNED_BYTE,
372             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING,
373             WINED3D_GL_EXT_NONE},
374     {WINED3DFMT_B4G4R4X4_UNORM,         GL_RGB4,                          GL_RGB4,                                0,
375             GL_BGRA,                    GL_UNSIGNED_SHORT_4_4_4_4_REV,
376             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
377             WINED3D_GL_EXT_NONE},
378     {WINED3DFMT_R10G10B10A2_UNORM,      GL_RGB10_A2,                      GL_RGB10_A2,                            0,
379             GL_RGBA,                    GL_UNSIGNED_INT_2_10_10_10_REV,
380             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
381             WINED3D_GL_EXT_NONE},
382     {WINED3DFMT_R8G8B8A8_UNORM,         GL_RGBA8,                         GL_RGBA8,                               0,
383             GL_RGBA,                    GL_UNSIGNED_INT_8_8_8_8_REV,
384             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
385             WINED3D_GL_EXT_NONE},
386     {WINED3DFMT_R8G8B8X8_UNORM,         GL_RGB8,                          GL_RGB8,                                0,
387             GL_RGBA,                    GL_UNSIGNED_INT_8_8_8_8_REV,
388             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
389             WINED3D_GL_EXT_NONE},
390     {WINED3DFMT_R16G16_UNORM,           GL_RGB16,                         GL_RGB16,                       GL_RGBA16,
391             GL_RGB,                     GL_UNSIGNED_SHORT,
392             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
393             WINED3D_GL_EXT_NONE},
394     {WINED3DFMT_B10G10R10A2_UNORM,      GL_RGB10_A2,                      GL_RGB10_A2,                            0,
395             GL_BGRA,                    GL_UNSIGNED_INT_2_10_10_10_REV,
396             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
397             WINED3D_GL_EXT_NONE},
398     {WINED3DFMT_R16G16B16A16_UNORM,     GL_RGBA16,                        GL_RGBA16,                              0,
399             GL_RGBA,                    GL_UNSIGNED_SHORT,
400             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
401             WINED3D_GL_EXT_NONE},
402     /* Luminance */
403     {WINED3DFMT_L8_UNORM,               GL_LUMINANCE8,                    GL_SLUMINANCE8_EXT,                     0,
404             GL_LUMINANCE,               GL_UNSIGNED_BYTE,
405             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
406             WINED3D_GL_EXT_NONE},
407     {WINED3DFMT_L8A8_UNORM,             GL_LUMINANCE8_ALPHA8,             GL_SLUMINANCE8_ALPHA8_EXT,              0,
408             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,
409             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
410             WINED3D_GL_EXT_NONE},
411     {WINED3DFMT_L4A4_UNORM,             GL_LUMINANCE4_ALPHA4,             GL_LUMINANCE4_ALPHA4,                   0,
412             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,
413             0,
414             WINED3D_GL_EXT_NONE},
415     /* Bump mapping stuff */
416     {WINED3DFMT_R8G8_SNORM,             GL_RGB8,                          GL_RGB8,                                0,
417             GL_BGR,                     GL_UNSIGNED_BYTE,
418             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
419             WINED3D_GL_EXT_NONE},
420     {WINED3DFMT_R8G8_SNORM,             GL_DSDT8_NV,                      GL_DSDT8_NV,                            0,
421             GL_DSDT_NV,                 GL_BYTE,
422             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
423             NV_TEXTURE_SHADER},
424     {WINED3DFMT_R5G5_SNORM_L6_UNORM,    GL_RGB5,                          GL_RGB5,                                0,
425             GL_RGB,                     GL_UNSIGNED_SHORT_5_6_5,
426             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
427             WINED3D_GL_EXT_NONE},
428     {WINED3DFMT_R5G5_SNORM_L6_UNORM,    GL_DSDT8_MAG8_NV,                 GL_DSDT8_MAG8_NV,                       0,
429             GL_DSDT_MAG_NV,             GL_BYTE,
430             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
431             NV_TEXTURE_SHADER},
432     {WINED3DFMT_R8G8_SNORM_L8X8_UNORM,  GL_RGB8,                          GL_RGB8,                                0,
433             GL_BGRA,                    GL_UNSIGNED_INT_8_8_8_8_REV,
434             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
435             WINED3D_GL_EXT_NONE},
436     {WINED3DFMT_R8G8_SNORM_L8X8_UNORM,  GL_DSDT8_MAG8_INTENSITY8_NV,      GL_DSDT8_MAG8_INTENSITY8_NV,            0,
437             GL_DSDT_MAG_VIB_NV,         GL_UNSIGNED_INT_8_8_S8_S8_REV_NV,
438             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
439             NV_TEXTURE_SHADER},
440     {WINED3DFMT_R8G8B8A8_SNORM,         GL_RGBA8,                         GL_RGBA8,                               0,
441             GL_BGRA,                    GL_UNSIGNED_BYTE,
442             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
443             WINED3D_GL_EXT_NONE},
444     {WINED3DFMT_R8G8B8A8_SNORM,         GL_SIGNED_RGBA8_NV,               GL_SIGNED_RGBA8_NV,                     0,
445             GL_RGBA,                    GL_BYTE,
446             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
447             NV_TEXTURE_SHADER},
448     {WINED3DFMT_R16G16_SNORM,           GL_RGB16,                         GL_RGB16,                               0,
449             GL_BGR,                     GL_UNSIGNED_SHORT,
450             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
451             WINED3D_GL_EXT_NONE},
452     {WINED3DFMT_R16G16_SNORM,           GL_SIGNED_HILO16_NV,              GL_SIGNED_HILO16_NV,                    0,
453             GL_HILO_NV,                 GL_SHORT,
454             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
455             NV_TEXTURE_SHADER},
456     /* Depth stencil formats */
457     {WINED3DFMT_D16_LOCKABLE,           GL_DEPTH_COMPONENT24_ARB,         GL_DEPTH_COMPONENT24_ARB,               0,
458             GL_DEPTH_COMPONENT,         GL_UNSIGNED_SHORT,
459             WINED3DFMT_FLAG_DEPTH,
460             ARB_DEPTH_TEXTURE},
461     {WINED3DFMT_D32_UNORM,              GL_DEPTH_COMPONENT32_ARB,         GL_DEPTH_COMPONENT32_ARB,               0,
462             GL_DEPTH_COMPONENT,         GL_UNSIGNED_INT,
463             WINED3DFMT_FLAG_DEPTH,
464             ARB_DEPTH_TEXTURE},
465     {WINED3DFMT_S1_UINT_D15_UNORM,      GL_DEPTH_COMPONENT24_ARB,         GL_DEPTH_COMPONENT24_ARB,               0,
466             GL_DEPTH_COMPONENT,         GL_UNSIGNED_SHORT,
467             WINED3DFMT_FLAG_DEPTH,
468             ARB_DEPTH_TEXTURE},
469     {WINED3DFMT_S1_UINT_D15_UNORM,      GL_DEPTH24_STENCIL8_EXT,          GL_DEPTH24_STENCIL8_EXT,                0,
470             GL_DEPTH_STENCIL_EXT,       GL_UNSIGNED_INT_24_8_EXT,
471             WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
472             EXT_PACKED_DEPTH_STENCIL},
473     {WINED3DFMT_S1_UINT_D15_UNORM,      GL_DEPTH24_STENCIL8,              GL_DEPTH24_STENCIL8,                    0,
474             GL_DEPTH_STENCIL,           GL_UNSIGNED_INT_24_8,
475             WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
476             ARB_FRAMEBUFFER_OBJECT},
477     {WINED3DFMT_D24_UNORM_S8_UINT,      GL_DEPTH_COMPONENT24_ARB,         GL_DEPTH_COMPONENT24_ARB,               0,
478             GL_DEPTH_COMPONENT,         GL_UNSIGNED_INT,
479             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH,
480             ARB_DEPTH_TEXTURE},
481     {WINED3DFMT_D24_UNORM_S8_UINT,      GL_DEPTH24_STENCIL8_EXT,          GL_DEPTH24_STENCIL8_EXT,                0,
482             GL_DEPTH_STENCIL_EXT,       GL_UNSIGNED_INT_24_8_EXT,
483             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
484             EXT_PACKED_DEPTH_STENCIL},
485     {WINED3DFMT_D24_UNORM_S8_UINT,      GL_DEPTH24_STENCIL8,              GL_DEPTH24_STENCIL8,                    0,
486             GL_DEPTH_STENCIL,           GL_UNSIGNED_INT_24_8,
487             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
488             ARB_FRAMEBUFFER_OBJECT},
489     {WINED3DFMT_X8D24_UNORM,            GL_DEPTH_COMPONENT24_ARB,         GL_DEPTH_COMPONENT24_ARB,               0,
490             GL_DEPTH_COMPONENT,         GL_UNSIGNED_INT,
491             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH,
492             ARB_DEPTH_TEXTURE},
493     {WINED3DFMT_S4X4_UINT_D24_UNORM,    GL_DEPTH_COMPONENT24_ARB,         GL_DEPTH_COMPONENT24_ARB,               0,
494             GL_DEPTH_COMPONENT,         GL_UNSIGNED_INT,
495             WINED3DFMT_FLAG_DEPTH,
496             ARB_DEPTH_TEXTURE},
497     {WINED3DFMT_S4X4_UINT_D24_UNORM,    GL_DEPTH24_STENCIL8_EXT,          GL_DEPTH24_STENCIL8_EXT,                0,
498             GL_DEPTH_STENCIL_EXT,       GL_UNSIGNED_INT_24_8_EXT,
499             WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
500             EXT_PACKED_DEPTH_STENCIL},
501     {WINED3DFMT_S4X4_UINT_D24_UNORM,    GL_DEPTH24_STENCIL8,              GL_DEPTH24_STENCIL8,                    0,
502             GL_DEPTH_STENCIL,           GL_UNSIGNED_INT_24_8,
503             WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
504             ARB_FRAMEBUFFER_OBJECT},
505     {WINED3DFMT_D16_UNORM,              GL_DEPTH_COMPONENT24_ARB,         GL_DEPTH_COMPONENT24_ARB,               0,
506             GL_DEPTH_COMPONENT,         GL_UNSIGNED_SHORT,
507             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH,
508             ARB_DEPTH_TEXTURE},
509     {WINED3DFMT_L16_UNORM,              GL_LUMINANCE16,                   GL_LUMINANCE16,                         0,
510             GL_LUMINANCE,               GL_UNSIGNED_SHORT,
511             WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
512             WINED3D_GL_EXT_NONE},
513     {WINED3DFMT_D32_FLOAT,              GL_DEPTH_COMPONENT32F,            GL_DEPTH_COMPONENT32F,                  0,
514             GL_DEPTH_COMPONENT,         GL_FLOAT,
515             WINED3DFMT_FLAG_DEPTH,
516             ARB_DEPTH_BUFFER_FLOAT},
517     {WINED3DFMT_S8_UINT_D24_FLOAT,      GL_DEPTH32F_STENCIL8,             GL_DEPTH32F_STENCIL8,                   0,
518             GL_DEPTH_STENCIL,           GL_FLOAT_32_UNSIGNED_INT_24_8_REV,
519             WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
520             ARB_DEPTH_BUFFER_FLOAT},
521     /* Vendor-specific formats */
522     {WINED3DFMT_ATI2N,                  GL_COMPRESSED_LUMINANCE_ALPHA_3DC_ATI, GL_COMPRESSED_LUMINANCE_ALPHA_3DC_ATI, 0,
523             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,
524             0,
525             ATI_TEXTURE_COMPRESSION_3DC},
526     {WINED3DFMT_ATI2N,                  GL_COMPRESSED_RED_GREEN_RGTC2_EXT, GL_COMPRESSED_RED_GREEN_RGTC2_EXT,     0,
527             GL_LUMINANCE_ALPHA,         GL_UNSIGNED_BYTE,
528             0,
529             EXT_TEXTURE_COMPRESSION_RGTC},
530 };
531
532 static inline int getFmtIdx(WINED3DFORMAT fmt) {
533     /* First check if the format is at the position of its value.
534      * This will catch the argb formats before the loop is entered
535      */
536     if(fmt < (sizeof(formats) / sizeof(formats[0])) && formats[fmt].format == fmt) {
537         return fmt;
538     } else {
539         unsigned int i;
540         for(i = 0; i < (sizeof(formats) / sizeof(formats[0])); i++) {
541             if(formats[i].format == fmt) {
542                 return i;
543             }
544         }
545     }
546     return -1;
547 }
548
549 static BOOL init_format_base_info(struct wined3d_gl_info *gl_info)
550 {
551     UINT format_count = sizeof(formats) / sizeof(*formats);
552     UINT i;
553
554     gl_info->gl_formats = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, format_count * sizeof(*gl_info->gl_formats));
555     if (!gl_info->gl_formats)
556     {
557         ERR("Failed to allocate memory.\n");
558         return FALSE;
559     }
560
561     for (i = 0; i < format_count; ++i)
562     {
563         struct GlPixelFormatDesc *desc = &gl_info->gl_formats[i];
564         desc->format = formats[i].format;
565         desc->red_mask = formats[i].redMask;
566         desc->green_mask = formats[i].greenMask;
567         desc->blue_mask = formats[i].blueMask;
568         desc->alpha_mask = formats[i].alphaMask;
569         desc->byte_count = formats[i].bpp;
570         desc->depth_size = formats[i].depthSize;
571         desc->stencil_size = formats[i].stencilSize;
572     }
573
574     for (i = 0; i < (sizeof(format_base_flags) / sizeof(*format_base_flags)); ++i)
575     {
576         int fmt_idx = getFmtIdx(format_base_flags[i].format);
577
578         if (fmt_idx == -1)
579         {
580             ERR("Format %s (%#x) not found.\n",
581                     debug_d3dformat(format_base_flags[i].format), format_base_flags[i].format);
582             HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
583             return FALSE;
584         }
585
586         gl_info->gl_formats[fmt_idx].Flags |= format_base_flags[i].flags;
587     }
588
589     return TRUE;
590 }
591
592 static BOOL init_format_compression_info(struct wined3d_gl_info *gl_info)
593 {
594     unsigned int i;
595
596     for (i = 0; i < (sizeof(format_compression_info) / sizeof(*format_compression_info)); ++i)
597     {
598         struct GlPixelFormatDesc *format_desc;
599         int fmt_idx = getFmtIdx(format_compression_info[i].format);
600
601         if (fmt_idx == -1)
602         {
603             ERR("Format %s (%#x) not found.\n",
604                     debug_d3dformat(format_compression_info[i].format), format_compression_info[i].format);
605             return FALSE;
606         }
607
608         format_desc = &gl_info->gl_formats[fmt_idx];
609         format_desc->block_width = format_compression_info[i].block_width;
610         format_desc->block_height = format_compression_info[i].block_height;
611         format_desc->block_byte_count = format_compression_info[i].block_byte_count;
612         format_desc->Flags |= WINED3DFMT_FLAG_COMPRESSED;
613     }
614
615     return TRUE;
616 }
617
618 /* Context activation is done by the caller. */
619 static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct GlPixelFormatDesc *format_desc)
620 {
621     /* Check if the default internal format is supported as a frame buffer
622      * target, otherwise fall back to the render target internal.
623      *
624      * Try to stick to the standard format if possible, this limits precision differences. */
625     GLenum status;
626     GLuint tex;
627
628     ENTER_GL();
629
630     while(glGetError());
631     glDisable(GL_BLEND);
632
633     glGenTextures(1, &tex);
634     glBindTexture(GL_TEXTURE_2D, tex);
635
636     glTexImage2D(GL_TEXTURE_2D, 0, format_desc->glInternal, 16, 16, 0,
637             format_desc->glFormat, format_desc->glType, NULL);
638     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
639     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
640
641     gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, 0);
642
643     status = gl_info->fbo_ops.glCheckFramebufferStatus(GL_FRAMEBUFFER);
644     checkGLcall("Framebuffer format check");
645
646     if (status == GL_FRAMEBUFFER_COMPLETE)
647     {
648         TRACE("Format %s is supported as FBO color attachment\n", debug_d3dformat(format_desc->format));
649         format_desc->Flags |= WINED3DFMT_FLAG_FBO_ATTACHABLE;
650         format_desc->rtInternal = format_desc->glInternal;
651     }
652     else
653     {
654         if (!format_desc->rtInternal)
655         {
656             if (format_desc->Flags & WINED3DFMT_FLAG_RENDERTARGET)
657             {
658                 FIXME("Format %s with rendertarget flag is not supported as FBO color attachment,"
659                         " and no fallback specified.\n", debug_d3dformat(format_desc->format));
660                 format_desc->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
661             }
662             else
663             {
664                 TRACE("Format %s is not supported as FBO color attachment.\n", debug_d3dformat(format_desc->format));
665             }
666             format_desc->rtInternal = format_desc->glInternal;
667         }
668         else
669         {
670             TRACE("Format %s is not supported as FBO color attachment, trying rtInternal format as fallback.\n",
671                     debug_d3dformat(format_desc->format));
672
673             while(glGetError());
674
675             gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0);
676
677             glTexImage2D(GL_TEXTURE_2D, 0, format_desc->rtInternal, 16, 16, 0,
678                     format_desc->glFormat, format_desc->glType, NULL);
679             glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
680             glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
681
682             gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, 0);
683
684             status = gl_info->fbo_ops.glCheckFramebufferStatus(GL_FRAMEBUFFER);
685             checkGLcall("Framebuffer format check");
686
687             if (status == GL_FRAMEBUFFER_COMPLETE)
688             {
689                 TRACE("Format %s rtInternal format is supported as FBO color attachment\n",
690                         debug_d3dformat(format_desc->format));
691             }
692             else
693             {
694                 FIXME("Format %s rtInternal format is not supported as FBO color attachment.\n",
695                         debug_d3dformat(format_desc->format));
696                 format_desc->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
697             }
698         }
699     }
700
701     if (status == GL_FRAMEBUFFER_COMPLETE && format_desc->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING)
702     {
703         GLuint rb;
704
705         if (gl_info->supported[ARB_FRAMEBUFFER_OBJECT]
706                 || gl_info->supported[EXT_PACKED_DEPTH_STENCIL])
707         {
708             gl_info->fbo_ops.glGenRenderbuffers(1, &rb);
709             gl_info->fbo_ops.glBindRenderbuffer(GL_RENDERBUFFER, rb);
710             gl_info->fbo_ops.glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8, 16, 16);
711             gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rb);
712             gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rb);
713             checkGLcall("RB attachment");
714         }
715
716         glEnable(GL_BLEND);
717         glClear(GL_COLOR_BUFFER_BIT);
718         if (glGetError() == GL_INVALID_FRAMEBUFFER_OPERATION)
719         {
720             while(glGetError());
721             TRACE("Format doesn't support post-pixelshader blending.\n");
722             format_desc->Flags &= ~WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING;
723         }
724
725         if (gl_info->supported[ARB_FRAMEBUFFER_OBJECT]
726                 || gl_info->supported[EXT_PACKED_DEPTH_STENCIL])
727         {
728             gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, 0);
729             gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, 0);
730             gl_info->fbo_ops.glDeleteRenderbuffers(1, &rb);
731             checkGLcall("RB cleanup");
732         }
733     }
734
735     glDeleteTextures(1, &tex);
736
737     LEAVE_GL();
738 }
739
740 /* Context activation is done by the caller. */
741 static void init_format_fbo_compat_info(struct wined3d_gl_info *gl_info)
742 {
743     unsigned int i;
744     GLuint fbo;
745
746     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
747     {
748         ENTER_GL();
749
750         gl_info->fbo_ops.glGenFramebuffers(1, &fbo);
751         gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, fbo);
752
753         LEAVE_GL();
754     }
755
756     for (i = 0; i < sizeof(formats) / sizeof(*formats); ++i)
757     {
758         struct GlPixelFormatDesc *desc = &gl_info->gl_formats[i];
759
760         if (!desc->glInternal) continue;
761
762         if (desc->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))
763         {
764             TRACE("Skipping format %s because it's a depth/stencil format.\n",
765                     debug_d3dformat(desc->format));
766             continue;
767         }
768
769         if (desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
770         {
771             TRACE("Skipping format %s because it's a compressed format.\n",
772                     debug_d3dformat(desc->format));
773             continue;
774         }
775
776         if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
777         {
778             TRACE("Checking if format %s is supported as FBO color attachment...\n", debug_d3dformat(desc->format));
779             check_fbo_compat(gl_info, desc);
780         }
781         else
782         {
783             desc->rtInternal = desc->glInternal;
784         }
785     }
786
787     if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
788     {
789         ENTER_GL();
790
791         gl_info->fbo_ops.glDeleteFramebuffers(1, &fbo);
792
793         LEAVE_GL();
794     }
795 }
796
797 static BOOL init_format_texture_info(struct wined3d_gl_info *gl_info)
798 {
799     unsigned int i;
800
801     for (i = 0; i < sizeof(gl_formats_template) / sizeof(gl_formats_template[0]); ++i)
802     {
803         int fmt_idx = getFmtIdx(gl_formats_template[i].fmt);
804         struct GlPixelFormatDesc *desc;
805
806         if (fmt_idx == -1)
807         {
808             ERR("Format %s (%#x) not found.\n",
809                     debug_d3dformat(gl_formats_template[i].fmt), gl_formats_template[i].fmt);
810             return FALSE;
811         }
812
813         if (!gl_info->supported[gl_formats_template[i].extension]) continue;
814
815         desc = &gl_info->gl_formats[fmt_idx];
816         desc->glInternal = gl_formats_template[i].glInternal;
817         desc->glGammaInternal = gl_formats_template[i].glGammaInternal;
818         desc->rtInternal = gl_formats_template[i].rtInternal;
819         desc->glFormat = gl_formats_template[i].glFormat;
820         desc->glType = gl_formats_template[i].glType;
821         desc->color_fixup = COLOR_FIXUP_IDENTITY;
822         desc->Flags |= gl_formats_template[i].Flags;
823         desc->heightscale = 1.0f;
824     }
825
826     return TRUE;
827 }
828
829 static BOOL color_match(DWORD c1, DWORD c2, BYTE max_diff)
830 {
831     if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
832     c1 >>= 8; c2 >>= 8;
833     if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
834     c1 >>= 8; c2 >>= 8;
835     if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
836     c1 >>= 8; c2 >>= 8;
837     if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
838     return TRUE;
839 }
840
841 /* A context is provided by the caller */
842 static BOOL check_filter(const struct wined3d_gl_info *gl_info, GLenum internal)
843 {
844     GLuint tex, fbo, buffer;
845     const DWORD data[] = {0x00000000, 0xffffffff};
846     DWORD readback[16 * 1];
847     BOOL ret = FALSE;
848
849     /* Render a filtered texture and see what happens. This is intended to detect the lack of
850      * float16 filtering on ATI X1000 class cards. The drivers disable filtering instead of
851      * falling back to software. If this changes in the future this code will get fooled and
852      * apps might hit the software path due to incorrectly advertised caps.
853      *
854      * Its unlikely that this changes however. GL Games like Mass Effect depend on the filter
855      * disable fallback, if Apple or ATI ever change the driver behavior they will break more
856      * than Wine. The Linux binary <= r500 driver is not maintained any more anyway
857      */
858
859     ENTER_GL();
860     while(glGetError());
861
862     glGenTextures(1, &buffer);
863     glBindTexture(GL_TEXTURE_2D, buffer);
864     memset(readback, 0x7e, sizeof(readback));
865     glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 16, 1, 0, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, readback);
866     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
867     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
868     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
869     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
870     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
871
872     glGenTextures(1, &tex);
873     glBindTexture(GL_TEXTURE_2D, tex);
874     glTexImage2D(GL_TEXTURE_2D, 0, internal, 2, 1, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, data);
875     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
876     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
877     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
878     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
879     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
880     glEnable(GL_TEXTURE_2D);
881
882     gl_info->fbo_ops.glGenFramebuffers(1, &fbo);
883     gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, fbo);
884     gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, buffer, 0);
885     glDrawBuffer(GL_COLOR_ATTACHMENT0);
886
887     glViewport(0, 0, 16, 1);
888     glDisable(GL_LIGHTING);
889     glMatrixMode(GL_MODELVIEW);
890     glLoadIdentity();
891     glMatrixMode(GL_PROJECTION);
892     glLoadIdentity();
893
894     glClearColor(0, 1, 0, 0);
895     glClear(GL_COLOR_BUFFER_BIT);
896
897     glBegin(GL_TRIANGLE_STRIP);
898     glTexCoord2f(0.0, 0.0);
899     glVertex2f(-1.0f, -1.0f);
900     glTexCoord2f(1.0, 0.0);
901     glVertex2f(1.0f, -1.0f);
902     glTexCoord2f(0.0, 1.0);
903     glVertex2f(-1.0f, 1.0f);
904     glTexCoord2f(1.0, 1.0);
905     glVertex2f(1.0f, 1.0f);
906     glEnd();
907
908     glBindTexture(GL_TEXTURE_2D, buffer);
909     memset(readback, 0x7f, sizeof(readback));
910     glGetTexImage(GL_TEXTURE_2D, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, readback);
911     if(color_match(readback[6], 0xffffffff, 5) || color_match(readback[6], 0x00000000, 5) ||
912        color_match(readback[9], 0xffffffff, 5) || color_match(readback[9], 0x00000000, 5))
913     {
914         TRACE("Read back colors 0x%08x and 0x%08x close to unfiltered color, asuming no filtering\n",
915               readback[6], readback[9]);
916         ret = FALSE;
917     }
918     else
919     {
920         TRACE("Read back colors are 0x%08x and 0x%08x, assuming texture is filtered\n",
921               readback[6], readback[9]);
922         ret = TRUE;
923     }
924
925     gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, 0);
926     gl_info->fbo_ops.glDeleteFramebuffers(1, &fbo);
927     glDeleteTextures(1, &tex);
928     glDeleteTextures(1, &buffer);
929
930     if(glGetError())
931     {
932         FIXME("Error during filtering test for format %x, returning no filtering\n", internal);
933         ret = FALSE;
934     }
935     LEAVE_GL();
936     return ret;
937 }
938
939 static void init_format_filter_info(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor)
940 {
941     unsigned int fmt_idx, i;
942     WINED3DFORMAT fmts16[] = {
943         WINED3DFMT_R16_FLOAT,
944         WINED3DFMT_R16G16_FLOAT,
945         WINED3DFMT_R16G16B16A16_FLOAT,
946     };
947     BOOL filtered;
948     struct GlPixelFormatDesc *desc;
949
950     if(wined3d_settings.offscreen_rendering_mode != ORM_FBO)
951     {
952         WARN("No FBO support, or no FBO ORM, guessing filter info from GL caps\n");
953         if (vendor == VENDOR_NVIDIA && gl_info->supported[ARB_TEXTURE_FLOAT])
954         {
955             TRACE("Nvidia card with texture_float support: Assuming float16 blending\n");
956             filtered = TRUE;
957         }
958         else if (gl_info->limits.glsl_varyings > 44)
959         {
960             TRACE("More than 44 GLSL varyings - assuming d3d10 card with float16 blending\n");
961             filtered = TRUE;
962         }
963         else
964         {
965             TRACE("Assuming no float16 blending\n");
966             filtered = FALSE;
967         }
968
969         if(filtered)
970         {
971             for(i = 0; i < (sizeof(fmts16) / sizeof(*fmts16)); i++)
972             {
973                 fmt_idx = getFmtIdx(fmts16[i]);
974                 gl_info->gl_formats[fmt_idx].Flags |= WINED3DFMT_FLAG_FILTERING;
975             }
976         }
977         return;
978     }
979
980     for(i = 0; i < (sizeof(fmts16) / sizeof(*fmts16)); i++)
981     {
982         fmt_idx = getFmtIdx(fmts16[i]);
983         desc = &gl_info->gl_formats[fmt_idx];
984         if(!desc->glInternal) continue; /* Not supported by GL */
985
986         filtered = check_filter(gl_info, gl_info->gl_formats[fmt_idx].glInternal);
987         if(filtered)
988         {
989             TRACE("Format %s supports filtering\n", debug_d3dformat(fmts16[i]));
990             desc->Flags |= WINED3DFMT_FLAG_FILTERING;
991         }
992         else
993         {
994             TRACE("Format %s does not support filtering\n", debug_d3dformat(fmts16[i]));
995         }
996     }
997 }
998
999 static void apply_format_fixups(struct wined3d_gl_info *gl_info)
1000 {
1001     int idx;
1002
1003     idx = getFmtIdx(WINED3DFMT_R16_FLOAT);
1004     gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1005             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1006
1007     idx = getFmtIdx(WINED3DFMT_R32_FLOAT);
1008     gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1009             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1010
1011     idx = getFmtIdx(WINED3DFMT_R16G16_UNORM);
1012     gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1013             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1014
1015     idx = getFmtIdx(WINED3DFMT_R16G16_FLOAT);
1016     gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1017             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1018
1019     idx = getFmtIdx(WINED3DFMT_R32G32_FLOAT);
1020     gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1021             0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1022
1023     /* V8U8 is supported natively by GL_ATI_envmap_bumpmap and GL_NV_texture_shader.
1024      * V16U16 is only supported by GL_NV_texture_shader. The formats need fixup if
1025      * their extensions are not available. GL_ATI_envmap_bumpmap is not used because
1026      * the only driver that implements it(fglrx) has a buggy implementation.
1027      *
1028      * V8U8 and V16U16 need a fixup of the undefined blue channel. OpenGL
1029      * returns 0.0 when sampling from it, DirectX 1.0. So we always have in-shader
1030      * conversion for this format.
1031      */
1032     if (!gl_info->supported[NV_TEXTURE_SHADER])
1033     {
1034         idx = getFmtIdx(WINED3DFMT_R8G8_SNORM);
1035         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1036                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1037         idx = getFmtIdx(WINED3DFMT_R16G16_SNORM);
1038         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1039                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1040     }
1041     else
1042     {
1043         idx = getFmtIdx(WINED3DFMT_R8G8_SNORM);
1044         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1045                 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1046         idx = getFmtIdx(WINED3DFMT_R16G16_SNORM);
1047         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1048                 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1049     }
1050
1051     if (!gl_info->supported[NV_TEXTURE_SHADER])
1052     {
1053         /* If GL_NV_texture_shader is not supported, those formats are converted, incompatibly
1054          * with each other
1055          */
1056         idx = getFmtIdx(WINED3DFMT_R5G5_SNORM_L6_UNORM);
1057         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1058                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Z, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE);
1059         idx = getFmtIdx(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
1060         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1061                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_Z, 0, CHANNEL_SOURCE_W);
1062         idx = getFmtIdx(WINED3DFMT_R8G8B8A8_SNORM);
1063         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1064                 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 1, CHANNEL_SOURCE_Z, 1, CHANNEL_SOURCE_W);
1065     }
1066     else
1067     {
1068         /* If GL_NV_texture_shader is supported, WINED3DFMT_L6V5U5 and WINED3DFMT_X8L8V8U8
1069          * are converted at surface loading time, but they do not need any modification in
1070          * the shader, thus they are compatible with all WINED3DFMT_UNKNOWN group formats.
1071          * WINED3DFMT_Q8W8V8U8 doesn't even need load-time conversion
1072          */
1073     }
1074
1075     if (gl_info->supported[EXT_TEXTURE_COMPRESSION_RGTC])
1076     {
1077         idx = getFmtIdx(WINED3DFMT_ATI2N);
1078         gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1079                 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1080     }
1081     else if (gl_info->supported[ATI_TEXTURE_COMPRESSION_3DC])
1082     {
1083         idx = getFmtIdx(WINED3DFMT_ATI2N);
1084         gl_info->gl_formats[idx].color_fixup= create_color_fixup_desc(
1085                 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_W, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1086     }
1087
1088     if (!gl_info->supported[APPLE_YCBCR_422])
1089     {
1090         idx = getFmtIdx(WINED3DFMT_YUY2);
1091         gl_info->gl_formats[idx].color_fixup = create_yuv_fixup_desc(YUV_FIXUP_YUY2);
1092
1093         idx = getFmtIdx(WINED3DFMT_UYVY);
1094         gl_info->gl_formats[idx].color_fixup = create_yuv_fixup_desc(YUV_FIXUP_UYVY);
1095     }
1096
1097     idx = getFmtIdx(WINED3DFMT_YV12);
1098     gl_info->gl_formats[idx].heightscale = 1.5f;
1099     gl_info->gl_formats[idx].color_fixup = create_yuv_fixup_desc(YUV_FIXUP_YV12);
1100
1101     if (gl_info->supported[ARB_VERTEX_ARRAY_BGRA])
1102     {
1103         idx = getFmtIdx(WINED3DFMT_B8G8R8A8_UNORM);
1104         gl_info->gl_formats[idx].gl_vtx_format = GL_BGRA;
1105     }
1106
1107     if (gl_info->supported[ARB_HALF_FLOAT_VERTEX])
1108     {
1109         /* Do not change the size of the type, it is CPU side. We have to change the GPU-side information though.
1110          * It is the job of the vertex buffer code to make sure that the vbos have the right format */
1111         idx = getFmtIdx(WINED3DFMT_R16G16_FLOAT);
1112         gl_info->gl_formats[idx].gl_vtx_type = GL_HALF_FLOAT; /* == GL_HALF_FLOAT_NV */
1113
1114         idx = getFmtIdx(WINED3DFMT_R16G16B16A16_FLOAT);
1115         gl_info->gl_formats[idx].gl_vtx_type = GL_HALF_FLOAT;
1116     }
1117 }
1118
1119 static BOOL init_format_vertex_info(struct wined3d_gl_info *gl_info)
1120 {
1121     unsigned int i;
1122
1123     for (i = 0; i < (sizeof(format_vertex_info) / sizeof(*format_vertex_info)); ++i)
1124     {
1125         struct GlPixelFormatDesc *format_desc;
1126         int fmt_idx = getFmtIdx(format_vertex_info[i].format);
1127
1128         if (fmt_idx == -1)
1129         {
1130             ERR("Format %s (%#x) not found.\n",
1131                     debug_d3dformat(format_vertex_info[i].format), format_vertex_info[i].format);
1132             return FALSE;
1133         }
1134
1135         format_desc = &gl_info->gl_formats[fmt_idx];
1136         format_desc->emit_idx = format_vertex_info[i].emit_idx;
1137         format_desc->component_count = format_vertex_info[i].component_count;
1138         format_desc->gl_vtx_type = format_vertex_info[i].gl_vtx_type;
1139         format_desc->gl_vtx_format = format_vertex_info[i].gl_vtx_format;
1140         format_desc->gl_normalized = format_vertex_info[i].gl_normalized;
1141         format_desc->component_size = format_vertex_info[i].component_size;
1142     }
1143
1144     return TRUE;
1145 }
1146
1147 BOOL initPixelFormatsNoGL(struct wined3d_gl_info *gl_info)
1148 {
1149     if (!init_format_base_info(gl_info)) return FALSE;
1150
1151     if (!init_format_compression_info(gl_info))
1152     {
1153         HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
1154         gl_info->gl_formats = NULL;
1155         return FALSE;
1156     }
1157
1158     return TRUE;
1159 }
1160
1161 /* Context activation is done by the caller. */
1162 BOOL initPixelFormats(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor)
1163 {
1164     if (!init_format_base_info(gl_info)) return FALSE;
1165
1166     if (!init_format_compression_info(gl_info)) goto fail;
1167     if (!init_format_texture_info(gl_info)) goto fail;
1168     if (!init_format_vertex_info(gl_info)) goto fail;
1169
1170     apply_format_fixups(gl_info);
1171     init_format_fbo_compat_info(gl_info);
1172     init_format_filter_info(gl_info, vendor);
1173
1174     return TRUE;
1175
1176 fail:
1177     HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
1178     gl_info->gl_formats = NULL;
1179     return FALSE;
1180 }
1181
1182 const struct GlPixelFormatDesc *getFormatDescEntry(WINED3DFORMAT fmt, const struct wined3d_gl_info *gl_info)
1183 {
1184     int idx = getFmtIdx(fmt);
1185
1186     if(idx == -1) {
1187         FIXME("Can't find format %s(%d) in the format lookup table\n", debug_d3dformat(fmt), fmt);
1188         /* Get the caller a valid pointer */
1189         idx = getFmtIdx(WINED3DFMT_UNKNOWN);
1190     }
1191
1192     return &gl_info->gl_formats[idx];
1193 }
1194
1195 /*****************************************************************************
1196  * Trace formatting of useful values
1197  */
1198 const char* debug_d3dformat(WINED3DFORMAT fmt) {
1199   switch (fmt) {
1200 #define FMT_TO_STR(fmt) case fmt: return #fmt
1201     FMT_TO_STR(WINED3DFMT_UNKNOWN);
1202     FMT_TO_STR(WINED3DFMT_B8G8R8_UNORM);
1203     FMT_TO_STR(WINED3DFMT_B5G5R5X1_UNORM);
1204     FMT_TO_STR(WINED3DFMT_B4G4R4A4_UNORM);
1205     FMT_TO_STR(WINED3DFMT_B2G3R3_UNORM);
1206     FMT_TO_STR(WINED3DFMT_B2G3R3A8_UNORM);
1207     FMT_TO_STR(WINED3DFMT_B4G4R4X4_UNORM);
1208     FMT_TO_STR(WINED3DFMT_R8G8B8X8_UNORM);
1209     FMT_TO_STR(WINED3DFMT_B10G10R10A2_UNORM);
1210     FMT_TO_STR(WINED3DFMT_P8_UINT_A8_UNORM);
1211     FMT_TO_STR(WINED3DFMT_P8_UINT);
1212     FMT_TO_STR(WINED3DFMT_L8_UNORM);
1213     FMT_TO_STR(WINED3DFMT_L8A8_UNORM);
1214     FMT_TO_STR(WINED3DFMT_L4A4_UNORM);
1215     FMT_TO_STR(WINED3DFMT_R5G5_SNORM_L6_UNORM);
1216     FMT_TO_STR(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
1217     FMT_TO_STR(WINED3DFMT_R10G11B11_SNORM);
1218     FMT_TO_STR(WINED3DFMT_R10G10B10_SNORM_A2_UNORM);
1219     FMT_TO_STR(WINED3DFMT_UYVY);
1220     FMT_TO_STR(WINED3DFMT_YUY2);
1221     FMT_TO_STR(WINED3DFMT_YV12);
1222     FMT_TO_STR(WINED3DFMT_DXT1);
1223     FMT_TO_STR(WINED3DFMT_DXT2);
1224     FMT_TO_STR(WINED3DFMT_DXT3);
1225     FMT_TO_STR(WINED3DFMT_DXT4);
1226     FMT_TO_STR(WINED3DFMT_DXT5);
1227     FMT_TO_STR(WINED3DFMT_MULTI2_ARGB8);
1228     FMT_TO_STR(WINED3DFMT_G8R8_G8B8);
1229     FMT_TO_STR(WINED3DFMT_R8G8_B8G8);
1230     FMT_TO_STR(WINED3DFMT_D16_LOCKABLE);
1231     FMT_TO_STR(WINED3DFMT_D32_UNORM);
1232     FMT_TO_STR(WINED3DFMT_S1_UINT_D15_UNORM);
1233     FMT_TO_STR(WINED3DFMT_X8D24_UNORM);
1234     FMT_TO_STR(WINED3DFMT_S4X4_UINT_D24_UNORM);
1235     FMT_TO_STR(WINED3DFMT_L16_UNORM);
1236     FMT_TO_STR(WINED3DFMT_S8_UINT_D24_FLOAT);
1237     FMT_TO_STR(WINED3DFMT_VERTEXDATA);
1238     FMT_TO_STR(WINED3DFMT_R8G8_SNORM_Cx);
1239     FMT_TO_STR(WINED3DFMT_ATI2N);
1240     FMT_TO_STR(WINED3DFMT_NVHU);
1241     FMT_TO_STR(WINED3DFMT_NVHS);
1242     FMT_TO_STR(WINED3DFMT_R32G32B32A32_TYPELESS);
1243     FMT_TO_STR(WINED3DFMT_R32G32B32A32_FLOAT);
1244     FMT_TO_STR(WINED3DFMT_R32G32B32A32_UINT);
1245     FMT_TO_STR(WINED3DFMT_R32G32B32A32_SINT);
1246     FMT_TO_STR(WINED3DFMT_R32G32B32_TYPELESS);
1247     FMT_TO_STR(WINED3DFMT_R32G32B32_FLOAT);
1248     FMT_TO_STR(WINED3DFMT_R32G32B32_UINT);
1249     FMT_TO_STR(WINED3DFMT_R32G32B32_SINT);
1250     FMT_TO_STR(WINED3DFMT_R16G16B16A16_TYPELESS);
1251     FMT_TO_STR(WINED3DFMT_R16G16B16A16_FLOAT);
1252     FMT_TO_STR(WINED3DFMT_R16G16B16A16_UNORM);
1253     FMT_TO_STR(WINED3DFMT_R16G16B16A16_UINT);
1254     FMT_TO_STR(WINED3DFMT_R16G16B16A16_SNORM);
1255     FMT_TO_STR(WINED3DFMT_R16G16B16A16_SINT);
1256     FMT_TO_STR(WINED3DFMT_R32G32_TYPELESS);
1257     FMT_TO_STR(WINED3DFMT_R32G32_FLOAT);
1258     FMT_TO_STR(WINED3DFMT_R32G32_UINT);
1259     FMT_TO_STR(WINED3DFMT_R32G32_SINT);
1260     FMT_TO_STR(WINED3DFMT_R32G8X24_TYPELESS);
1261     FMT_TO_STR(WINED3DFMT_D32_FLOAT_S8X24_UINT);
1262     FMT_TO_STR(WINED3DFMT_R32_FLOAT_X8X24_TYPELESS);
1263     FMT_TO_STR(WINED3DFMT_X32_TYPELESS_G8X24_UINT);
1264     FMT_TO_STR(WINED3DFMT_R10G10B10A2_TYPELESS);
1265     FMT_TO_STR(WINED3DFMT_R10G10B10A2_UNORM);
1266     FMT_TO_STR(WINED3DFMT_R10G10B10A2_UINT);
1267     FMT_TO_STR(WINED3DFMT_R10G10B10A2_SNORM);
1268     FMT_TO_STR(WINED3DFMT_R11G11B10_FLOAT);
1269     FMT_TO_STR(WINED3DFMT_R8G8B8A8_TYPELESS);
1270     FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM);
1271     FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM_SRGB);
1272     FMT_TO_STR(WINED3DFMT_R8G8B8A8_UINT);
1273     FMT_TO_STR(WINED3DFMT_R8G8B8A8_SNORM);
1274     FMT_TO_STR(WINED3DFMT_R8G8B8A8_SINT);
1275     FMT_TO_STR(WINED3DFMT_R16G16_TYPELESS);
1276     FMT_TO_STR(WINED3DFMT_R16G16_FLOAT);
1277     FMT_TO_STR(WINED3DFMT_R16G16_UNORM);
1278     FMT_TO_STR(WINED3DFMT_R16G16_UINT);
1279     FMT_TO_STR(WINED3DFMT_R16G16_SNORM);
1280     FMT_TO_STR(WINED3DFMT_R16G16_SINT);
1281     FMT_TO_STR(WINED3DFMT_R32_TYPELESS);
1282     FMT_TO_STR(WINED3DFMT_D32_FLOAT);
1283     FMT_TO_STR(WINED3DFMT_R32_FLOAT);
1284     FMT_TO_STR(WINED3DFMT_R32_UINT);
1285     FMT_TO_STR(WINED3DFMT_R32_SINT);
1286     FMT_TO_STR(WINED3DFMT_R24G8_TYPELESS);
1287     FMT_TO_STR(WINED3DFMT_D24_UNORM_S8_UINT);
1288     FMT_TO_STR(WINED3DFMT_R24_UNORM_X8_TYPELESS);
1289     FMT_TO_STR(WINED3DFMT_X24_TYPELESS_G8_UINT);
1290     FMT_TO_STR(WINED3DFMT_R8G8_TYPELESS);
1291     FMT_TO_STR(WINED3DFMT_R8G8_UNORM);
1292     FMT_TO_STR(WINED3DFMT_R8G8_UINT);
1293     FMT_TO_STR(WINED3DFMT_R8G8_SNORM);
1294     FMT_TO_STR(WINED3DFMT_R8G8_SINT);
1295     FMT_TO_STR(WINED3DFMT_R16_TYPELESS);
1296     FMT_TO_STR(WINED3DFMT_R16_FLOAT);
1297     FMT_TO_STR(WINED3DFMT_D16_UNORM);
1298     FMT_TO_STR(WINED3DFMT_R16_UNORM);
1299     FMT_TO_STR(WINED3DFMT_R16_UINT);
1300     FMT_TO_STR(WINED3DFMT_R16_SNORM);
1301     FMT_TO_STR(WINED3DFMT_R16_SINT);
1302     FMT_TO_STR(WINED3DFMT_R8_TYPELESS);
1303     FMT_TO_STR(WINED3DFMT_R8_UNORM);
1304     FMT_TO_STR(WINED3DFMT_R8_UINT);
1305     FMT_TO_STR(WINED3DFMT_R8_SNORM);
1306     FMT_TO_STR(WINED3DFMT_R8_SINT);
1307     FMT_TO_STR(WINED3DFMT_A8_UNORM);
1308     FMT_TO_STR(WINED3DFMT_R1_UNORM);
1309     FMT_TO_STR(WINED3DFMT_R9G9B9E5_SHAREDEXP);
1310     FMT_TO_STR(WINED3DFMT_R8G8_B8G8_UNORM);
1311     FMT_TO_STR(WINED3DFMT_G8R8_G8B8_UNORM);
1312     FMT_TO_STR(WINED3DFMT_BC1_TYPELESS);
1313     FMT_TO_STR(WINED3DFMT_BC1_UNORM);
1314     FMT_TO_STR(WINED3DFMT_BC1_UNORM_SRGB);
1315     FMT_TO_STR(WINED3DFMT_BC2_TYPELESS);
1316     FMT_TO_STR(WINED3DFMT_BC2_UNORM);
1317     FMT_TO_STR(WINED3DFMT_BC2_UNORM_SRGB);
1318     FMT_TO_STR(WINED3DFMT_BC3_TYPELESS);
1319     FMT_TO_STR(WINED3DFMT_BC3_UNORM);
1320     FMT_TO_STR(WINED3DFMT_BC3_UNORM_SRGB);
1321     FMT_TO_STR(WINED3DFMT_BC4_TYPELESS);
1322     FMT_TO_STR(WINED3DFMT_BC4_UNORM);
1323     FMT_TO_STR(WINED3DFMT_BC4_SNORM);
1324     FMT_TO_STR(WINED3DFMT_BC5_TYPELESS);
1325     FMT_TO_STR(WINED3DFMT_BC5_UNORM);
1326     FMT_TO_STR(WINED3DFMT_BC5_SNORM);
1327     FMT_TO_STR(WINED3DFMT_B5G6R5_UNORM);
1328     FMT_TO_STR(WINED3DFMT_B5G5R5A1_UNORM);
1329     FMT_TO_STR(WINED3DFMT_B8G8R8A8_UNORM);
1330     FMT_TO_STR(WINED3DFMT_B8G8R8X8_UNORM);
1331 #undef FMT_TO_STR
1332   default:
1333     {
1334       char fourcc[5];
1335       fourcc[0] = (char)(fmt);
1336       fourcc[1] = (char)(fmt >> 8);
1337       fourcc[2] = (char)(fmt >> 16);
1338       fourcc[3] = (char)(fmt >> 24);
1339       fourcc[4] = 0;
1340       if( isprint(fourcc[0]) && isprint(fourcc[1]) && isprint(fourcc[2]) && isprint(fourcc[3]) )
1341         FIXME("Unrecognized %u (as fourcc: %s) WINED3DFORMAT!\n", fmt, fourcc);
1342       else
1343         FIXME("Unrecognized %u WINED3DFORMAT!\n", fmt);
1344     }
1345     return "unrecognized";
1346   }
1347 }
1348
1349 const char* debug_d3ddevicetype(WINED3DDEVTYPE devtype) {
1350   switch (devtype) {
1351 #define DEVTYPE_TO_STR(dev) case dev: return #dev
1352     DEVTYPE_TO_STR(WINED3DDEVTYPE_HAL);
1353     DEVTYPE_TO_STR(WINED3DDEVTYPE_REF);
1354     DEVTYPE_TO_STR(WINED3DDEVTYPE_SW);
1355 #undef DEVTYPE_TO_STR
1356   default:
1357     FIXME("Unrecognized %u WINED3DDEVTYPE!\n", devtype);
1358     return "unrecognized";
1359   }
1360 }
1361
1362 const char *debug_d3dusage(DWORD usage)
1363 {
1364     char buf[284];
1365
1366     buf[0] = '\0';
1367 #define WINED3DUSAGE_TO_STR(u) if (usage & u) { strcat(buf, " | "#u); usage &= ~u; }
1368     WINED3DUSAGE_TO_STR(WINED3DUSAGE_RENDERTARGET);
1369     WINED3DUSAGE_TO_STR(WINED3DUSAGE_DEPTHSTENCIL);
1370     WINED3DUSAGE_TO_STR(WINED3DUSAGE_WRITEONLY);
1371     WINED3DUSAGE_TO_STR(WINED3DUSAGE_SOFTWAREPROCESSING);
1372     WINED3DUSAGE_TO_STR(WINED3DUSAGE_DONOTCLIP);
1373     WINED3DUSAGE_TO_STR(WINED3DUSAGE_POINTS);
1374     WINED3DUSAGE_TO_STR(WINED3DUSAGE_RTPATCHES);
1375     WINED3DUSAGE_TO_STR(WINED3DUSAGE_NPATCHES);
1376     WINED3DUSAGE_TO_STR(WINED3DUSAGE_DYNAMIC);
1377     WINED3DUSAGE_TO_STR(WINED3DUSAGE_AUTOGENMIPMAP);
1378     WINED3DUSAGE_TO_STR(WINED3DUSAGE_DMAP);
1379 #undef WINED3DUSAGE_TO_STR
1380     if (usage) FIXME("Unrecognized usage flag(s) %#x\n", usage);
1381
1382     return buf[0] ? wine_dbg_sprintf("%s", &buf[3]) : "0";
1383 }
1384
1385 const char *debug_d3dusagequery(DWORD usagequery)
1386 {
1387     char buf[238];
1388
1389     buf[0] = '\0';
1390 #define WINED3DUSAGEQUERY_TO_STR(u) if (usagequery & u) { strcat(buf, " | "#u); usagequery &= ~u; }
1391     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_FILTER);
1392     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_LEGACYBUMPMAP);
1393     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING);
1394     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_SRGBREAD);
1395     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_SRGBWRITE);
1396     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_VERTEXTEXTURE);
1397     WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_WRAPANDMIP);
1398 #undef WINED3DUSAGEQUERY_TO_STR
1399     if (usagequery) FIXME("Unrecognized usage query flag(s) %#x\n", usagequery);
1400
1401     return buf[0] ? wine_dbg_sprintf("%s", &buf[3]) : "0";
1402 }
1403
1404 const char* debug_d3ddeclmethod(WINED3DDECLMETHOD method) {
1405     switch (method) {
1406 #define WINED3DDECLMETHOD_TO_STR(u) case u: return #u
1407         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_DEFAULT);
1408         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_PARTIALU);
1409         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_PARTIALV);
1410         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_CROSSUV);
1411         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_UV);
1412         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_LOOKUP);
1413         WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_LOOKUPPRESAMPLED);
1414 #undef WINED3DDECLMETHOD_TO_STR
1415         default:
1416             FIXME("Unrecognized %u declaration method!\n", method);
1417             return "unrecognized";
1418     }
1419 }
1420
1421 const char* debug_d3ddeclusage(BYTE usage) {
1422     switch (usage) {
1423 #define WINED3DDECLUSAGE_TO_STR(u) case u: return #u
1424         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_POSITION);
1425         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_BLENDWEIGHT);
1426         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_BLENDINDICES);
1427         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_NORMAL);
1428         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_PSIZE);
1429         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_TEXCOORD);
1430         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_TANGENT);
1431         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_BINORMAL);
1432         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_TESSFACTOR);
1433         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_POSITIONT);
1434         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_COLOR);
1435         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_FOG);
1436         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_DEPTH);
1437         WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_SAMPLE);
1438 #undef WINED3DDECLUSAGE_TO_STR
1439         default:
1440             FIXME("Unrecognized %u declaration usage!\n", usage);
1441             return "unrecognized";
1442     }
1443 }
1444
1445 const char* debug_d3dresourcetype(WINED3DRESOURCETYPE res) {
1446   switch (res) {
1447 #define RES_TO_STR(res) case res: return #res
1448     RES_TO_STR(WINED3DRTYPE_SURFACE);
1449     RES_TO_STR(WINED3DRTYPE_VOLUME);
1450     RES_TO_STR(WINED3DRTYPE_TEXTURE);
1451     RES_TO_STR(WINED3DRTYPE_VOLUMETEXTURE);
1452     RES_TO_STR(WINED3DRTYPE_CUBETEXTURE);
1453     RES_TO_STR(WINED3DRTYPE_BUFFER);
1454 #undef  RES_TO_STR
1455   default:
1456     FIXME("Unrecognized %u WINED3DRESOURCETYPE!\n", res);
1457     return "unrecognized";
1458   }
1459 }
1460
1461 const char* debug_d3dprimitivetype(WINED3DPRIMITIVETYPE PrimitiveType) {
1462   switch (PrimitiveType) {
1463 #define PRIM_TO_STR(prim) case prim: return #prim
1464     PRIM_TO_STR(WINED3DPT_UNDEFINED);
1465     PRIM_TO_STR(WINED3DPT_POINTLIST);
1466     PRIM_TO_STR(WINED3DPT_LINELIST);
1467     PRIM_TO_STR(WINED3DPT_LINESTRIP);
1468     PRIM_TO_STR(WINED3DPT_TRIANGLELIST);
1469     PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP);
1470     PRIM_TO_STR(WINED3DPT_TRIANGLEFAN);
1471     PRIM_TO_STR(WINED3DPT_LINELIST_ADJ);
1472     PRIM_TO_STR(WINED3DPT_LINESTRIP_ADJ);
1473     PRIM_TO_STR(WINED3DPT_TRIANGLELIST_ADJ);
1474     PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP_ADJ);
1475 #undef  PRIM_TO_STR
1476   default:
1477     FIXME("Unrecognized %u WINED3DPRIMITIVETYPE!\n", PrimitiveType);
1478     return "unrecognized";
1479   }
1480 }
1481
1482 const char* debug_d3drenderstate(DWORD state) {
1483   switch (state) {
1484 #define D3DSTATE_TO_STR(u) case u: return #u
1485     D3DSTATE_TO_STR(WINED3DRS_TEXTUREHANDLE             );
1486     D3DSTATE_TO_STR(WINED3DRS_ANTIALIAS                 );
1487     D3DSTATE_TO_STR(WINED3DRS_TEXTUREADDRESS            );
1488     D3DSTATE_TO_STR(WINED3DRS_TEXTUREPERSPECTIVE        );
1489     D3DSTATE_TO_STR(WINED3DRS_WRAPU                     );
1490     D3DSTATE_TO_STR(WINED3DRS_WRAPV                     );
1491     D3DSTATE_TO_STR(WINED3DRS_ZENABLE                   );
1492     D3DSTATE_TO_STR(WINED3DRS_FILLMODE                  );
1493     D3DSTATE_TO_STR(WINED3DRS_SHADEMODE                 );
1494     D3DSTATE_TO_STR(WINED3DRS_LINEPATTERN               );
1495     D3DSTATE_TO_STR(WINED3DRS_MONOENABLE                );
1496     D3DSTATE_TO_STR(WINED3DRS_ROP2                      );
1497     D3DSTATE_TO_STR(WINED3DRS_PLANEMASK                 );
1498     D3DSTATE_TO_STR(WINED3DRS_ZWRITEENABLE              );
1499     D3DSTATE_TO_STR(WINED3DRS_ALPHATESTENABLE           );
1500     D3DSTATE_TO_STR(WINED3DRS_LASTPIXEL                 );
1501     D3DSTATE_TO_STR(WINED3DRS_TEXTUREMAG                );
1502     D3DSTATE_TO_STR(WINED3DRS_TEXTUREMIN                );
1503     D3DSTATE_TO_STR(WINED3DRS_SRCBLEND                  );
1504     D3DSTATE_TO_STR(WINED3DRS_DESTBLEND                 );
1505     D3DSTATE_TO_STR(WINED3DRS_TEXTUREMAPBLEND           );
1506     D3DSTATE_TO_STR(WINED3DRS_CULLMODE                  );
1507     D3DSTATE_TO_STR(WINED3DRS_ZFUNC                     );
1508     D3DSTATE_TO_STR(WINED3DRS_ALPHAREF                  );
1509     D3DSTATE_TO_STR(WINED3DRS_ALPHAFUNC                 );
1510     D3DSTATE_TO_STR(WINED3DRS_DITHERENABLE              );
1511     D3DSTATE_TO_STR(WINED3DRS_ALPHABLENDENABLE          );
1512     D3DSTATE_TO_STR(WINED3DRS_FOGENABLE                 );
1513     D3DSTATE_TO_STR(WINED3DRS_SPECULARENABLE            );
1514     D3DSTATE_TO_STR(WINED3DRS_ZVISIBLE                  );
1515     D3DSTATE_TO_STR(WINED3DRS_SUBPIXEL                  );
1516     D3DSTATE_TO_STR(WINED3DRS_SUBPIXELX                 );
1517     D3DSTATE_TO_STR(WINED3DRS_STIPPLEDALPHA             );
1518     D3DSTATE_TO_STR(WINED3DRS_FOGCOLOR                  );
1519     D3DSTATE_TO_STR(WINED3DRS_FOGTABLEMODE              );
1520     D3DSTATE_TO_STR(WINED3DRS_FOGSTART                  );
1521     D3DSTATE_TO_STR(WINED3DRS_FOGEND                    );
1522     D3DSTATE_TO_STR(WINED3DRS_FOGDENSITY                );
1523     D3DSTATE_TO_STR(WINED3DRS_STIPPLEENABLE             );
1524     D3DSTATE_TO_STR(WINED3DRS_EDGEANTIALIAS             );
1525     D3DSTATE_TO_STR(WINED3DRS_COLORKEYENABLE            );
1526     D3DSTATE_TO_STR(WINED3DRS_BORDERCOLOR               );
1527     D3DSTATE_TO_STR(WINED3DRS_TEXTUREADDRESSU           );
1528     D3DSTATE_TO_STR(WINED3DRS_TEXTUREADDRESSV           );
1529     D3DSTATE_TO_STR(WINED3DRS_MIPMAPLODBIAS             );
1530     D3DSTATE_TO_STR(WINED3DRS_ZBIAS                     );
1531     D3DSTATE_TO_STR(WINED3DRS_RANGEFOGENABLE            );
1532     D3DSTATE_TO_STR(WINED3DRS_ANISOTROPY                );
1533     D3DSTATE_TO_STR(WINED3DRS_FLUSHBATCH                );
1534     D3DSTATE_TO_STR(WINED3DRS_TRANSLUCENTSORTINDEPENDENT);
1535     D3DSTATE_TO_STR(WINED3DRS_STENCILENABLE             );
1536     D3DSTATE_TO_STR(WINED3DRS_STENCILFAIL               );
1537     D3DSTATE_TO_STR(WINED3DRS_STENCILZFAIL              );
1538     D3DSTATE_TO_STR(WINED3DRS_STENCILPASS               );
1539     D3DSTATE_TO_STR(WINED3DRS_STENCILFUNC               );
1540     D3DSTATE_TO_STR(WINED3DRS_STENCILREF                );
1541     D3DSTATE_TO_STR(WINED3DRS_STENCILMASK               );
1542     D3DSTATE_TO_STR(WINED3DRS_STENCILWRITEMASK          );
1543     D3DSTATE_TO_STR(WINED3DRS_TEXTUREFACTOR             );
1544     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN00          );
1545     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN01          );
1546     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN02          );
1547     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN03          );
1548     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN04          );
1549     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN05          );
1550     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN06          );
1551     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN07          );
1552     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN08          );
1553     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN09          );
1554     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN10          );
1555     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN11          );
1556     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN12          );
1557     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN13          );
1558     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN14          );
1559     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN15          );
1560     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN16          );
1561     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN17          );
1562     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN18          );
1563     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN19          );
1564     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN20          );
1565     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN21          );
1566     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN22          );
1567     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN23          );
1568     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN24          );
1569     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN25          );
1570     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN26          );
1571     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN27          );
1572     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN28          );
1573     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN29          );
1574     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN30          );
1575     D3DSTATE_TO_STR(WINED3DRS_STIPPLEPATTERN31          );
1576     D3DSTATE_TO_STR(WINED3DRS_WRAP0                     );
1577     D3DSTATE_TO_STR(WINED3DRS_WRAP1                     );
1578     D3DSTATE_TO_STR(WINED3DRS_WRAP2                     );
1579     D3DSTATE_TO_STR(WINED3DRS_WRAP3                     );
1580     D3DSTATE_TO_STR(WINED3DRS_WRAP4                     );
1581     D3DSTATE_TO_STR(WINED3DRS_WRAP5                     );
1582     D3DSTATE_TO_STR(WINED3DRS_WRAP6                     );
1583     D3DSTATE_TO_STR(WINED3DRS_WRAP7                     );
1584     D3DSTATE_TO_STR(WINED3DRS_CLIPPING                  );
1585     D3DSTATE_TO_STR(WINED3DRS_LIGHTING                  );
1586     D3DSTATE_TO_STR(WINED3DRS_EXTENTS                   );
1587     D3DSTATE_TO_STR(WINED3DRS_AMBIENT                   );
1588     D3DSTATE_TO_STR(WINED3DRS_FOGVERTEXMODE             );
1589     D3DSTATE_TO_STR(WINED3DRS_COLORVERTEX               );
1590     D3DSTATE_TO_STR(WINED3DRS_LOCALVIEWER               );
1591     D3DSTATE_TO_STR(WINED3DRS_NORMALIZENORMALS          );
1592     D3DSTATE_TO_STR(WINED3DRS_COLORKEYBLENDENABLE       );
1593     D3DSTATE_TO_STR(WINED3DRS_DIFFUSEMATERIALSOURCE     );
1594     D3DSTATE_TO_STR(WINED3DRS_SPECULARMATERIALSOURCE    );
1595     D3DSTATE_TO_STR(WINED3DRS_AMBIENTMATERIALSOURCE     );
1596     D3DSTATE_TO_STR(WINED3DRS_EMISSIVEMATERIALSOURCE    );
1597     D3DSTATE_TO_STR(WINED3DRS_VERTEXBLEND               );
1598     D3DSTATE_TO_STR(WINED3DRS_CLIPPLANEENABLE           );
1599     D3DSTATE_TO_STR(WINED3DRS_SOFTWAREVERTEXPROCESSING  );
1600     D3DSTATE_TO_STR(WINED3DRS_POINTSIZE                 );
1601     D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MIN             );
1602     D3DSTATE_TO_STR(WINED3DRS_POINTSPRITEENABLE         );
1603     D3DSTATE_TO_STR(WINED3DRS_POINTSCALEENABLE          );
1604     D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_A              );
1605     D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_B              );
1606     D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_C              );
1607     D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEANTIALIAS      );
1608     D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEMASK           );
1609     D3DSTATE_TO_STR(WINED3DRS_PATCHEDGESTYLE            );
1610     D3DSTATE_TO_STR(WINED3DRS_PATCHSEGMENTS             );
1611     D3DSTATE_TO_STR(WINED3DRS_DEBUGMONITORTOKEN         );
1612     D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MAX             );
1613     D3DSTATE_TO_STR(WINED3DRS_INDEXEDVERTEXBLENDENABLE  );
1614     D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE          );
1615     D3DSTATE_TO_STR(WINED3DRS_TWEENFACTOR               );
1616     D3DSTATE_TO_STR(WINED3DRS_BLENDOP                   );
1617     D3DSTATE_TO_STR(WINED3DRS_POSITIONDEGREE            );
1618     D3DSTATE_TO_STR(WINED3DRS_NORMALDEGREE              );
1619     D3DSTATE_TO_STR(WINED3DRS_SCISSORTESTENABLE         );
1620     D3DSTATE_TO_STR(WINED3DRS_SLOPESCALEDEPTHBIAS       );
1621     D3DSTATE_TO_STR(WINED3DRS_ANTIALIASEDLINEENABLE     );
1622     D3DSTATE_TO_STR(WINED3DRS_MINTESSELLATIONLEVEL      );
1623     D3DSTATE_TO_STR(WINED3DRS_MAXTESSELLATIONLEVEL      );
1624     D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_X            );
1625     D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Y            );
1626     D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Z            );
1627     D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_W            );
1628     D3DSTATE_TO_STR(WINED3DRS_ENABLEADAPTIVETESSELLATION);
1629     D3DSTATE_TO_STR(WINED3DRS_TWOSIDEDSTENCILMODE       );
1630     D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFAIL           );
1631     D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILZFAIL          );
1632     D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILPASS           );
1633     D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFUNC           );
1634     D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE1         );
1635     D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE2         );
1636     D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE3         );
1637     D3DSTATE_TO_STR(WINED3DRS_BLENDFACTOR               );
1638     D3DSTATE_TO_STR(WINED3DRS_SRGBWRITEENABLE           );
1639     D3DSTATE_TO_STR(WINED3DRS_DEPTHBIAS                 );
1640     D3DSTATE_TO_STR(WINED3DRS_WRAP8                     );
1641     D3DSTATE_TO_STR(WINED3DRS_WRAP9                     );
1642     D3DSTATE_TO_STR(WINED3DRS_WRAP10                    );
1643     D3DSTATE_TO_STR(WINED3DRS_WRAP11                    );
1644     D3DSTATE_TO_STR(WINED3DRS_WRAP12                    );
1645     D3DSTATE_TO_STR(WINED3DRS_WRAP13                    );
1646     D3DSTATE_TO_STR(WINED3DRS_WRAP14                    );
1647     D3DSTATE_TO_STR(WINED3DRS_WRAP15                    );
1648     D3DSTATE_TO_STR(WINED3DRS_SEPARATEALPHABLENDENABLE  );
1649     D3DSTATE_TO_STR(WINED3DRS_SRCBLENDALPHA             );
1650     D3DSTATE_TO_STR(WINED3DRS_DESTBLENDALPHA            );
1651     D3DSTATE_TO_STR(WINED3DRS_BLENDOPALPHA              );
1652 #undef D3DSTATE_TO_STR
1653   default:
1654     FIXME("Unrecognized %u render state!\n", state);
1655     return "unrecognized";
1656   }
1657 }
1658
1659 const char* debug_d3dsamplerstate(DWORD state) {
1660   switch (state) {
1661 #define D3DSTATE_TO_STR(u) case u: return #u
1662     D3DSTATE_TO_STR(WINED3DSAMP_BORDERCOLOR  );
1663     D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSU     );
1664     D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSV     );
1665     D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSW     );
1666     D3DSTATE_TO_STR(WINED3DSAMP_MAGFILTER    );
1667     D3DSTATE_TO_STR(WINED3DSAMP_MINFILTER    );
1668     D3DSTATE_TO_STR(WINED3DSAMP_MIPFILTER    );
1669     D3DSTATE_TO_STR(WINED3DSAMP_MIPMAPLODBIAS);
1670     D3DSTATE_TO_STR(WINED3DSAMP_MAXMIPLEVEL  );
1671     D3DSTATE_TO_STR(WINED3DSAMP_MAXANISOTROPY);
1672     D3DSTATE_TO_STR(WINED3DSAMP_SRGBTEXTURE  );
1673     D3DSTATE_TO_STR(WINED3DSAMP_ELEMENTINDEX );
1674     D3DSTATE_TO_STR(WINED3DSAMP_DMAPOFFSET   );
1675 #undef D3DSTATE_TO_STR
1676   default:
1677     FIXME("Unrecognized %u sampler state!\n", state);
1678     return "unrecognized";
1679   }
1680 }
1681
1682 const char *debug_d3dtexturefiltertype(WINED3DTEXTUREFILTERTYPE filter_type) {
1683     switch (filter_type) {
1684 #define D3DTEXTUREFILTERTYPE_TO_STR(u) case u: return #u
1685         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_NONE);
1686         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_POINT);
1687         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_LINEAR);
1688         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_ANISOTROPIC);
1689         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_FLATCUBIC);
1690         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_GAUSSIANCUBIC);
1691         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_PYRAMIDALQUAD);
1692         D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_GAUSSIANQUAD);
1693 #undef D3DTEXTUREFILTERTYPE_TO_STR
1694         default:
1695             FIXME("Unrecognied texture filter type 0x%08x\n", filter_type);
1696             return "unrecognized";
1697     }
1698 }
1699
1700 const char* debug_d3dtexturestate(DWORD state) {
1701   switch (state) {
1702 #define D3DSTATE_TO_STR(u) case u: return #u
1703     D3DSTATE_TO_STR(WINED3DTSS_COLOROP               );
1704     D3DSTATE_TO_STR(WINED3DTSS_COLORARG1             );
1705     D3DSTATE_TO_STR(WINED3DTSS_COLORARG2             );
1706     D3DSTATE_TO_STR(WINED3DTSS_ALPHAOP               );
1707     D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG1             );
1708     D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG2             );
1709     D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT00          );
1710     D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT01          );
1711     D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT10          );
1712     D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT11          );
1713     D3DSTATE_TO_STR(WINED3DTSS_TEXCOORDINDEX         );
1714     D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLSCALE         );
1715     D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLOFFSET        );
1716     D3DSTATE_TO_STR(WINED3DTSS_TEXTURETRANSFORMFLAGS );
1717     D3DSTATE_TO_STR(WINED3DTSS_COLORARG0             );
1718     D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG0             );
1719     D3DSTATE_TO_STR(WINED3DTSS_RESULTARG             );
1720     D3DSTATE_TO_STR(WINED3DTSS_CONSTANT              );
1721 #undef D3DSTATE_TO_STR
1722   default:
1723     FIXME("Unrecognized %u texture state!\n", state);
1724     return "unrecognized";
1725   }
1726 }
1727
1728 const char* debug_d3dtop(WINED3DTEXTUREOP d3dtop) {
1729     switch (d3dtop) {
1730 #define D3DTOP_TO_STR(u) case u: return #u
1731         D3DTOP_TO_STR(WINED3DTOP_DISABLE);
1732         D3DTOP_TO_STR(WINED3DTOP_SELECTARG1);
1733         D3DTOP_TO_STR(WINED3DTOP_SELECTARG2);
1734         D3DTOP_TO_STR(WINED3DTOP_MODULATE);
1735         D3DTOP_TO_STR(WINED3DTOP_MODULATE2X);
1736         D3DTOP_TO_STR(WINED3DTOP_MODULATE4X);
1737         D3DTOP_TO_STR(WINED3DTOP_ADD);
1738         D3DTOP_TO_STR(WINED3DTOP_ADDSIGNED);
1739         D3DTOP_TO_STR(WINED3DTOP_ADDSIGNED2X);
1740         D3DTOP_TO_STR(WINED3DTOP_SUBTRACT);
1741         D3DTOP_TO_STR(WINED3DTOP_ADDSMOOTH);
1742         D3DTOP_TO_STR(WINED3DTOP_BLENDDIFFUSEALPHA);
1743         D3DTOP_TO_STR(WINED3DTOP_BLENDTEXTUREALPHA);
1744         D3DTOP_TO_STR(WINED3DTOP_BLENDFACTORALPHA);
1745         D3DTOP_TO_STR(WINED3DTOP_BLENDTEXTUREALPHAPM);
1746         D3DTOP_TO_STR(WINED3DTOP_BLENDCURRENTALPHA);
1747         D3DTOP_TO_STR(WINED3DTOP_PREMODULATE);
1748         D3DTOP_TO_STR(WINED3DTOP_MODULATEALPHA_ADDCOLOR);
1749         D3DTOP_TO_STR(WINED3DTOP_MODULATECOLOR_ADDALPHA);
1750         D3DTOP_TO_STR(WINED3DTOP_MODULATEINVALPHA_ADDCOLOR);
1751         D3DTOP_TO_STR(WINED3DTOP_MODULATEINVCOLOR_ADDALPHA);
1752         D3DTOP_TO_STR(WINED3DTOP_BUMPENVMAP);
1753         D3DTOP_TO_STR(WINED3DTOP_BUMPENVMAPLUMINANCE);
1754         D3DTOP_TO_STR(WINED3DTOP_DOTPRODUCT3);
1755         D3DTOP_TO_STR(WINED3DTOP_MULTIPLYADD);
1756         D3DTOP_TO_STR(WINED3DTOP_LERP);
1757 #undef D3DTOP_TO_STR
1758         default:
1759             FIXME("Unrecognized %u WINED3DTOP\n", d3dtop);
1760             return "unrecognized";
1761     }
1762 }
1763
1764 const char* debug_d3dtstype(WINED3DTRANSFORMSTATETYPE tstype) {
1765     switch (tstype) {
1766 #define TSTYPE_TO_STR(tstype) case tstype: return #tstype
1767     TSTYPE_TO_STR(WINED3DTS_VIEW);
1768     TSTYPE_TO_STR(WINED3DTS_PROJECTION);
1769     TSTYPE_TO_STR(WINED3DTS_TEXTURE0);
1770     TSTYPE_TO_STR(WINED3DTS_TEXTURE1);
1771     TSTYPE_TO_STR(WINED3DTS_TEXTURE2);
1772     TSTYPE_TO_STR(WINED3DTS_TEXTURE3);
1773     TSTYPE_TO_STR(WINED3DTS_TEXTURE4);
1774     TSTYPE_TO_STR(WINED3DTS_TEXTURE5);
1775     TSTYPE_TO_STR(WINED3DTS_TEXTURE6);
1776     TSTYPE_TO_STR(WINED3DTS_TEXTURE7);
1777     TSTYPE_TO_STR(WINED3DTS_WORLDMATRIX(0));
1778 #undef TSTYPE_TO_STR
1779     default:
1780         if (tstype > 256 && tstype < 512) {
1781             FIXME("WINED3DTS_WORLDMATRIX(%u). 1..255 not currently supported\n", tstype);
1782             return ("WINED3DTS_WORLDMATRIX > 0");
1783         }
1784         FIXME("Unrecognized %u WINED3DTS\n", tstype);
1785         return "unrecognized";
1786     }
1787 }
1788
1789 const char *debug_d3dstate(DWORD state)
1790 {
1791     if (STATE_IS_RENDER(state))
1792         return wine_dbg_sprintf("STATE_RENDER(%s)", debug_d3drenderstate(state - STATE_RENDER(0)));
1793     if (STATE_IS_TEXTURESTAGE(state))
1794     {
1795         DWORD texture_stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
1796         DWORD texture_state = state - STATE_TEXTURESTAGE(texture_stage, 0);
1797         return wine_dbg_sprintf("STATE_TEXTURESTAGE(%#x, %s)",
1798                 texture_stage, debug_d3dtexturestate(texture_state));
1799     }
1800     if (STATE_IS_SAMPLER(state))
1801         return wine_dbg_sprintf("STATE_SAMPLER(%#x)", state - STATE_SAMPLER(0));
1802     if (STATE_IS_PIXELSHADER(state))
1803         return "STATE_PIXELSHADER";
1804     if (STATE_IS_TRANSFORM(state))
1805         return wine_dbg_sprintf("STATE_TRANSFORM(%s)", debug_d3dtstype(state - STATE_TRANSFORM(0)));
1806     if (STATE_IS_STREAMSRC(state))
1807         return "STATE_STREAMSRC";
1808     if (STATE_IS_INDEXBUFFER(state))
1809         return "STATE_INDEXBUFFER";
1810     if (STATE_IS_VDECL(state))
1811         return "STATE_VDECL";
1812     if (STATE_IS_VSHADER(state))
1813         return "STATE_VSHADER";
1814     if (STATE_IS_VIEWPORT(state))
1815         return "STATE_VIEWPORT";
1816     if (STATE_IS_VERTEXSHADERCONSTANT(state))
1817         return "STATE_VERTEXSHADERCONSTANT";
1818     if (STATE_IS_PIXELSHADERCONSTANT(state))
1819         return "STATE_PIXELSHADERCONSTANT";
1820     if (STATE_IS_ACTIVELIGHT(state))
1821         return wine_dbg_sprintf("STATE_ACTIVELIGHT(%#x)", state - STATE_ACTIVELIGHT(0));
1822     if (STATE_IS_SCISSORRECT(state))
1823         return "STATE_SCISSORRECT";
1824     if (STATE_IS_CLIPPLANE(state))
1825         return wine_dbg_sprintf("STATE_CLIPPLANE(%#x)", state - STATE_CLIPPLANE(0));
1826     if (STATE_IS_MATERIAL(state))
1827         return "STATE_MATERIAL";
1828     if (STATE_IS_FRONTFACE(state))
1829         return "STATE_FRONTFACE";
1830
1831     return wine_dbg_sprintf("UNKNOWN_STATE(%#x)", state);
1832 }
1833
1834 const char* debug_d3dpool(WINED3DPOOL Pool) {
1835   switch (Pool) {
1836 #define POOL_TO_STR(p) case p: return #p
1837     POOL_TO_STR(WINED3DPOOL_DEFAULT);
1838     POOL_TO_STR(WINED3DPOOL_MANAGED);
1839     POOL_TO_STR(WINED3DPOOL_SYSTEMMEM);
1840     POOL_TO_STR(WINED3DPOOL_SCRATCH);
1841 #undef  POOL_TO_STR
1842   default:
1843     FIXME("Unrecognized %u WINED3DPOOL!\n", Pool);
1844     return "unrecognized";
1845   }
1846 }
1847
1848 const char *debug_fbostatus(GLenum status) {
1849     switch(status) {
1850 #define FBOSTATUS_TO_STR(u) case u: return #u
1851         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_COMPLETE);
1852         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT);
1853         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT);
1854         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT);
1855         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_FORMATS_EXT);
1856         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER);
1857         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER);
1858         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE);
1859         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_UNSUPPORTED);
1860         FBOSTATUS_TO_STR(GL_FRAMEBUFFER_UNDEFINED);
1861 #undef FBOSTATUS_TO_STR
1862         default:
1863             FIXME("Unrecognied FBO status 0x%08x\n", status);
1864             return "unrecognized";
1865     }
1866 }
1867
1868 const char *debug_glerror(GLenum error) {
1869     switch(error) {
1870 #define GLERROR_TO_STR(u) case u: return #u
1871         GLERROR_TO_STR(GL_NO_ERROR);
1872         GLERROR_TO_STR(GL_INVALID_ENUM);
1873         GLERROR_TO_STR(GL_INVALID_VALUE);
1874         GLERROR_TO_STR(GL_INVALID_OPERATION);
1875         GLERROR_TO_STR(GL_STACK_OVERFLOW);
1876         GLERROR_TO_STR(GL_STACK_UNDERFLOW);
1877         GLERROR_TO_STR(GL_OUT_OF_MEMORY);
1878         GLERROR_TO_STR(GL_INVALID_FRAMEBUFFER_OPERATION);
1879 #undef GLERROR_TO_STR
1880         default:
1881             FIXME("Unrecognied GL error 0x%08x\n", error);
1882             return "unrecognized";
1883     }
1884 }
1885
1886 const char *debug_d3dbasis(WINED3DBASISTYPE basis) {
1887     switch(basis) {
1888         case WINED3DBASIS_BEZIER:       return "WINED3DBASIS_BEZIER";
1889         case WINED3DBASIS_BSPLINE:      return "WINED3DBASIS_BSPLINE";
1890         case WINED3DBASIS_INTERPOLATE:  return "WINED3DBASIS_INTERPOLATE";
1891         default:                        return "unrecognized";
1892     }
1893 }
1894
1895 const char *debug_d3ddegree(WINED3DDEGREETYPE degree) {
1896     switch(degree) {
1897         case WINED3DDEGREE_LINEAR:      return "WINED3DDEGREE_LINEAR";
1898         case WINED3DDEGREE_QUADRATIC:   return "WINED3DDEGREE_QUADRATIC";
1899         case WINED3DDEGREE_CUBIC:       return "WINED3DDEGREE_CUBIC";
1900         case WINED3DDEGREE_QUINTIC:     return "WINED3DDEGREE_QUINTIC";
1901         default:                        return "unrecognized";
1902     }
1903 }
1904
1905 static const char *debug_fixup_channel_source(enum fixup_channel_source source)
1906 {
1907     switch(source)
1908     {
1909 #define WINED3D_TO_STR(x) case x: return #x
1910         WINED3D_TO_STR(CHANNEL_SOURCE_ZERO);
1911         WINED3D_TO_STR(CHANNEL_SOURCE_ONE);
1912         WINED3D_TO_STR(CHANNEL_SOURCE_X);
1913         WINED3D_TO_STR(CHANNEL_SOURCE_Y);
1914         WINED3D_TO_STR(CHANNEL_SOURCE_Z);
1915         WINED3D_TO_STR(CHANNEL_SOURCE_W);
1916         WINED3D_TO_STR(CHANNEL_SOURCE_YUV0);
1917         WINED3D_TO_STR(CHANNEL_SOURCE_YUV1);
1918 #undef WINED3D_TO_STR
1919         default:
1920             FIXME("Unrecognized fixup_channel_source %#x\n", source);
1921             return "unrecognized";
1922     }
1923 }
1924
1925 static const char *debug_yuv_fixup(enum yuv_fixup yuv_fixup)
1926 {
1927     switch(yuv_fixup)
1928     {
1929 #define WINED3D_TO_STR(x) case x: return #x
1930         WINED3D_TO_STR(YUV_FIXUP_YUY2);
1931         WINED3D_TO_STR(YUV_FIXUP_UYVY);
1932         WINED3D_TO_STR(YUV_FIXUP_YV12);
1933 #undef WINED3D_TO_STR
1934         default:
1935             FIXME("Unrecognized YUV fixup %#x\n", yuv_fixup);
1936             return "unrecognized";
1937     }
1938 }
1939
1940 void dump_color_fixup_desc(struct color_fixup_desc fixup)
1941 {
1942     if (is_yuv_fixup(fixup))
1943     {
1944         TRACE("\tYUV: %s\n", debug_yuv_fixup(get_yuv_fixup(fixup)));
1945         return;
1946     }
1947
1948     TRACE("\tX: %s%s\n", debug_fixup_channel_source(fixup.x_source), fixup.x_sign_fixup ? ", SIGN_FIXUP" : "");
1949     TRACE("\tY: %s%s\n", debug_fixup_channel_source(fixup.y_source), fixup.y_sign_fixup ? ", SIGN_FIXUP" : "");
1950     TRACE("\tZ: %s%s\n", debug_fixup_channel_source(fixup.z_source), fixup.z_sign_fixup ? ", SIGN_FIXUP" : "");
1951     TRACE("\tW: %s%s\n", debug_fixup_channel_source(fixup.w_source), fixup.w_sign_fixup ? ", SIGN_FIXUP" : "");
1952 }
1953
1954 const char *debug_surflocation(DWORD flag) {
1955     char buf[128];
1956
1957     buf[0] = 0;
1958     if(flag & SFLAG_INSYSMEM) strcat(buf, " | SFLAG_INSYSMEM");
1959     if(flag & SFLAG_INDRAWABLE) strcat(buf, " | SFLAG_INDRAWABLE");
1960     if(flag & SFLAG_INTEXTURE) strcat(buf, " | SFLAG_INTEXTURE");
1961     if(flag & SFLAG_INSRGBTEX) strcat(buf, " | SFLAG_INSRGBTEX");
1962     return wine_dbg_sprintf("%s", buf[0] ? buf + 3 : "0");
1963 }
1964
1965 /*****************************************************************************
1966  * Useful functions mapping GL <-> D3D values
1967  */
1968 GLenum StencilOp(DWORD op) {
1969     switch(op) {
1970     case WINED3DSTENCILOP_KEEP    : return GL_KEEP;
1971     case WINED3DSTENCILOP_ZERO    : return GL_ZERO;
1972     case WINED3DSTENCILOP_REPLACE : return GL_REPLACE;
1973     case WINED3DSTENCILOP_INCRSAT : return GL_INCR;
1974     case WINED3DSTENCILOP_DECRSAT : return GL_DECR;
1975     case WINED3DSTENCILOP_INVERT  : return GL_INVERT;
1976     case WINED3DSTENCILOP_INCR    : return GL_INCR_WRAP_EXT;
1977     case WINED3DSTENCILOP_DECR    : return GL_DECR_WRAP_EXT;
1978     default:
1979         FIXME("Unrecognized stencil op %d\n", op);
1980         return GL_KEEP;
1981     }
1982 }
1983
1984 GLenum CompareFunc(DWORD func) {
1985     switch ((WINED3DCMPFUNC)func) {
1986     case WINED3DCMP_NEVER        : return GL_NEVER;
1987     case WINED3DCMP_LESS         : return GL_LESS;
1988     case WINED3DCMP_EQUAL        : return GL_EQUAL;
1989     case WINED3DCMP_LESSEQUAL    : return GL_LEQUAL;
1990     case WINED3DCMP_GREATER      : return GL_GREATER;
1991     case WINED3DCMP_NOTEQUAL     : return GL_NOTEQUAL;
1992     case WINED3DCMP_GREATEREQUAL : return GL_GEQUAL;
1993     case WINED3DCMP_ALWAYS       : return GL_ALWAYS;
1994     default:
1995         FIXME("Unrecognized WINED3DCMPFUNC value %d\n", func);
1996         return 0;
1997     }
1998 }
1999
2000 BOOL is_invalid_op(IWineD3DDeviceImpl *This, int stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3) {
2001     if (op == WINED3DTOP_DISABLE) return FALSE;
2002     if (This->stateBlock->textures[stage]) return FALSE;
2003
2004     if ((arg1 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
2005             && op != WINED3DTOP_SELECTARG2) return TRUE;
2006     if ((arg2 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
2007             && op != WINED3DTOP_SELECTARG1) return TRUE;
2008     if ((arg3 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
2009             && (op == WINED3DTOP_MULTIPLYADD || op == WINED3DTOP_LERP)) return TRUE;
2010
2011     return FALSE;
2012 }
2013
2014 /* Setup this textures matrix according to the texture flags*/
2015 /* GL locking is done by the caller (state handler) */
2016 void set_texture_matrix(const float *smat, DWORD flags, BOOL calculatedCoords, BOOL transformed,
2017         WINED3DFORMAT vtx_fmt, BOOL ffp_proj_control)
2018 {
2019     float mat[16];
2020
2021     glMatrixMode(GL_TEXTURE);
2022     checkGLcall("glMatrixMode(GL_TEXTURE)");
2023
2024     if (flags == WINED3DTTFF_DISABLE || flags == WINED3DTTFF_COUNT1 || transformed) {
2025         glLoadIdentity();
2026         checkGLcall("glLoadIdentity()");
2027         return;
2028     }
2029
2030     if (flags == (WINED3DTTFF_COUNT1|WINED3DTTFF_PROJECTED)) {
2031         ERR("Invalid texture transform flags: WINED3DTTFF_COUNT1|WINED3DTTFF_PROJECTED\n");
2032         return;
2033     }
2034
2035     memcpy(mat, smat, 16 * sizeof(float));
2036
2037     if (flags & WINED3DTTFF_PROJECTED) {
2038         if(!ffp_proj_control) {
2039             switch (flags & ~WINED3DTTFF_PROJECTED) {
2040             case WINED3DTTFF_COUNT2:
2041                 mat[3] = mat[1], mat[7] = mat[5], mat[11] = mat[9], mat[15] = mat[13];
2042                 mat[1] = mat[5] = mat[9] = mat[13] = 0;
2043                 break;
2044             case WINED3DTTFF_COUNT3:
2045                 mat[3] = mat[2], mat[7] = mat[6], mat[11] = mat[10], mat[15] = mat[14];
2046                 mat[2] = mat[6] = mat[10] = mat[14] = 0;
2047                 break;
2048             }
2049         }
2050     } else { /* under directx the R/Z coord can be used for translation, under opengl we use the Q coord instead */
2051         if(!calculatedCoords) {
2052             switch(vtx_fmt)
2053             {
2054                 case WINED3DFMT_R32_FLOAT:
2055                     /* Direct3D passes the default 1.0 in the 2nd coord, while gl passes it in the 4th.
2056                      * swap 2nd and 4th coord. No need to store the value of mat[12] in mat[4] because
2057                      * the input value to the transformation will be 0, so the matrix value is irrelevant
2058                      */
2059                     mat[12] = mat[4];
2060                     mat[13] = mat[5];
2061                     mat[14] = mat[6];
2062                     mat[15] = mat[7];
2063                     break;
2064                 case WINED3DFMT_R32G32_FLOAT:
2065                     /* See above, just 3rd and 4th coord
2066                     */
2067                     mat[12] = mat[8];
2068                     mat[13] = mat[9];
2069                     mat[14] = mat[10];
2070                     mat[15] = mat[11];
2071                     break;
2072                 case WINED3DFMT_R32G32B32_FLOAT: /* Opengl defaults match dx defaults */
2073                 case WINED3DFMT_R32G32B32A32_FLOAT: /* No defaults apply, all app defined */
2074
2075                 /* This is to prevent swapping the matrix lines and put the default 4th coord = 1.0
2076                  * into a bad place. The division elimination below will apply to make sure the
2077                  * 1.0 doesn't do anything bad. The caller will set this value if the stride is 0
2078                  */
2079                 case WINED3DFMT_UNKNOWN: /* No texture coords, 0/0/0/1 defaults are passed */
2080                     break;
2081                 default:
2082                     FIXME("Unexpected fixed function texture coord input\n");
2083             }
2084         }
2085         if(!ffp_proj_control) {
2086             switch (flags & ~WINED3DTTFF_PROJECTED) {
2087                 /* case WINED3DTTFF_COUNT1: Won't ever get here */
2088                 case WINED3DTTFF_COUNT2: mat[2] = mat[6] = mat[10] = mat[14] = 0;
2089                 /* OpenGL divides the first 3 vertex coord by the 4th by default,
2090                 * which is essentially the same as D3DTTFF_PROJECTED. Make sure that
2091                 * the 4th coord evaluates to 1.0 to eliminate that.
2092                 *
2093                 * If the fixed function pipeline is used, the 4th value remains unused,
2094                 * so there is no danger in doing this. With vertex shaders we have a
2095                 * problem. Should an app hit that problem, the code here would have to
2096                 * check for pixel shaders, and the shader has to undo the default gl divide.
2097                 *
2098                 * A more serious problem occurs if the app passes 4 coordinates in, and the
2099                 * 4th is != 1.0(opengl default). This would have to be fixed in drawStridedSlow
2100                 * or a replacement shader
2101                 */
2102                 default: mat[3] = mat[7] = mat[11] = 0; mat[15] = 1;
2103             }
2104         }
2105     }
2106
2107     glLoadMatrixf(mat);
2108     checkGLcall("glLoadMatrixf(mat)");
2109 }
2110
2111 /* This small helper function is used to convert a bitmask into the number of masked bits */
2112 unsigned int count_bits(unsigned int mask)
2113 {
2114     unsigned int count;
2115     for (count = 0; mask; ++count)
2116     {
2117         mask &= mask - 1;
2118     }
2119     return count;
2120 }
2121
2122 /* Helper function for retrieving color info for ChoosePixelFormat and wglChoosePixelFormatARB.
2123  * The later function requires individual color components. */
2124 BOOL getColorBits(const struct GlPixelFormatDesc *format_desc,
2125         short *redSize, short *greenSize, short *blueSize, short *alphaSize, short *totalSize)
2126 {
2127     TRACE("fmt: %s\n", debug_d3dformat(format_desc->format));
2128     switch(format_desc->format)
2129     {
2130         case WINED3DFMT_B8G8R8X8_UNORM:
2131         case WINED3DFMT_B8G8R8_UNORM:
2132         case WINED3DFMT_B8G8R8A8_UNORM:
2133         case WINED3DFMT_R8G8B8A8_UNORM:
2134         case WINED3DFMT_B10G10R10A2_UNORM:
2135         case WINED3DFMT_B5G5R5X1_UNORM:
2136         case WINED3DFMT_B5G5R5A1_UNORM:
2137         case WINED3DFMT_B5G6R5_UNORM:
2138         case WINED3DFMT_B4G4R4X4_UNORM:
2139         case WINED3DFMT_B4G4R4A4_UNORM:
2140         case WINED3DFMT_B2G3R3_UNORM:
2141         case WINED3DFMT_P8_UINT_A8_UNORM:
2142         case WINED3DFMT_P8_UINT:
2143             break;
2144         default:
2145             ERR("Unsupported format: %s\n", debug_d3dformat(format_desc->format));
2146             return FALSE;
2147     }
2148
2149     *redSize = count_bits(format_desc->red_mask);
2150     *greenSize = count_bits(format_desc->green_mask);
2151     *blueSize = count_bits(format_desc->blue_mask);
2152     *alphaSize = count_bits(format_desc->alpha_mask);
2153     *totalSize = *redSize + *greenSize + *blueSize + *alphaSize;
2154
2155     TRACE("Returning red:  %d, green: %d, blue: %d, alpha: %d, total: %d for fmt=%s\n",
2156             *redSize, *greenSize, *blueSize, *alphaSize, *totalSize, debug_d3dformat(format_desc->format));
2157     return TRUE;
2158 }
2159
2160 /* Helper function for retrieving depth/stencil info for ChoosePixelFormat and wglChoosePixelFormatARB */
2161 BOOL getDepthStencilBits(const struct GlPixelFormatDesc *format_desc, short *depthSize, short *stencilSize)
2162 {
2163     TRACE("fmt: %s\n", debug_d3dformat(format_desc->format));
2164     switch(format_desc->format)
2165     {
2166         case WINED3DFMT_D16_LOCKABLE:
2167         case WINED3DFMT_D16_UNORM:
2168         case WINED3DFMT_S1_UINT_D15_UNORM:
2169         case WINED3DFMT_X8D24_UNORM:
2170         case WINED3DFMT_S4X4_UINT_D24_UNORM:
2171         case WINED3DFMT_D24_UNORM_S8_UINT:
2172         case WINED3DFMT_S8_UINT_D24_FLOAT:
2173         case WINED3DFMT_D32_UNORM:
2174         case WINED3DFMT_D32_FLOAT:
2175             break;
2176         default:
2177             FIXME("Unsupported stencil format: %s\n", debug_d3dformat(format_desc->format));
2178             return FALSE;
2179     }
2180
2181     *depthSize = format_desc->depth_size;
2182     *stencilSize = format_desc->stencil_size;
2183
2184     TRACE("Returning depthSize: %d and stencilSize: %d for fmt=%s\n",
2185             *depthSize, *stencilSize, debug_d3dformat(format_desc->format));
2186     return TRUE;
2187 }
2188
2189 /* DirectDraw stuff */
2190 WINED3DFORMAT pixelformat_for_depth(DWORD depth) {
2191     switch(depth) {
2192         case 8:  return WINED3DFMT_P8_UINT;
2193         case 15: return WINED3DFMT_B5G5R5X1_UNORM;
2194         case 16: return WINED3DFMT_B5G6R5_UNORM;
2195         case 24: return WINED3DFMT_B8G8R8X8_UNORM; /* Robots needs 24bit to be WINED3DFMT_B8G8R8X8_UNORM */
2196         case 32: return WINED3DFMT_B8G8R8X8_UNORM; /* EVE online and the Fur demo need 32bit AdapterDisplayMode to return WINED3DFMT_B8G8R8X8_UNORM */
2197         default: return WINED3DFMT_UNKNOWN;
2198     }
2199 }
2200
2201 void multiply_matrix(WINED3DMATRIX *dest, const WINED3DMATRIX *src1, const WINED3DMATRIX *src2) {
2202     WINED3DMATRIX temp;
2203
2204     /* Now do the multiplication 'by hand'.
2205        I know that all this could be optimised, but this will be done later :-) */
2206     temp.u.s._11 = (src1->u.s._11 * src2->u.s._11) + (src1->u.s._21 * src2->u.s._12) + (src1->u.s._31 * src2->u.s._13) + (src1->u.s._41 * src2->u.s._14);
2207     temp.u.s._21 = (src1->u.s._11 * src2->u.s._21) + (src1->u.s._21 * src2->u.s._22) + (src1->u.s._31 * src2->u.s._23) + (src1->u.s._41 * src2->u.s._24);
2208     temp.u.s._31 = (src1->u.s._11 * src2->u.s._31) + (src1->u.s._21 * src2->u.s._32) + (src1->u.s._31 * src2->u.s._33) + (src1->u.s._41 * src2->u.s._34);
2209     temp.u.s._41 = (src1->u.s._11 * src2->u.s._41) + (src1->u.s._21 * src2->u.s._42) + (src1->u.s._31 * src2->u.s._43) + (src1->u.s._41 * src2->u.s._44);
2210
2211     temp.u.s._12 = (src1->u.s._12 * src2->u.s._11) + (src1->u.s._22 * src2->u.s._12) + (src1->u.s._32 * src2->u.s._13) + (src1->u.s._42 * src2->u.s._14);
2212     temp.u.s._22 = (src1->u.s._12 * src2->u.s._21) + (src1->u.s._22 * src2->u.s._22) + (src1->u.s._32 * src2->u.s._23) + (src1->u.s._42 * src2->u.s._24);
2213     temp.u.s._32 = (src1->u.s._12 * src2->u.s._31) + (src1->u.s._22 * src2->u.s._32) + (src1->u.s._32 * src2->u.s._33) + (src1->u.s._42 * src2->u.s._34);
2214     temp.u.s._42 = (src1->u.s._12 * src2->u.s._41) + (src1->u.s._22 * src2->u.s._42) + (src1->u.s._32 * src2->u.s._43) + (src1->u.s._42 * src2->u.s._44);
2215
2216     temp.u.s._13 = (src1->u.s._13 * src2->u.s._11) + (src1->u.s._23 * src2->u.s._12) + (src1->u.s._33 * src2->u.s._13) + (src1->u.s._43 * src2->u.s._14);
2217     temp.u.s._23 = (src1->u.s._13 * src2->u.s._21) + (src1->u.s._23 * src2->u.s._22) + (src1->u.s._33 * src2->u.s._23) + (src1->u.s._43 * src2->u.s._24);
2218     temp.u.s._33 = (src1->u.s._13 * src2->u.s._31) + (src1->u.s._23 * src2->u.s._32) + (src1->u.s._33 * src2->u.s._33) + (src1->u.s._43 * src2->u.s._34);
2219     temp.u.s._43 = (src1->u.s._13 * src2->u.s._41) + (src1->u.s._23 * src2->u.s._42) + (src1->u.s._33 * src2->u.s._43) + (src1->u.s._43 * src2->u.s._44);
2220
2221     temp.u.s._14 = (src1->u.s._14 * src2->u.s._11) + (src1->u.s._24 * src2->u.s._12) + (src1->u.s._34 * src2->u.s._13) + (src1->u.s._44 * src2->u.s._14);
2222     temp.u.s._24 = (src1->u.s._14 * src2->u.s._21) + (src1->u.s._24 * src2->u.s._22) + (src1->u.s._34 * src2->u.s._23) + (src1->u.s._44 * src2->u.s._24);
2223     temp.u.s._34 = (src1->u.s._14 * src2->u.s._31) + (src1->u.s._24 * src2->u.s._32) + (src1->u.s._34 * src2->u.s._33) + (src1->u.s._44 * src2->u.s._34);
2224     temp.u.s._44 = (src1->u.s._14 * src2->u.s._41) + (src1->u.s._24 * src2->u.s._42) + (src1->u.s._34 * src2->u.s._43) + (src1->u.s._44 * src2->u.s._44);
2225
2226     /* And copy the new matrix in the good storage.. */
2227     memcpy(dest, &temp, 16 * sizeof(float));
2228 }
2229
2230 DWORD get_flexible_vertex_size(DWORD d3dvtVertexType) {
2231     DWORD size = 0;
2232     int i;
2233     int numTextures = (d3dvtVertexType & WINED3DFVF_TEXCOUNT_MASK) >> WINED3DFVF_TEXCOUNT_SHIFT;
2234
2235     if (d3dvtVertexType & WINED3DFVF_NORMAL) size += 3 * sizeof(float);
2236     if (d3dvtVertexType & WINED3DFVF_DIFFUSE) size += sizeof(DWORD);
2237     if (d3dvtVertexType & WINED3DFVF_SPECULAR) size += sizeof(DWORD);
2238     if (d3dvtVertexType & WINED3DFVF_PSIZE) size += sizeof(DWORD);
2239     switch (d3dvtVertexType & WINED3DFVF_POSITION_MASK) {
2240         case WINED3DFVF_XYZ:    size += 3 * sizeof(float); break;
2241         case WINED3DFVF_XYZRHW: size += 4 * sizeof(float); break;
2242         case WINED3DFVF_XYZB1:  size += 4 * sizeof(float); break;
2243         case WINED3DFVF_XYZB2:  size += 5 * sizeof(float); break;
2244         case WINED3DFVF_XYZB3:  size += 6 * sizeof(float); break;
2245         case WINED3DFVF_XYZB4:  size += 7 * sizeof(float); break;
2246         case WINED3DFVF_XYZB5:  size += 8 * sizeof(float); break;
2247         case WINED3DFVF_XYZW:   size += 4 * sizeof(float); break;
2248         default: ERR("Unexpected position mask\n");
2249     }
2250     for (i = 0; i < numTextures; i++) {
2251         size += GET_TEXCOORD_SIZE_FROM_FVF(d3dvtVertexType, i) * sizeof(float);
2252     }
2253
2254     return size;
2255 }
2256
2257 /***********************************************************************
2258  * CalculateTexRect
2259  *
2260  * Calculates the dimensions of the opengl texture used for blits.
2261  * Handled oversized opengl textures and updates the source rectangle
2262  * accordingly
2263  *
2264  * Params:
2265  *  This: Surface to operate on
2266  *  Rect: Requested rectangle
2267  *
2268  * Returns:
2269  *  TRUE if the texture part can be loaded,
2270  *  FALSE otherwise
2271  *
2272  *********************************************************************/
2273 BOOL CalculateTexRect(IWineD3DSurfaceImpl *This, RECT *Rect, float glTexCoord[4])
2274 {
2275     const struct wined3d_gl_info *gl_info = &This->resource.device->adapter->gl_info;
2276     int x1 = Rect->left, x2 = Rect->right;
2277     int y1 = Rect->top, y2 = Rect->bottom;
2278     GLint maxSize = gl_info->limits.texture_size;
2279
2280     TRACE("(%p)->(%d,%d)-(%d,%d)\n", This,
2281           Rect->left, Rect->top, Rect->right, Rect->bottom);
2282
2283     /* The sizes might be reversed */
2284     if(Rect->left > Rect->right) {
2285         x1 = Rect->right;
2286         x2 = Rect->left;
2287     }
2288     if(Rect->top > Rect->bottom) {
2289         y1 = Rect->bottom;
2290         y2 = Rect->top;
2291     }
2292
2293     /* No oversized texture? This is easy */
2294     if(!(This->Flags & SFLAG_OVERSIZE)) {
2295         /* Which rect from the texture do I need? */
2296         if (This->texture_target == GL_TEXTURE_RECTANGLE_ARB)
2297         {
2298             glTexCoord[0] = (float) Rect->left;
2299             glTexCoord[2] = (float) Rect->top;
2300             glTexCoord[1] = (float) Rect->right;
2301             glTexCoord[3] = (float) Rect->bottom;
2302         } else {
2303             glTexCoord[0] = (float) Rect->left / (float) This->pow2Width;
2304             glTexCoord[2] = (float) Rect->top / (float) This->pow2Height;
2305             glTexCoord[1] = (float) Rect->right / (float) This->pow2Width;
2306             glTexCoord[3] = (float) Rect->bottom / (float) This->pow2Height;
2307         }
2308
2309         return TRUE;
2310     } else {
2311         /* Check if we can succeed at all */
2312         if( (x2 - x1) > maxSize ||
2313             (y2 - y1) > maxSize ) {
2314             TRACE("Requested rectangle is too large for gl\n");
2315             return FALSE;
2316         }
2317
2318         /* A part of the texture has to be picked. First, check if
2319          * some texture part is loaded already, if yes try to re-use it.
2320          * If the texture is dirty, or the part can't be used,
2321          * re-position the part to load
2322          */
2323         if(This->Flags & SFLAG_INTEXTURE) {
2324             if(This->glRect.left <= x1 && This->glRect.right >= x2 &&
2325                This->glRect.top <= y1 && This->glRect.bottom >= x2 ) {
2326                 /* Ok, the rectangle is ok, re-use it */
2327                 TRACE("Using existing gl Texture\n");
2328             } else {
2329                 /* Rectangle is not ok, dirtify the texture to reload it */
2330                 TRACE("Dirtifying texture to force reload\n");
2331                 This->Flags &= ~SFLAG_INTEXTURE;
2332             }
2333         }
2334
2335         /* Now if we are dirty(no else if!) */
2336         if(!(This->Flags & SFLAG_INTEXTURE)) {
2337             /* Set the new rectangle. Use the following strategy:
2338              * 1) Use as big textures as possible.
2339              * 2) Place the texture part in the way that the requested
2340              *    part is in the middle of the texture(well, almost)
2341              * 3) If the texture is moved over the edges of the
2342              *    surface, replace it nicely
2343              * 4) If the coord is not limiting the texture size,
2344              *    use the whole size
2345              */
2346             if((This->pow2Width) > maxSize) {
2347                 This->glRect.left = x1 - maxSize / 2;
2348                 if(This->glRect.left < 0) {
2349                     This->glRect.left = 0;
2350                 }
2351                 This->glRect.right = This->glRect.left + maxSize;
2352                 if(This->glRect.right > This->currentDesc.Width) {
2353                     This->glRect.right = This->currentDesc.Width;
2354                     This->glRect.left = This->glRect.right - maxSize;
2355                 }
2356             } else {
2357                 This->glRect.left = 0;
2358                 This->glRect.right = This->pow2Width;
2359             }
2360
2361             if (This->pow2Height > maxSize)
2362             {
2363                 This->glRect.top = x1 - gl_info->limits.texture_size / 2;
2364                 if(This->glRect.top < 0) This->glRect.top = 0;
2365                 This->glRect.bottom = This->glRect.left + maxSize;
2366                 if(This->glRect.bottom > This->currentDesc.Height) {
2367                     This->glRect.bottom = This->currentDesc.Height;
2368                     This->glRect.top = This->glRect.bottom - maxSize;
2369                 }
2370             } else {
2371                 This->glRect.top = 0;
2372                 This->glRect.bottom = This->pow2Height;
2373             }
2374             TRACE("(%p): Using rect (%d,%d)-(%d,%d)\n", This,
2375                    This->glRect.left, This->glRect.top, This->glRect.right, This->glRect.bottom);
2376         }
2377
2378         /* Re-calculate the rect to draw */
2379         Rect->left -= This->glRect.left;
2380         Rect->right -= This->glRect.left;
2381         Rect->top -= This->glRect.top;
2382         Rect->bottom -= This->glRect.top;
2383
2384         /* Get the gl coordinates. The gl rectangle is a power of 2, eigher the max size,
2385          * or the pow2Width / pow2Height of the surface.
2386          *
2387          * Can never be GL_TEXTURE_RECTANGLE_ARB because oversized surfaces are always set up
2388          * as regular GL_TEXTURE_2D.
2389          */
2390         glTexCoord[0] = (float) Rect->left / (float) (This->glRect.right - This->glRect.left);
2391         glTexCoord[2] = (float) Rect->top / (float) (This->glRect.bottom - This->glRect.top);
2392         glTexCoord[1] = (float) Rect->right / (float) (This->glRect.right - This->glRect.left);
2393         glTexCoord[3] = (float) Rect->bottom / (float) (This->glRect.bottom - This->glRect.top);
2394     }
2395     return TRUE;
2396 }
2397
2398 void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_settings *settings, BOOL ignore_textype) {
2399 #define ARG1 0x01
2400 #define ARG2 0x02
2401 #define ARG0 0x04
2402     static const unsigned char args[WINED3DTOP_LERP + 1] = {
2403         /* undefined                        */  0,
2404         /* D3DTOP_DISABLE                   */  0,
2405         /* D3DTOP_SELECTARG1                */  ARG1,
2406         /* D3DTOP_SELECTARG2                */  ARG2,
2407         /* D3DTOP_MODULATE                  */  ARG1 | ARG2,
2408         /* D3DTOP_MODULATE2X                */  ARG1 | ARG2,
2409         /* D3DTOP_MODULATE4X                */  ARG1 | ARG2,
2410         /* D3DTOP_ADD                       */  ARG1 | ARG2,
2411         /* D3DTOP_ADDSIGNED                 */  ARG1 | ARG2,
2412         /* D3DTOP_ADDSIGNED2X               */  ARG1 | ARG2,
2413         /* D3DTOP_SUBTRACT                  */  ARG1 | ARG2,
2414         /* D3DTOP_ADDSMOOTH                 */  ARG1 | ARG2,
2415         /* D3DTOP_BLENDDIFFUSEALPHA         */  ARG1 | ARG2,
2416         /* D3DTOP_BLENDTEXTUREALPHA         */  ARG1 | ARG2,
2417         /* D3DTOP_BLENDFACTORALPHA          */  ARG1 | ARG2,
2418         /* D3DTOP_BLENDTEXTUREALPHAPM       */  ARG1 | ARG2,
2419         /* D3DTOP_BLENDCURRENTALPHA         */  ARG1 | ARG2,
2420         /* D3DTOP_PREMODULATE               */  ARG1 | ARG2,
2421         /* D3DTOP_MODULATEALPHA_ADDCOLOR    */  ARG1 | ARG2,
2422         /* D3DTOP_MODULATECOLOR_ADDALPHA    */  ARG1 | ARG2,
2423         /* D3DTOP_MODULATEINVALPHA_ADDCOLOR */  ARG1 | ARG2,
2424         /* D3DTOP_MODULATEINVCOLOR_ADDALPHA */  ARG1 | ARG2,
2425         /* D3DTOP_BUMPENVMAP                */  ARG1 | ARG2,
2426         /* D3DTOP_BUMPENVMAPLUMINANCE       */  ARG1 | ARG2,
2427         /* D3DTOP_DOTPRODUCT3               */  ARG1 | ARG2,
2428         /* D3DTOP_MULTIPLYADD               */  ARG1 | ARG2 | ARG0,
2429         /* D3DTOP_LERP                      */  ARG1 | ARG2 | ARG0
2430     };
2431     unsigned int i;
2432     DWORD ttff;
2433     DWORD cop, aop, carg0, carg1, carg2, aarg0, aarg1, aarg2;
2434     IWineD3DDeviceImpl *device = stateblock->device;
2435     const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
2436
2437     for (i = 0; i < gl_info->limits.texture_stages; ++i)
2438     {
2439         IWineD3DBaseTextureImpl *texture;
2440         settings->op[i].padding = 0;
2441         if(stateblock->textureState[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE) {
2442             settings->op[i].cop = WINED3DTOP_DISABLE;
2443             settings->op[i].aop = WINED3DTOP_DISABLE;
2444             settings->op[i].carg0 = settings->op[i].carg1 = settings->op[i].carg2 = ARG_UNUSED;
2445             settings->op[i].aarg0 = settings->op[i].aarg1 = settings->op[i].aarg2 = ARG_UNUSED;
2446             settings->op[i].color_fixup = COLOR_FIXUP_IDENTITY;
2447             settings->op[i].dst = resultreg;
2448             settings->op[i].tex_type = tex_1d;
2449             settings->op[i].projected = proj_none;
2450             i++;
2451             break;
2452         }
2453
2454         texture = (IWineD3DBaseTextureImpl *) stateblock->textures[i];
2455         if(texture) {
2456             settings->op[i].color_fixup = texture->resource.format_desc->color_fixup;
2457             if(ignore_textype) {
2458                 settings->op[i].tex_type = tex_1d;
2459             } else {
2460                 switch (IWineD3DBaseTexture_GetTextureDimensions((IWineD3DBaseTexture *)texture)) {
2461                     case GL_TEXTURE_1D:
2462                         settings->op[i].tex_type = tex_1d;
2463                         break;
2464                     case GL_TEXTURE_2D:
2465                         settings->op[i].tex_type = tex_2d;
2466                         break;
2467                     case GL_TEXTURE_3D:
2468                         settings->op[i].tex_type = tex_3d;
2469                         break;
2470                     case GL_TEXTURE_CUBE_MAP_ARB:
2471                         settings->op[i].tex_type = tex_cube;
2472                         break;
2473                     case GL_TEXTURE_RECTANGLE_ARB:
2474                         settings->op[i].tex_type = tex_rect;
2475                         break;
2476                 }
2477             }
2478         } else {
2479             settings->op[i].color_fixup = COLOR_FIXUP_IDENTITY;
2480             settings->op[i].tex_type = tex_1d;
2481         }
2482
2483         cop = stateblock->textureState[i][WINED3DTSS_COLOROP];
2484         aop = stateblock->textureState[i][WINED3DTSS_ALPHAOP];
2485
2486         carg1 = (args[cop] & ARG1) ? stateblock->textureState[i][WINED3DTSS_COLORARG1] : ARG_UNUSED;
2487         carg2 = (args[cop] & ARG2) ? stateblock->textureState[i][WINED3DTSS_COLORARG2] : ARG_UNUSED;
2488         carg0 = (args[cop] & ARG0) ? stateblock->textureState[i][WINED3DTSS_COLORARG0] : ARG_UNUSED;
2489
2490         if(is_invalid_op(device, i, cop, carg1, carg2, carg0)) {
2491             carg0 = ARG_UNUSED;
2492             carg2 = ARG_UNUSED;
2493             carg1 = WINED3DTA_CURRENT;
2494             cop = WINED3DTOP_SELECTARG1;
2495         }
2496
2497         if(cop == WINED3DTOP_DOTPRODUCT3) {
2498             /* A dotproduct3 on the colorop overwrites the alphaop operation and replicates
2499              * the color result to the alpha component of the destination
2500              */
2501             aop = cop;
2502             aarg1 = carg1;
2503             aarg2 = carg2;
2504             aarg0 = carg0;
2505         } else {
2506             aarg1 = (args[aop] & ARG1) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG1] : ARG_UNUSED;
2507             aarg2 = (args[aop] & ARG2) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG2] : ARG_UNUSED;
2508             aarg0 = (args[aop] & ARG0) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG0] : ARG_UNUSED;
2509         }
2510
2511         if (i == 0 && stateblock->textures[0] && stateblock->renderState[WINED3DRS_COLORKEYENABLE])
2512         {
2513             UINT texture_dimensions = IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[0]);
2514
2515             if (texture_dimensions == GL_TEXTURE_2D || texture_dimensions == GL_TEXTURE_RECTANGLE_ARB)
2516             {
2517                 IWineD3DSurfaceImpl *surf;
2518                 surf = (IWineD3DSurfaceImpl *) ((IWineD3DTextureImpl *) stateblock->textures[0])->surfaces[0];
2519
2520                 if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format_desc->alpha_mask)
2521                 {
2522                     if (aop == WINED3DTOP_DISABLE)
2523                     {
2524                        aarg1 = WINED3DTA_TEXTURE;
2525                        aop = WINED3DTOP_SELECTARG1;
2526                     }
2527                     else if (aop == WINED3DTOP_SELECTARG1 && aarg1 != WINED3DTA_TEXTURE)
2528                     {
2529                         if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
2530                         {
2531                             aarg2 = WINED3DTA_TEXTURE;
2532                             aop = WINED3DTOP_MODULATE;
2533                         }
2534                         else aarg1 = WINED3DTA_TEXTURE;
2535                     }
2536                     else if (aop == WINED3DTOP_SELECTARG2 && aarg2 != WINED3DTA_TEXTURE)
2537                     {
2538                         if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
2539                         {
2540                             aarg1 = WINED3DTA_TEXTURE;
2541                             aop = WINED3DTOP_MODULATE;
2542                         }
2543                         else aarg2 = WINED3DTA_TEXTURE;
2544                     }
2545                 }
2546             }
2547         }
2548
2549         if(is_invalid_op(device, i, aop, aarg1, aarg2, aarg0)) {
2550                aarg0 = ARG_UNUSED;
2551                aarg2 = ARG_UNUSED;
2552                aarg1 = WINED3DTA_CURRENT;
2553                aop = WINED3DTOP_SELECTARG1;
2554         }
2555
2556         if(carg1 == WINED3DTA_TEXTURE || carg2 == WINED3DTA_TEXTURE || carg0 == WINED3DTA_TEXTURE ||
2557            aarg1 == WINED3DTA_TEXTURE || aarg2 == WINED3DTA_TEXTURE || aarg0 == WINED3DTA_TEXTURE) {
2558             ttff = stateblock->textureState[i][WINED3DTSS_TEXTURETRANSFORMFLAGS];
2559             if(ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT3)) {
2560                 settings->op[i].projected = proj_count3;
2561             } else if(ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT4)) {
2562                 settings->op[i].projected = proj_count4;
2563             } else {
2564                 settings->op[i].projected = proj_none;
2565             }
2566         } else {
2567             settings->op[i].projected = proj_none;
2568         }
2569
2570         settings->op[i].cop = cop;
2571         settings->op[i].aop = aop;
2572         settings->op[i].carg0 = carg0;
2573         settings->op[i].carg1 = carg1;
2574         settings->op[i].carg2 = carg2;
2575         settings->op[i].aarg0 = aarg0;
2576         settings->op[i].aarg1 = aarg1;
2577         settings->op[i].aarg2 = aarg2;
2578
2579         if(stateblock->textureState[i][WINED3DTSS_RESULTARG] == WINED3DTA_TEMP) {
2580             settings->op[i].dst = tempreg;
2581         } else {
2582             settings->op[i].dst = resultreg;
2583         }
2584     }
2585
2586     /* Clear unsupported stages */
2587     for(; i < MAX_TEXTURES; i++) {
2588         memset(&settings->op[i], 0xff, sizeof(settings->op[i]));
2589     }
2590
2591     if(stateblock->renderState[WINED3DRS_FOGENABLE] == FALSE) {
2592         settings->fog = FOG_OFF;
2593     } else if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE) {
2594         if(use_vs(stateblock) || ((IWineD3DVertexDeclarationImpl *) stateblock->vertexDecl)->position_transformed) {
2595             settings->fog = FOG_LINEAR;
2596         } else {
2597             switch(stateblock->renderState[WINED3DRS_FOGVERTEXMODE]) {
2598                 case WINED3DFOG_NONE:
2599                 case WINED3DFOG_LINEAR:
2600                     settings->fog = FOG_LINEAR;
2601                     break;
2602                 case WINED3DFOG_EXP:
2603                     settings->fog = FOG_EXP;
2604                     break;
2605                 case WINED3DFOG_EXP2:
2606                     settings->fog = FOG_EXP2;
2607                     break;
2608             }
2609         }
2610     } else {
2611         switch(stateblock->renderState[WINED3DRS_FOGTABLEMODE]) {
2612             case WINED3DFOG_LINEAR:
2613                 settings->fog = FOG_LINEAR;
2614                 break;
2615             case WINED3DFOG_EXP:
2616                 settings->fog = FOG_EXP;
2617                 break;
2618             case WINED3DFOG_EXP2:
2619                 settings->fog = FOG_EXP2;
2620                 break;
2621         }
2622     }
2623     if(stateblock->renderState[WINED3DRS_SRGBWRITEENABLE]) {
2624         settings->sRGB_write = 1;
2625     } else {
2626         settings->sRGB_write = 0;
2627     }
2628     if(device->vs_clipping || !use_vs(stateblock) || !stateblock->renderState[WINED3DRS_CLIPPING] ||
2629        !stateblock->renderState[WINED3DRS_CLIPPLANEENABLE]) {
2630         /* No need to emulate clipplanes if GL supports native vertex shader clipping or if
2631          * the fixed function vertex pipeline is used(which always supports clipplanes), or
2632          * if no clipplane is enabled
2633          */
2634         settings->emul_clipplanes = 0;
2635     } else {
2636         settings->emul_clipplanes = 1;
2637     }
2638 }
2639
2640 const struct ffp_frag_desc *find_ffp_frag_shader(const struct wine_rb_tree *fragment_shaders,
2641         const struct ffp_frag_settings *settings)
2642 {
2643     struct wine_rb_entry *entry = wine_rb_get(fragment_shaders, settings);
2644     return entry ? WINE_RB_ENTRY_VALUE(entry, struct ffp_frag_desc, entry) : NULL;
2645 }
2646
2647 void add_ffp_frag_shader(struct wine_rb_tree *shaders, struct ffp_frag_desc *desc)
2648 {
2649     /* Note that the key is the implementation independent part of the ffp_frag_desc structure,
2650      * whereas desc points to an extended structure with implementation specific parts. */
2651     if (wine_rb_put(shaders, &desc->settings, &desc->entry) == -1)
2652     {
2653         ERR("Failed to insert ffp frag shader.\n");
2654     }
2655 }
2656
2657 /* Activates the texture dimension according to the bound D3D texture.
2658  * Does not care for the colorop or correct gl texture unit(when using nvrc)
2659  * Requires the caller to activate the correct unit before
2660  */
2661 /* GL locking is done by the caller (state handler) */
2662 void texture_activate_dimensions(DWORD stage, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
2663 {
2664     const struct wined3d_gl_info *gl_info = context->gl_info;
2665
2666     if (stateblock->textures[stage])
2667     {
2668         switch (IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[stage])) {
2669             case GL_TEXTURE_2D:
2670                 glDisable(GL_TEXTURE_3D);
2671                 checkGLcall("glDisable(GL_TEXTURE_3D)");
2672                 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2673                 {
2674                     glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2675                     checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2676                 }
2677                 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2678                 {
2679                     glDisable(GL_TEXTURE_RECTANGLE_ARB);
2680                     checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2681                 }
2682                 glEnable(GL_TEXTURE_2D);
2683                 checkGLcall("glEnable(GL_TEXTURE_2D)");
2684                 break;
2685             case GL_TEXTURE_RECTANGLE_ARB:
2686                 glDisable(GL_TEXTURE_2D);
2687                 checkGLcall("glDisable(GL_TEXTURE_2D)");
2688                 glDisable(GL_TEXTURE_3D);
2689                 checkGLcall("glDisable(GL_TEXTURE_3D)");
2690                 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2691                 {
2692                     glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2693                     checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2694                 }
2695                 glEnable(GL_TEXTURE_RECTANGLE_ARB);
2696                 checkGLcall("glEnable(GL_TEXTURE_RECTANGLE_ARB)");
2697                 break;
2698             case GL_TEXTURE_3D:
2699                 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2700                 {
2701                     glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2702                     checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2703                 }
2704                 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2705                 {
2706                     glDisable(GL_TEXTURE_RECTANGLE_ARB);
2707                     checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2708                 }
2709                 glDisable(GL_TEXTURE_2D);
2710                 checkGLcall("glDisable(GL_TEXTURE_2D)");
2711                 glEnable(GL_TEXTURE_3D);
2712                 checkGLcall("glEnable(GL_TEXTURE_3D)");
2713                 break;
2714             case GL_TEXTURE_CUBE_MAP_ARB:
2715                 glDisable(GL_TEXTURE_2D);
2716                 checkGLcall("glDisable(GL_TEXTURE_2D)");
2717                 glDisable(GL_TEXTURE_3D);
2718                 checkGLcall("glDisable(GL_TEXTURE_3D)");
2719                 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2720                 {
2721                     glDisable(GL_TEXTURE_RECTANGLE_ARB);
2722                     checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2723                 }
2724                 glEnable(GL_TEXTURE_CUBE_MAP_ARB);
2725                 checkGLcall("glEnable(GL_TEXTURE_CUBE_MAP_ARB)");
2726               break;
2727         }
2728     } else {
2729         glEnable(GL_TEXTURE_2D);
2730         checkGLcall("glEnable(GL_TEXTURE_2D)");
2731         glDisable(GL_TEXTURE_3D);
2732         checkGLcall("glDisable(GL_TEXTURE_3D)");
2733         if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2734         {
2735             glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2736             checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2737         }
2738         if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2739         {
2740             glDisable(GL_TEXTURE_RECTANGLE_ARB);
2741             checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2742         }
2743         /* Binding textures is done by samplers. A dummy texture will be bound */
2744     }
2745 }
2746
2747 /* GL locking is done by the caller (state handler) */
2748 void sampler_texdim(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
2749 {
2750     DWORD sampler = state - STATE_SAMPLER(0);
2751     DWORD mapped_stage = stateblock->device->texUnitMap[sampler];
2752
2753     /* No need to enable / disable anything here for unused samplers. The tex_colorop
2754     * handler takes care. Also no action is needed with pixel shaders, or if tex_colorop
2755     * will take care of this business
2756     */
2757     if (mapped_stage == WINED3D_UNMAPPED_STAGE || mapped_stage >= context->gl_info->limits.textures) return;
2758     if(sampler >= stateblock->lowest_disabled_stage) return;
2759     if(isStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP))) return;
2760
2761     texture_activate_dimensions(sampler, stateblock, context);
2762 }
2763
2764 void *wined3d_rb_alloc(size_t size)
2765 {
2766     return HeapAlloc(GetProcessHeap(), 0, size);
2767 }
2768
2769 void *wined3d_rb_realloc(void *ptr, size_t size)
2770 {
2771     return HeapReAlloc(GetProcessHeap(), 0, ptr, size);
2772 }
2773
2774 void wined3d_rb_free(void *ptr)
2775 {
2776     HeapFree(GetProcessHeap(), 0, ptr);
2777 }
2778
2779 static int ffp_frag_program_key_compare(const void *key, const struct wine_rb_entry *entry)
2780 {
2781     const struct ffp_frag_settings *ka = key;
2782     const struct ffp_frag_settings *kb = &WINE_RB_ENTRY_VALUE(entry, const struct ffp_frag_desc, entry)->settings;
2783
2784     return memcmp(ka, kb, sizeof(*ka));
2785 }
2786
2787 const struct wine_rb_functions wined3d_ffp_frag_program_rb_functions =
2788 {
2789     wined3d_rb_alloc,
2790     wined3d_rb_realloc,
2791     wined3d_rb_free,
2792     ffp_frag_program_key_compare,
2793 };
2794
2795 UINT wined3d_log2i(UINT32 x)
2796 {
2797     static const UINT l[] =
2798     {
2799         ~0U, 0, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3,
2800           4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
2801           5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
2802           5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
2803           6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2804           6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2805           6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2806           6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2807           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2808           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2809           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2810           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2811           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2812           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2813           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2814           7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2815     };
2816     UINT32 i;
2817
2818     return (i = x >> 16) ? (x = i >> 8) ? l[x] + 24 : l[i] + 16 : (i = x >> 8) ? l[i] + 8 : l[x];
2819 }
2820
2821 /* Set the shader type for this device, depending on the given capabilities
2822  * and the user preferences in wined3d_settings. */
2823 void select_shader_mode(const struct wined3d_gl_info *gl_info, int *ps_selected, int *vs_selected)
2824 {
2825     if (wined3d_settings.vs_mode == VS_NONE) *vs_selected = SHADER_NONE;
2826     else if (gl_info->supported[ARB_VERTEX_SHADER] && wined3d_settings.glslRequested)
2827     {
2828         /* Geforce4 cards support GLSL but for vertex shaders only. Further its reported GLSL caps are
2829          * wrong. This combined with the fact that glsl won't offer more features or performance, use ARB
2830          * shaders only on this card. */
2831         if (gl_info->supported[NV_VERTEX_PROGRAM] && !gl_info->supported[NV_VERTEX_PROGRAM2]) *vs_selected = SHADER_ARB;
2832         else *vs_selected = SHADER_GLSL;
2833     }
2834     else if (gl_info->supported[ARB_VERTEX_PROGRAM]) *vs_selected = SHADER_ARB;
2835     else *vs_selected = SHADER_NONE;
2836
2837     if (wined3d_settings.ps_mode == PS_NONE) *ps_selected = SHADER_NONE;
2838     else if (gl_info->supported[ARB_FRAGMENT_SHADER] && wined3d_settings.glslRequested) *ps_selected = SHADER_GLSL;
2839     else if (gl_info->supported[ARB_FRAGMENT_PROGRAM]) *ps_selected = SHADER_ARB;
2840     else if (gl_info->supported[ATI_FRAGMENT_SHADER]) *ps_selected = SHADER_ATI;
2841     else *ps_selected = SHADER_NONE;
2842 }
2843
2844 const shader_backend_t *select_shader_backend(struct wined3d_adapter *adapter, WINED3DDEVTYPE device_type)
2845 {
2846     int vs_selected_mode, ps_selected_mode;
2847
2848     select_shader_mode(&adapter->gl_info, &ps_selected_mode, &vs_selected_mode);
2849     if (vs_selected_mode == SHADER_GLSL || ps_selected_mode == SHADER_GLSL) return &glsl_shader_backend;
2850     if (vs_selected_mode == SHADER_ARB || ps_selected_mode == SHADER_ARB) return &arb_program_shader_backend;
2851     return &none_shader_backend;
2852 }
2853
2854 const struct fragment_pipeline *select_fragment_implementation(struct wined3d_adapter *adapter,
2855         WINED3DDEVTYPE device_type)
2856 {
2857     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
2858     int vs_selected_mode, ps_selected_mode;
2859
2860     select_shader_mode(gl_info, &ps_selected_mode, &vs_selected_mode);
2861     if ((ps_selected_mode == SHADER_ARB || ps_selected_mode == SHADER_GLSL)
2862             && gl_info->supported[ARB_FRAGMENT_PROGRAM]) return &arbfp_fragment_pipeline;
2863     else if (ps_selected_mode == SHADER_ATI) return &atifs_fragment_pipeline;
2864     else if (gl_info->supported[NV_REGISTER_COMBINERS]
2865             && gl_info->supported[NV_TEXTURE_SHADER2]) return &nvts_fragment_pipeline;
2866     else if (gl_info->supported[NV_REGISTER_COMBINERS]) return &nvrc_fragment_pipeline;
2867     else return &ffp_fragment_pipeline;
2868 }
2869
2870 const struct blit_shader *select_blit_implementation(struct wined3d_adapter *adapter, WINED3DDEVTYPE device_type)
2871 {
2872     const struct wined3d_gl_info *gl_info = &adapter->gl_info;
2873     int vs_selected_mode, ps_selected_mode;
2874
2875     select_shader_mode(gl_info, &ps_selected_mode, &vs_selected_mode);
2876     if ((ps_selected_mode == SHADER_ARB || ps_selected_mode == SHADER_GLSL)
2877             && gl_info->supported[ARB_FRAGMENT_PROGRAM]) return &arbfp_blit;
2878     else return &ffp_blit;
2879 }