2 * Utility functions for the WineD3D Library
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
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.
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.
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
28 #include "wined3d_private.h"
30 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
32 struct StaticPixelFormatDesc
35 DWORD alphaMask, redMask, greenMask, blueMask;
37 short depthSize, stencilSize;
40 /*****************************************************************************
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.
50 static const struct StaticPixelFormatDesc formats[] =
52 /* WINED3DFORMAT alphamask redmask greenmask bluemask bpp depth stencil */
53 {WINED3DFMT_UNKNOWN, 0x0, 0x0, 0x0, 0x0, 0, 0, 0},
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},
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},
72 {WINED3DFMT_R8G8_SNORM_Cx, 0x0, 0x0, 0x0, 0x0, 2, 0, 0},
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},
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},
136 struct wined3d_format_base_flags
138 WINED3DFORMAT format;
142 static const struct wined3d_format_base_flags format_base_flags[] =
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 {WINED3DFMT_R32_FLOAT, WINED3DFMT_FLAG_FLOAT},
170 {WINED3DFMT_R32G32_FLOAT, WINED3DFMT_FLAG_FLOAT},
171 {WINED3DFMT_R32G32B32_FLOAT, WINED3DFMT_FLAG_FLOAT},
172 {WINED3DFMT_R32G32B32A32_FLOAT, WINED3DFMT_FLAG_FLOAT},
173 {WINED3DFMT_R16_FLOAT, WINED3DFMT_FLAG_FLOAT},
174 {WINED3DFMT_R16G16_FLOAT, WINED3DFMT_FLAG_FLOAT},
175 {WINED3DFMT_R16G16B16A16_FLOAT, WINED3DFMT_FLAG_FLOAT},
176 {WINED3DFMT_D32_FLOAT, WINED3DFMT_FLAG_FLOAT},
177 {WINED3DFMT_S8_UINT_D24_FLOAT, WINED3DFMT_FLAG_FLOAT},
180 struct wined3d_format_compression_info
182 WINED3DFORMAT format;
185 UINT block_byte_count;
188 static const struct wined3d_format_compression_info format_compression_info[] =
190 {WINED3DFMT_DXT1, 4, 4, 8},
191 {WINED3DFMT_DXT2, 4, 4, 16},
192 {WINED3DFMT_DXT3, 4, 4, 16},
193 {WINED3DFMT_DXT4, 4, 4, 16},
194 {WINED3DFMT_DXT5, 4, 4, 16},
195 {WINED3DFMT_ATI2N, 1, 1, 1},
198 struct wined3d_format_vertex_info
200 WINED3DFORMAT format;
201 enum wined3d_ffp_emit_idx emit_idx;
202 GLint component_count;
205 GLboolean gl_normalized;
206 unsigned int component_size;
209 static const struct wined3d_format_vertex_info format_vertex_info[] =
211 {WINED3DFMT_R32_FLOAT, WINED3D_FFP_EMIT_FLOAT1, 1, GL_FLOAT, 1, GL_FALSE, sizeof(float)},
212 {WINED3DFMT_R32G32_FLOAT, WINED3D_FFP_EMIT_FLOAT2, 2, GL_FLOAT, 2, GL_FALSE, sizeof(float)},
213 {WINED3DFMT_R32G32B32_FLOAT, WINED3D_FFP_EMIT_FLOAT3, 3, GL_FLOAT, 3, GL_FALSE, sizeof(float)},
214 {WINED3DFMT_R32G32B32A32_FLOAT, WINED3D_FFP_EMIT_FLOAT4, 4, GL_FLOAT, 4, GL_FALSE, sizeof(float)},
215 {WINED3DFMT_B8G8R8A8_UNORM, WINED3D_FFP_EMIT_D3DCOLOR, 4, GL_UNSIGNED_BYTE, 4, GL_TRUE, sizeof(BYTE)},
216 {WINED3DFMT_R8G8B8A8_UINT, WINED3D_FFP_EMIT_UBYTE4, 4, GL_UNSIGNED_BYTE, 4, GL_FALSE, sizeof(BYTE)},
217 {WINED3DFMT_R16G16_SINT, WINED3D_FFP_EMIT_SHORT2, 2, GL_SHORT, 2, GL_FALSE, sizeof(short int)},
218 {WINED3DFMT_R16G16B16A16_SINT, WINED3D_FFP_EMIT_SHORT4, 4, GL_SHORT, 4, GL_FALSE, sizeof(short int)},
219 {WINED3DFMT_R8G8B8A8_UNORM, WINED3D_FFP_EMIT_UBYTE4N, 4, GL_UNSIGNED_BYTE, 4, GL_TRUE, sizeof(BYTE)},
220 {WINED3DFMT_R16G16_SNORM, WINED3D_FFP_EMIT_SHORT2N, 2, GL_SHORT, 2, GL_TRUE, sizeof(short int)},
221 {WINED3DFMT_R16G16B16A16_SNORM, WINED3D_FFP_EMIT_SHORT4N, 4, GL_SHORT, 4, GL_TRUE, sizeof(short int)},
222 {WINED3DFMT_R16G16_UNORM, WINED3D_FFP_EMIT_USHORT2N, 2, GL_UNSIGNED_SHORT, 2, GL_TRUE, sizeof(short int)},
223 {WINED3DFMT_R16G16B16A16_UNORM, WINED3D_FFP_EMIT_USHORT4N, 4, GL_UNSIGNED_SHORT, 4, GL_TRUE, sizeof(short int)},
224 {WINED3DFMT_R10G10B10A2_UINT, WINED3D_FFP_EMIT_UDEC3, 3, GL_UNSIGNED_SHORT, 3, GL_FALSE, sizeof(short int)},
225 {WINED3DFMT_R10G10B10A2_SNORM, WINED3D_FFP_EMIT_DEC3N, 3, GL_SHORT, 3, GL_TRUE, sizeof(short int)},
226 {WINED3DFMT_R16G16_FLOAT, WINED3D_FFP_EMIT_FLOAT16_2, 2, GL_FLOAT, 2, GL_FALSE, sizeof(GLhalfNV)},
227 {WINED3DFMT_R16G16B16A16_FLOAT, WINED3D_FFP_EMIT_FLOAT16_4, 4, GL_FLOAT, 4, GL_FALSE, sizeof(GLhalfNV)}
230 struct wined3d_format_texture_info
232 WINED3DFORMAT format;
234 GLint gl_srgb_internal;
235 GLint gl_rt_internal;
239 GL_SupportedExt extension;
242 static const struct wined3d_format_texture_info format_texture_info[] =
244 /* WINED3DFORMAT internal srgbInternal rtInternal
249 /* GL_APPLE_ycbcr_422 claims that its '2YUV' format, which is supported via the UNSIGNED_SHORT_8_8_REV_APPLE type
250 * is equivalent to 'UYVY' format on Windows, and the 'YUVS' via UNSIGNED_SHORT_8_8_APPLE equates to 'YUY2'. The
251 * d3d9 test however shows that the opposite is true. Since the extension is from 2002, it predates the x86 based
252 * Macs, so probably the endianess differs. This could be tested as soon as we have a Windows and MacOS on a big
255 {WINED3DFMT_UYVY, GL_LUMINANCE_ALPHA, GL_LUMINANCE_ALPHA, 0,
256 GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
257 WINED3DFMT_FLAG_FILTERING,
258 WINED3D_GL_EXT_NONE},
259 {WINED3DFMT_UYVY, GL_RGB, GL_RGB, 0,
260 GL_YCBCR_422_APPLE, UNSIGNED_SHORT_8_8_APPLE,
261 WINED3DFMT_FLAG_FILTERING,
263 {WINED3DFMT_YUY2, GL_LUMINANCE_ALPHA, GL_LUMINANCE_ALPHA, 0,
264 GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
265 WINED3DFMT_FLAG_FILTERING,
266 WINED3D_GL_EXT_NONE},
267 {WINED3DFMT_YUY2, GL_RGB, GL_RGB, 0,
268 GL_YCBCR_422_APPLE, UNSIGNED_SHORT_8_8_REV_APPLE,
269 WINED3DFMT_FLAG_FILTERING,
271 {WINED3DFMT_YV12, GL_ALPHA, GL_ALPHA, 0,
272 GL_ALPHA, GL_UNSIGNED_BYTE,
273 WINED3DFMT_FLAG_FILTERING,
274 WINED3D_GL_EXT_NONE},
275 {WINED3DFMT_DXT1, GL_COMPRESSED_RGBA_S3TC_DXT1_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT, 0,
276 GL_RGBA, GL_UNSIGNED_BYTE,
277 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
278 EXT_TEXTURE_COMPRESSION_S3TC},
279 {WINED3DFMT_DXT2, GL_COMPRESSED_RGBA_S3TC_DXT3_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT, 0,
280 GL_RGBA, GL_UNSIGNED_BYTE,
281 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
282 EXT_TEXTURE_COMPRESSION_S3TC},
283 {WINED3DFMT_DXT3, GL_COMPRESSED_RGBA_S3TC_DXT3_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT, 0,
284 GL_RGBA, GL_UNSIGNED_BYTE,
285 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
286 EXT_TEXTURE_COMPRESSION_S3TC},
287 {WINED3DFMT_DXT4, GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, 0,
288 GL_RGBA, GL_UNSIGNED_BYTE,
289 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
290 EXT_TEXTURE_COMPRESSION_S3TC},
291 {WINED3DFMT_DXT5, GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, 0,
292 GL_RGBA, GL_UNSIGNED_BYTE,
293 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
294 EXT_TEXTURE_COMPRESSION_S3TC},
296 {WINED3DFMT_R32_FLOAT, GL_RGB32F_ARB, GL_RGB32F_ARB, 0,
298 WINED3DFMT_FLAG_RENDERTARGET,
300 {WINED3DFMT_R32_FLOAT, GL_R32F, GL_R32F, 0,
302 WINED3DFMT_FLAG_RENDERTARGET,
304 {WINED3DFMT_R32G32_FLOAT, GL_RGB32F_ARB, GL_RGB32F_ARB, 0,
306 WINED3DFMT_FLAG_RENDERTARGET,
308 {WINED3DFMT_R32G32_FLOAT, GL_RG32F, GL_RG32F, 0,
310 WINED3DFMT_FLAG_RENDERTARGET,
312 {WINED3DFMT_R32G32B32A32_FLOAT, GL_RGBA32F_ARB, GL_RGBA32F_ARB, 0,
314 WINED3DFMT_FLAG_RENDERTARGET,
317 {WINED3DFMT_R16_FLOAT, GL_RGB16F_ARB, GL_RGB16F_ARB, 0,
318 GL_RED, GL_HALF_FLOAT_ARB,
319 WINED3DFMT_FLAG_RENDERTARGET,
321 {WINED3DFMT_R16_FLOAT, GL_R16F, GL_R16F, 0,
322 GL_RED, GL_HALF_FLOAT_ARB,
323 WINED3DFMT_FLAG_RENDERTARGET,
325 {WINED3DFMT_R16G16_FLOAT, GL_RGB16F_ARB, GL_RGB16F_ARB, 0,
326 GL_RGB, GL_HALF_FLOAT_ARB,
327 WINED3DFMT_FLAG_RENDERTARGET,
329 {WINED3DFMT_R16G16_FLOAT, GL_RG16F, GL_RG16F, 0,
330 GL_RG, GL_HALF_FLOAT_ARB,
331 WINED3DFMT_FLAG_RENDERTARGET,
333 {WINED3DFMT_R16G16B16A16_FLOAT, GL_RGBA16F_ARB, GL_RGBA16F_ARB, 0,
334 GL_RGBA, GL_HALF_FLOAT_ARB,
335 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_RENDERTARGET,
337 /* Palettized formats */
338 {WINED3DFMT_P8_UINT, GL_RGBA, GL_RGBA, 0,
339 GL_RGBA, GL_UNSIGNED_BYTE,
341 ARB_FRAGMENT_PROGRAM},
342 {WINED3DFMT_P8_UINT, GL_COLOR_INDEX8_EXT, GL_COLOR_INDEX8_EXT, 0,
343 GL_COLOR_INDEX, GL_UNSIGNED_BYTE,
345 EXT_PALETTED_TEXTURE},
346 /* Standard ARGB formats */
347 {WINED3DFMT_B8G8R8_UNORM, GL_RGB8, GL_RGB8, 0,
348 GL_BGR, GL_UNSIGNED_BYTE,
349 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
350 WINED3D_GL_EXT_NONE},
351 {WINED3DFMT_B8G8R8A8_UNORM, GL_RGBA8, GL_SRGB8_ALPHA8_EXT, 0,
352 GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV,
353 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
354 WINED3D_GL_EXT_NONE},
355 {WINED3DFMT_B8G8R8X8_UNORM, GL_RGB8, GL_SRGB8_EXT, 0,
356 GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV,
357 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
358 WINED3D_GL_EXT_NONE},
359 {WINED3DFMT_B5G6R5_UNORM, GL_RGB5, GL_RGB5, GL_RGB8,
360 GL_RGB, GL_UNSIGNED_SHORT_5_6_5,
361 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
362 WINED3D_GL_EXT_NONE},
363 {WINED3DFMT_B5G5R5X1_UNORM, GL_RGB5, GL_RGB5_A1, 0,
364 GL_BGRA, GL_UNSIGNED_SHORT_1_5_5_5_REV,
365 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
366 WINED3D_GL_EXT_NONE},
367 {WINED3DFMT_B5G5R5A1_UNORM, GL_RGB5_A1, GL_RGB5_A1, 0,
368 GL_BGRA, GL_UNSIGNED_SHORT_1_5_5_5_REV,
369 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
370 WINED3D_GL_EXT_NONE},
371 {WINED3DFMT_B4G4R4A4_UNORM, GL_RGBA4, GL_SRGB8_ALPHA8_EXT, 0,
372 GL_BGRA, GL_UNSIGNED_SHORT_4_4_4_4_REV,
373 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
374 WINED3D_GL_EXT_NONE},
375 {WINED3DFMT_B2G3R3_UNORM, GL_R3_G3_B2, GL_R3_G3_B2, 0,
376 GL_RGB, GL_UNSIGNED_BYTE_3_3_2,
377 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING,
378 WINED3D_GL_EXT_NONE},
379 {WINED3DFMT_A8_UNORM, GL_ALPHA8, GL_ALPHA8, 0,
380 GL_ALPHA, GL_UNSIGNED_BYTE,
381 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING,
382 WINED3D_GL_EXT_NONE},
383 {WINED3DFMT_B4G4R4X4_UNORM, GL_RGB4, GL_RGB4, 0,
384 GL_BGRA, GL_UNSIGNED_SHORT_4_4_4_4_REV,
385 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
386 WINED3D_GL_EXT_NONE},
387 {WINED3DFMT_R10G10B10A2_UNORM, GL_RGB10_A2, GL_RGB10_A2, 0,
388 GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV,
389 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
390 WINED3D_GL_EXT_NONE},
391 {WINED3DFMT_R8G8B8A8_UNORM, GL_RGBA8, GL_RGBA8, 0,
392 GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV,
393 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
394 WINED3D_GL_EXT_NONE},
395 {WINED3DFMT_R8G8B8X8_UNORM, GL_RGB8, GL_RGB8, 0,
396 GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV,
397 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
398 WINED3D_GL_EXT_NONE},
399 {WINED3DFMT_R16G16_UNORM, GL_RGB16, GL_RGB16, GL_RGBA16,
400 GL_RGB, GL_UNSIGNED_SHORT,
401 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
402 WINED3D_GL_EXT_NONE},
403 {WINED3DFMT_B10G10R10A2_UNORM, GL_RGB10_A2, GL_RGB10_A2, 0,
404 GL_BGRA, GL_UNSIGNED_INT_2_10_10_10_REV,
405 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
406 WINED3D_GL_EXT_NONE},
407 {WINED3DFMT_R16G16B16A16_UNORM, GL_RGBA16, GL_RGBA16, 0,
408 GL_RGBA, GL_UNSIGNED_SHORT,
409 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_RENDERTARGET,
410 WINED3D_GL_EXT_NONE},
412 {WINED3DFMT_L8_UNORM, GL_LUMINANCE8, GL_SLUMINANCE8_EXT, 0,
413 GL_LUMINANCE, GL_UNSIGNED_BYTE,
414 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
415 WINED3D_GL_EXT_NONE},
416 {WINED3DFMT_L8A8_UNORM, GL_LUMINANCE8_ALPHA8, GL_SLUMINANCE8_ALPHA8_EXT, 0,
417 GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
418 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
419 WINED3D_GL_EXT_NONE},
420 {WINED3DFMT_L4A4_UNORM, GL_LUMINANCE4_ALPHA4, GL_LUMINANCE4_ALPHA4, 0,
421 GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
423 WINED3D_GL_EXT_NONE},
424 /* Bump mapping stuff */
425 {WINED3DFMT_R8G8_SNORM, GL_RGB8, GL_RGB8, 0,
426 GL_BGR, GL_UNSIGNED_BYTE,
427 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
428 WINED3D_GL_EXT_NONE},
429 {WINED3DFMT_R8G8_SNORM, GL_DSDT8_NV, GL_DSDT8_NV, 0,
431 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
433 {WINED3DFMT_R5G5_SNORM_L6_UNORM, GL_RGB5, GL_RGB5, 0,
434 GL_RGB, GL_UNSIGNED_SHORT_5_6_5,
435 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
436 WINED3D_GL_EXT_NONE},
437 {WINED3DFMT_R5G5_SNORM_L6_UNORM, GL_DSDT8_MAG8_NV, GL_DSDT8_MAG8_NV, 0,
438 GL_DSDT_MAG_NV, GL_BYTE,
439 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
441 {WINED3DFMT_R8G8_SNORM_L8X8_UNORM, GL_RGB8, GL_RGB8, 0,
442 GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV,
443 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
444 WINED3D_GL_EXT_NONE},
445 {WINED3DFMT_R8G8_SNORM_L8X8_UNORM, GL_DSDT8_MAG8_INTENSITY8_NV, GL_DSDT8_MAG8_INTENSITY8_NV, 0,
446 GL_DSDT_MAG_VIB_NV, GL_UNSIGNED_INT_8_8_S8_S8_REV_NV,
447 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
449 {WINED3DFMT_R8G8B8A8_SNORM, GL_RGBA8, GL_RGBA8, 0,
450 GL_BGRA, GL_UNSIGNED_BYTE,
451 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
452 WINED3D_GL_EXT_NONE},
453 {WINED3DFMT_R8G8B8A8_SNORM, GL_SIGNED_RGBA8_NV, GL_SIGNED_RGBA8_NV, 0,
455 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
457 {WINED3DFMT_R16G16_SNORM, GL_RGB16, GL_RGB16, 0,
458 GL_BGR, GL_UNSIGNED_SHORT,
459 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
460 WINED3D_GL_EXT_NONE},
461 {WINED3DFMT_R16G16_SNORM, GL_SIGNED_HILO16_NV, GL_SIGNED_HILO16_NV, 0,
462 GL_HILO_NV, GL_SHORT,
463 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
465 /* Depth stencil formats */
466 {WINED3DFMT_D16_LOCKABLE, GL_DEPTH_COMPONENT24_ARB, GL_DEPTH_COMPONENT24_ARB, 0,
467 GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT,
468 WINED3DFMT_FLAG_DEPTH,
470 {WINED3DFMT_D32_UNORM, GL_DEPTH_COMPONENT32_ARB, GL_DEPTH_COMPONENT32_ARB, 0,
471 GL_DEPTH_COMPONENT, GL_UNSIGNED_INT,
472 WINED3DFMT_FLAG_DEPTH,
474 {WINED3DFMT_S1_UINT_D15_UNORM, GL_DEPTH_COMPONENT24_ARB, GL_DEPTH_COMPONENT24_ARB, 0,
475 GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT,
476 WINED3DFMT_FLAG_DEPTH,
478 {WINED3DFMT_S1_UINT_D15_UNORM, GL_DEPTH24_STENCIL8_EXT, GL_DEPTH24_STENCIL8_EXT, 0,
479 GL_DEPTH_STENCIL_EXT, GL_UNSIGNED_INT_24_8_EXT,
480 WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
481 EXT_PACKED_DEPTH_STENCIL},
482 {WINED3DFMT_S1_UINT_D15_UNORM, GL_DEPTH24_STENCIL8, GL_DEPTH24_STENCIL8, 0,
483 GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8,
484 WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
485 ARB_FRAMEBUFFER_OBJECT},
486 {WINED3DFMT_D24_UNORM_S8_UINT, GL_DEPTH_COMPONENT24_ARB, GL_DEPTH_COMPONENT24_ARB, 0,
487 GL_DEPTH_COMPONENT, GL_UNSIGNED_INT,
488 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH,
490 {WINED3DFMT_D24_UNORM_S8_UINT, GL_DEPTH24_STENCIL8_EXT, GL_DEPTH24_STENCIL8_EXT, 0,
491 GL_DEPTH_STENCIL_EXT, GL_UNSIGNED_INT_24_8_EXT,
492 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
493 EXT_PACKED_DEPTH_STENCIL},
494 {WINED3DFMT_D24_UNORM_S8_UINT, GL_DEPTH24_STENCIL8, GL_DEPTH24_STENCIL8, 0,
495 GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8,
496 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
497 ARB_FRAMEBUFFER_OBJECT},
498 {WINED3DFMT_X8D24_UNORM, GL_DEPTH_COMPONENT24_ARB, GL_DEPTH_COMPONENT24_ARB, 0,
499 GL_DEPTH_COMPONENT, GL_UNSIGNED_INT,
500 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH,
502 {WINED3DFMT_S4X4_UINT_D24_UNORM, GL_DEPTH_COMPONENT24_ARB, GL_DEPTH_COMPONENT24_ARB, 0,
503 GL_DEPTH_COMPONENT, GL_UNSIGNED_INT,
504 WINED3DFMT_FLAG_DEPTH,
506 {WINED3DFMT_S4X4_UINT_D24_UNORM, GL_DEPTH24_STENCIL8_EXT, GL_DEPTH24_STENCIL8_EXT, 0,
507 GL_DEPTH_STENCIL_EXT, GL_UNSIGNED_INT_24_8_EXT,
508 WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
509 EXT_PACKED_DEPTH_STENCIL},
510 {WINED3DFMT_S4X4_UINT_D24_UNORM, GL_DEPTH24_STENCIL8, GL_DEPTH24_STENCIL8, 0,
511 GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8,
512 WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
513 ARB_FRAMEBUFFER_OBJECT},
514 {WINED3DFMT_D16_UNORM, GL_DEPTH_COMPONENT24_ARB, GL_DEPTH_COMPONENT24_ARB, 0,
515 GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT,
516 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING | WINED3DFMT_FLAG_DEPTH,
518 {WINED3DFMT_L16_UNORM, GL_LUMINANCE16, GL_LUMINANCE16, 0,
519 GL_LUMINANCE, GL_UNSIGNED_SHORT,
520 WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING | WINED3DFMT_FLAG_FILTERING,
521 WINED3D_GL_EXT_NONE},
522 {WINED3DFMT_D32_FLOAT, GL_DEPTH_COMPONENT32F, GL_DEPTH_COMPONENT32F, 0,
523 GL_DEPTH_COMPONENT, GL_FLOAT,
524 WINED3DFMT_FLAG_DEPTH,
525 ARB_DEPTH_BUFFER_FLOAT},
526 {WINED3DFMT_S8_UINT_D24_FLOAT, GL_DEPTH32F_STENCIL8, GL_DEPTH32F_STENCIL8, 0,
527 GL_DEPTH_STENCIL, GL_FLOAT_32_UNSIGNED_INT_24_8_REV,
528 WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL,
529 ARB_DEPTH_BUFFER_FLOAT},
530 /* Vendor-specific formats */
531 {WINED3DFMT_ATI2N, GL_COMPRESSED_LUMINANCE_ALPHA_3DC_ATI, GL_COMPRESSED_LUMINANCE_ALPHA_3DC_ATI, 0,
532 GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
534 ATI_TEXTURE_COMPRESSION_3DC},
535 {WINED3DFMT_ATI2N, GL_COMPRESSED_RED_GREEN_RGTC2_EXT, GL_COMPRESSED_RED_GREEN_RGTC2_EXT, 0,
536 GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE,
538 EXT_TEXTURE_COMPRESSION_RGTC},
541 static inline int getFmtIdx(WINED3DFORMAT fmt) {
542 /* First check if the format is at the position of its value.
543 * This will catch the argb formats before the loop is entered
545 if(fmt < (sizeof(formats) / sizeof(formats[0])) && formats[fmt].format == fmt) {
549 for(i = 0; i < (sizeof(formats) / sizeof(formats[0])); i++) {
550 if(formats[i].format == fmt) {
558 static BOOL init_format_base_info(struct wined3d_gl_info *gl_info)
560 UINT format_count = sizeof(formats) / sizeof(*formats);
563 gl_info->gl_formats = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, format_count * sizeof(*gl_info->gl_formats));
564 if (!gl_info->gl_formats)
566 ERR("Failed to allocate memory.\n");
570 for (i = 0; i < format_count; ++i)
572 struct wined3d_format_desc *desc = &gl_info->gl_formats[i];
573 desc->format = formats[i].format;
574 desc->red_mask = formats[i].redMask;
575 desc->green_mask = formats[i].greenMask;
576 desc->blue_mask = formats[i].blueMask;
577 desc->alpha_mask = formats[i].alphaMask;
578 desc->byte_count = formats[i].bpp;
579 desc->depth_size = formats[i].depthSize;
580 desc->stencil_size = formats[i].stencilSize;
583 for (i = 0; i < (sizeof(format_base_flags) / sizeof(*format_base_flags)); ++i)
585 int fmt_idx = getFmtIdx(format_base_flags[i].format);
589 ERR("Format %s (%#x) not found.\n",
590 debug_d3dformat(format_base_flags[i].format), format_base_flags[i].format);
591 HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
595 gl_info->gl_formats[fmt_idx].Flags |= format_base_flags[i].flags;
601 static BOOL init_format_compression_info(struct wined3d_gl_info *gl_info)
605 for (i = 0; i < (sizeof(format_compression_info) / sizeof(*format_compression_info)); ++i)
607 struct wined3d_format_desc *format_desc;
608 int fmt_idx = getFmtIdx(format_compression_info[i].format);
612 ERR("Format %s (%#x) not found.\n",
613 debug_d3dformat(format_compression_info[i].format), format_compression_info[i].format);
617 format_desc = &gl_info->gl_formats[fmt_idx];
618 format_desc->block_width = format_compression_info[i].block_width;
619 format_desc->block_height = format_compression_info[i].block_height;
620 format_desc->block_byte_count = format_compression_info[i].block_byte_count;
621 format_desc->Flags |= WINED3DFMT_FLAG_COMPRESSED;
627 /* Context activation is done by the caller. */
628 static void check_fbo_compat(const struct wined3d_gl_info *gl_info, struct wined3d_format_desc *format_desc)
630 /* Check if the default internal format is supported as a frame buffer
631 * target, otherwise fall back to the render target internal.
633 * Try to stick to the standard format if possible, this limits precision differences. */
642 glGenTextures(1, &tex);
643 glBindTexture(GL_TEXTURE_2D, tex);
645 glTexImage2D(GL_TEXTURE_2D, 0, format_desc->glInternal, 16, 16, 0,
646 format_desc->glFormat, format_desc->glType, NULL);
647 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
648 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
650 gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, 0);
652 status = gl_info->fbo_ops.glCheckFramebufferStatus(GL_FRAMEBUFFER);
653 checkGLcall("Framebuffer format check");
655 if (status == GL_FRAMEBUFFER_COMPLETE)
657 TRACE("Format %s is supported as FBO color attachment\n", debug_d3dformat(format_desc->format));
658 format_desc->Flags |= WINED3DFMT_FLAG_FBO_ATTACHABLE;
659 format_desc->rtInternal = format_desc->glInternal;
663 if (!format_desc->rtInternal)
665 if (format_desc->Flags & WINED3DFMT_FLAG_RENDERTARGET)
667 FIXME("Format %s with rendertarget flag is not supported as FBO color attachment,"
668 " and no fallback specified.\n", debug_d3dformat(format_desc->format));
669 format_desc->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
673 TRACE("Format %s is not supported as FBO color attachment.\n", debug_d3dformat(format_desc->format));
675 format_desc->rtInternal = format_desc->glInternal;
679 TRACE("Format %s is not supported as FBO color attachment, trying rtInternal format as fallback.\n",
680 debug_d3dformat(format_desc->format));
684 gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0);
686 glTexImage2D(GL_TEXTURE_2D, 0, format_desc->rtInternal, 16, 16, 0,
687 format_desc->glFormat, format_desc->glType, NULL);
688 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
689 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
691 gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, 0);
693 status = gl_info->fbo_ops.glCheckFramebufferStatus(GL_FRAMEBUFFER);
694 checkGLcall("Framebuffer format check");
696 if (status == GL_FRAMEBUFFER_COMPLETE)
698 TRACE("Format %s rtInternal format is supported as FBO color attachment\n",
699 debug_d3dformat(format_desc->format));
703 FIXME("Format %s rtInternal format is not supported as FBO color attachment.\n",
704 debug_d3dformat(format_desc->format));
705 format_desc->Flags &= ~WINED3DFMT_FLAG_RENDERTARGET;
710 if (status == GL_FRAMEBUFFER_COMPLETE && format_desc->Flags & WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING)
714 if (gl_info->supported[ARB_FRAMEBUFFER_OBJECT]
715 || gl_info->supported[EXT_PACKED_DEPTH_STENCIL])
717 gl_info->fbo_ops.glGenRenderbuffers(1, &rb);
718 gl_info->fbo_ops.glBindRenderbuffer(GL_RENDERBUFFER, rb);
719 gl_info->fbo_ops.glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8, 16, 16);
720 gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, rb);
721 gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, rb);
722 checkGLcall("RB attachment");
726 glClear(GL_COLOR_BUFFER_BIT);
727 if (glGetError() == GL_INVALID_FRAMEBUFFER_OPERATION)
730 TRACE("Format doesn't support post-pixelshader blending.\n");
731 format_desc->Flags &= ~WINED3DFMT_FLAG_POSTPIXELSHADER_BLENDING;
734 if (gl_info->supported[ARB_FRAMEBUFFER_OBJECT]
735 || gl_info->supported[EXT_PACKED_DEPTH_STENCIL])
737 gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, 0);
738 gl_info->fbo_ops.glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, 0);
739 gl_info->fbo_ops.glDeleteRenderbuffers(1, &rb);
740 checkGLcall("RB cleanup");
744 glDeleteTextures(1, &tex);
749 /* Context activation is done by the caller. */
750 static void init_format_fbo_compat_info(struct wined3d_gl_info *gl_info)
755 if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
759 gl_info->fbo_ops.glGenFramebuffers(1, &fbo);
760 gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, fbo);
765 for (i = 0; i < sizeof(formats) / sizeof(*formats); ++i)
767 struct wined3d_format_desc *desc = &gl_info->gl_formats[i];
769 if (!desc->glInternal) continue;
771 if (desc->Flags & (WINED3DFMT_FLAG_DEPTH | WINED3DFMT_FLAG_STENCIL))
773 TRACE("Skipping format %s because it's a depth/stencil format.\n",
774 debug_d3dformat(desc->format));
778 if (desc->Flags & WINED3DFMT_FLAG_COMPRESSED)
780 TRACE("Skipping format %s because it's a compressed format.\n",
781 debug_d3dformat(desc->format));
785 if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
787 TRACE("Checking if format %s is supported as FBO color attachment...\n", debug_d3dformat(desc->format));
788 check_fbo_compat(gl_info, desc);
792 desc->rtInternal = desc->glInternal;
796 if (wined3d_settings.offscreen_rendering_mode == ORM_FBO)
800 gl_info->fbo_ops.glDeleteFramebuffers(1, &fbo);
806 static BOOL init_format_texture_info(struct wined3d_gl_info *gl_info)
810 for (i = 0; i < sizeof(format_texture_info) / sizeof(*format_texture_info); ++i)
812 int fmt_idx = getFmtIdx(format_texture_info[i].format);
813 struct wined3d_format_desc *desc;
817 ERR("Format %s (%#x) not found.\n",
818 debug_d3dformat(format_texture_info[i].format), format_texture_info[i].format);
822 if (!gl_info->supported[format_texture_info[i].extension]) continue;
824 desc = &gl_info->gl_formats[fmt_idx];
825 desc->glInternal = format_texture_info[i].gl_internal;
826 desc->glGammaInternal = format_texture_info[i].gl_srgb_internal;
827 desc->rtInternal = format_texture_info[i].gl_rt_internal;
828 desc->glFormat = format_texture_info[i].gl_format;
829 desc->glType = format_texture_info[i].gl_type;
830 desc->color_fixup = COLOR_FIXUP_IDENTITY;
831 desc->Flags |= format_texture_info[i].flags;
832 desc->heightscale = 1.0f;
838 static BOOL color_match(DWORD c1, DWORD c2, BYTE max_diff)
840 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
842 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
844 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
846 if (abs((c1 & 0xff) - (c2 & 0xff)) > max_diff) return FALSE;
850 /* A context is provided by the caller */
851 static BOOL check_filter(const struct wined3d_gl_info *gl_info, GLenum internal)
853 GLuint tex, fbo, buffer;
854 const DWORD data[] = {0x00000000, 0xffffffff};
855 DWORD readback[16 * 1];
858 /* Render a filtered texture and see what happens. This is intended to detect the lack of
859 * float16 filtering on ATI X1000 class cards. The drivers disable filtering instead of
860 * falling back to software. If this changes in the future this code will get fooled and
861 * apps might hit the software path due to incorrectly advertised caps.
863 * Its unlikely that this changes however. GL Games like Mass Effect depend on the filter
864 * disable fallback, if Apple or ATI ever change the driver behavior they will break more
865 * than Wine. The Linux binary <= r500 driver is not maintained any more anyway
871 glGenTextures(1, &buffer);
872 glBindTexture(GL_TEXTURE_2D, buffer);
873 memset(readback, 0x7e, sizeof(readback));
874 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 16, 1, 0, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, readback);
875 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
876 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
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);
881 glGenTextures(1, &tex);
882 glBindTexture(GL_TEXTURE_2D, tex);
883 glTexImage2D(GL_TEXTURE_2D, 0, internal, 2, 1, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, data);
884 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
885 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
886 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
887 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
888 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
889 glEnable(GL_TEXTURE_2D);
891 gl_info->fbo_ops.glGenFramebuffers(1, &fbo);
892 gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, fbo);
893 gl_info->fbo_ops.glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, buffer, 0);
894 glDrawBuffer(GL_COLOR_ATTACHMENT0);
896 glViewport(0, 0, 16, 1);
897 glDisable(GL_LIGHTING);
898 glMatrixMode(GL_MODELVIEW);
900 glMatrixMode(GL_PROJECTION);
903 glClearColor(0, 1, 0, 0);
904 glClear(GL_COLOR_BUFFER_BIT);
906 glBegin(GL_TRIANGLE_STRIP);
907 glTexCoord2f(0.0, 0.0);
908 glVertex2f(-1.0f, -1.0f);
909 glTexCoord2f(1.0, 0.0);
910 glVertex2f(1.0f, -1.0f);
911 glTexCoord2f(0.0, 1.0);
912 glVertex2f(-1.0f, 1.0f);
913 glTexCoord2f(1.0, 1.0);
914 glVertex2f(1.0f, 1.0f);
917 glBindTexture(GL_TEXTURE_2D, buffer);
918 memset(readback, 0x7f, sizeof(readback));
919 glGetTexImage(GL_TEXTURE_2D, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, readback);
920 if(color_match(readback[6], 0xffffffff, 5) || color_match(readback[6], 0x00000000, 5) ||
921 color_match(readback[9], 0xffffffff, 5) || color_match(readback[9], 0x00000000, 5))
923 TRACE("Read back colors 0x%08x and 0x%08x close to unfiltered color, asuming no filtering\n",
924 readback[6], readback[9]);
929 TRACE("Read back colors are 0x%08x and 0x%08x, assuming texture is filtered\n",
930 readback[6], readback[9]);
934 gl_info->fbo_ops.glBindFramebuffer(GL_FRAMEBUFFER, 0);
935 gl_info->fbo_ops.glDeleteFramebuffers(1, &fbo);
936 glDeleteTextures(1, &tex);
937 glDeleteTextures(1, &buffer);
941 FIXME("Error during filtering test for format %x, returning no filtering\n", internal);
948 static void init_format_filter_info(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor)
950 struct wined3d_format_desc *desc;
951 unsigned int fmt_idx, i;
952 WINED3DFORMAT fmts16[] = {
953 WINED3DFMT_R16_FLOAT,
954 WINED3DFMT_R16G16_FLOAT,
955 WINED3DFMT_R16G16B16A16_FLOAT,
959 if(wined3d_settings.offscreen_rendering_mode != ORM_FBO)
961 WARN("No FBO support, or no FBO ORM, guessing filter info from GL caps\n");
962 if (vendor == HW_VENDOR_NVIDIA && gl_info->supported[ARB_TEXTURE_FLOAT])
964 TRACE("Nvidia card with texture_float support: Assuming float16 blending\n");
967 else if (gl_info->limits.glsl_varyings > 44)
969 TRACE("More than 44 GLSL varyings - assuming d3d10 card with float16 blending\n");
974 TRACE("Assuming no float16 blending\n");
980 for(i = 0; i < (sizeof(fmts16) / sizeof(*fmts16)); i++)
982 fmt_idx = getFmtIdx(fmts16[i]);
983 gl_info->gl_formats[fmt_idx].Flags |= WINED3DFMT_FLAG_FILTERING;
989 for(i = 0; i < (sizeof(fmts16) / sizeof(*fmts16)); i++)
991 fmt_idx = getFmtIdx(fmts16[i]);
992 desc = &gl_info->gl_formats[fmt_idx];
993 if(!desc->glInternal) continue; /* Not supported by GL */
995 filtered = check_filter(gl_info, gl_info->gl_formats[fmt_idx].glInternal);
998 TRACE("Format %s supports filtering\n", debug_d3dformat(fmts16[i]));
999 desc->Flags |= WINED3DFMT_FLAG_FILTERING;
1003 TRACE("Format %s does not support filtering\n", debug_d3dformat(fmts16[i]));
1008 static void apply_format_fixups(struct wined3d_gl_info *gl_info)
1012 idx = getFmtIdx(WINED3DFMT_R16_FLOAT);
1013 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1014 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1016 idx = getFmtIdx(WINED3DFMT_R32_FLOAT);
1017 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1018 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1020 idx = getFmtIdx(WINED3DFMT_R16G16_UNORM);
1021 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1022 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1024 idx = getFmtIdx(WINED3DFMT_R16G16_FLOAT);
1025 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1026 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1028 idx = getFmtIdx(WINED3DFMT_R32G32_FLOAT);
1029 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1030 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_W);
1032 /* V8U8 is supported natively by GL_ATI_envmap_bumpmap and GL_NV_texture_shader.
1033 * V16U16 is only supported by GL_NV_texture_shader. The formats need fixup if
1034 * their extensions are not available. GL_ATI_envmap_bumpmap is not used because
1035 * the only driver that implements it(fglrx) has a buggy implementation.
1037 * V8U8 and V16U16 need a fixup of the undefined blue channel. OpenGL
1038 * returns 0.0 when sampling from it, DirectX 1.0. So we always have in-shader
1039 * conversion for this format.
1041 if (!gl_info->supported[NV_TEXTURE_SHADER])
1043 idx = getFmtIdx(WINED3DFMT_R8G8_SNORM);
1044 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1045 1, CHANNEL_SOURCE_X, 1, 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 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1052 idx = getFmtIdx(WINED3DFMT_R8G8_SNORM);
1053 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1054 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1055 idx = getFmtIdx(WINED3DFMT_R16G16_SNORM);
1056 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1057 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1060 if (!gl_info->supported[NV_TEXTURE_SHADER])
1062 /* If GL_NV_texture_shader is not supported, those formats are converted, incompatibly
1065 idx = getFmtIdx(WINED3DFMT_R5G5_SNORM_L6_UNORM);
1066 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1067 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Z, 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_ONE);
1068 idx = getFmtIdx(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
1069 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1070 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_Z, 0, CHANNEL_SOURCE_W);
1071 idx = getFmtIdx(WINED3DFMT_R8G8B8A8_SNORM);
1072 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1073 1, CHANNEL_SOURCE_X, 1, CHANNEL_SOURCE_Y, 1, CHANNEL_SOURCE_Z, 1, CHANNEL_SOURCE_W);
1077 /* If GL_NV_texture_shader is supported, WINED3DFMT_L6V5U5 and WINED3DFMT_X8L8V8U8
1078 * are converted at surface loading time, but they do not need any modification in
1079 * the shader, thus they are compatible with all WINED3DFMT_UNKNOWN group formats.
1080 * WINED3DFMT_Q8W8V8U8 doesn't even need load-time conversion
1084 if (gl_info->supported[EXT_TEXTURE_COMPRESSION_RGTC])
1086 idx = getFmtIdx(WINED3DFMT_ATI2N);
1087 gl_info->gl_formats[idx].color_fixup = create_color_fixup_desc(
1088 0, CHANNEL_SOURCE_Y, 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1090 else if (gl_info->supported[ATI_TEXTURE_COMPRESSION_3DC])
1092 idx = getFmtIdx(WINED3DFMT_ATI2N);
1093 gl_info->gl_formats[idx].color_fixup= create_color_fixup_desc(
1094 0, CHANNEL_SOURCE_X, 0, CHANNEL_SOURCE_W, 0, CHANNEL_SOURCE_ONE, 0, CHANNEL_SOURCE_ONE);
1097 if (!gl_info->supported[APPLE_YCBCR_422])
1099 idx = getFmtIdx(WINED3DFMT_YUY2);
1100 gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_YUY2);
1102 idx = getFmtIdx(WINED3DFMT_UYVY);
1103 gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_UYVY);
1106 idx = getFmtIdx(WINED3DFMT_YV12);
1107 gl_info->gl_formats[idx].heightscale = 1.5f;
1108 gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_YV12);
1110 if (gl_info->supported[EXT_PALETTED_TEXTURE] || gl_info->supported[ARB_FRAGMENT_PROGRAM])
1112 idx = getFmtIdx(WINED3DFMT_P8_UINT);
1113 gl_info->gl_formats[idx].color_fixup = create_complex_fixup_desc(COMPLEX_FIXUP_P8);
1116 if (gl_info->supported[ARB_VERTEX_ARRAY_BGRA])
1118 idx = getFmtIdx(WINED3DFMT_B8G8R8A8_UNORM);
1119 gl_info->gl_formats[idx].gl_vtx_format = GL_BGRA;
1122 if (gl_info->supported[ARB_HALF_FLOAT_VERTEX])
1124 /* Do not change the size of the type, it is CPU side. We have to change the GPU-side information though.
1125 * It is the job of the vertex buffer code to make sure that the vbos have the right format */
1126 idx = getFmtIdx(WINED3DFMT_R16G16_FLOAT);
1127 gl_info->gl_formats[idx].gl_vtx_type = GL_HALF_FLOAT; /* == GL_HALF_FLOAT_NV */
1129 idx = getFmtIdx(WINED3DFMT_R16G16B16A16_FLOAT);
1130 gl_info->gl_formats[idx].gl_vtx_type = GL_HALF_FLOAT;
1134 static BOOL init_format_vertex_info(struct wined3d_gl_info *gl_info)
1138 for (i = 0; i < (sizeof(format_vertex_info) / sizeof(*format_vertex_info)); ++i)
1140 struct wined3d_format_desc *format_desc;
1141 int fmt_idx = getFmtIdx(format_vertex_info[i].format);
1145 ERR("Format %s (%#x) not found.\n",
1146 debug_d3dformat(format_vertex_info[i].format), format_vertex_info[i].format);
1150 format_desc = &gl_info->gl_formats[fmt_idx];
1151 format_desc->emit_idx = format_vertex_info[i].emit_idx;
1152 format_desc->component_count = format_vertex_info[i].component_count;
1153 format_desc->gl_vtx_type = format_vertex_info[i].gl_vtx_type;
1154 format_desc->gl_vtx_format = format_vertex_info[i].gl_vtx_format;
1155 format_desc->gl_normalized = format_vertex_info[i].gl_normalized;
1156 format_desc->component_size = format_vertex_info[i].component_size;
1162 BOOL initPixelFormatsNoGL(struct wined3d_gl_info *gl_info)
1164 if (!init_format_base_info(gl_info)) return FALSE;
1166 if (!init_format_compression_info(gl_info))
1168 HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
1169 gl_info->gl_formats = NULL;
1176 /* Context activation is done by the caller. */
1177 BOOL initPixelFormats(struct wined3d_gl_info *gl_info, enum wined3d_pci_vendor vendor)
1179 if (!init_format_base_info(gl_info)) return FALSE;
1181 if (!init_format_compression_info(gl_info)) goto fail;
1182 if (!init_format_texture_info(gl_info)) goto fail;
1183 if (!init_format_vertex_info(gl_info)) goto fail;
1185 apply_format_fixups(gl_info);
1186 init_format_fbo_compat_info(gl_info);
1187 init_format_filter_info(gl_info, vendor);
1192 HeapFree(GetProcessHeap(), 0, gl_info->gl_formats);
1193 gl_info->gl_formats = NULL;
1197 const struct wined3d_format_desc *getFormatDescEntry(WINED3DFORMAT fmt, const struct wined3d_gl_info *gl_info)
1199 int idx = getFmtIdx(fmt);
1202 FIXME("Can't find format %s(%d) in the format lookup table\n", debug_d3dformat(fmt), fmt);
1203 /* Get the caller a valid pointer */
1204 idx = getFmtIdx(WINED3DFMT_UNKNOWN);
1207 return &gl_info->gl_formats[idx];
1210 /*****************************************************************************
1211 * Trace formatting of useful values
1213 const char* debug_d3dformat(WINED3DFORMAT fmt) {
1215 #define FMT_TO_STR(fmt) case fmt: return #fmt
1216 FMT_TO_STR(WINED3DFMT_UNKNOWN);
1217 FMT_TO_STR(WINED3DFMT_B8G8R8_UNORM);
1218 FMT_TO_STR(WINED3DFMT_B5G5R5X1_UNORM);
1219 FMT_TO_STR(WINED3DFMT_B4G4R4A4_UNORM);
1220 FMT_TO_STR(WINED3DFMT_B2G3R3_UNORM);
1221 FMT_TO_STR(WINED3DFMT_B2G3R3A8_UNORM);
1222 FMT_TO_STR(WINED3DFMT_B4G4R4X4_UNORM);
1223 FMT_TO_STR(WINED3DFMT_R8G8B8X8_UNORM);
1224 FMT_TO_STR(WINED3DFMT_B10G10R10A2_UNORM);
1225 FMT_TO_STR(WINED3DFMT_P8_UINT_A8_UNORM);
1226 FMT_TO_STR(WINED3DFMT_P8_UINT);
1227 FMT_TO_STR(WINED3DFMT_L8_UNORM);
1228 FMT_TO_STR(WINED3DFMT_L8A8_UNORM);
1229 FMT_TO_STR(WINED3DFMT_L4A4_UNORM);
1230 FMT_TO_STR(WINED3DFMT_R5G5_SNORM_L6_UNORM);
1231 FMT_TO_STR(WINED3DFMT_R8G8_SNORM_L8X8_UNORM);
1232 FMT_TO_STR(WINED3DFMT_R10G11B11_SNORM);
1233 FMT_TO_STR(WINED3DFMT_R10G10B10_SNORM_A2_UNORM);
1234 FMT_TO_STR(WINED3DFMT_UYVY);
1235 FMT_TO_STR(WINED3DFMT_YUY2);
1236 FMT_TO_STR(WINED3DFMT_YV12);
1237 FMT_TO_STR(WINED3DFMT_DXT1);
1238 FMT_TO_STR(WINED3DFMT_DXT2);
1239 FMT_TO_STR(WINED3DFMT_DXT3);
1240 FMT_TO_STR(WINED3DFMT_DXT4);
1241 FMT_TO_STR(WINED3DFMT_DXT5);
1242 FMT_TO_STR(WINED3DFMT_MULTI2_ARGB8);
1243 FMT_TO_STR(WINED3DFMT_G8R8_G8B8);
1244 FMT_TO_STR(WINED3DFMT_R8G8_B8G8);
1245 FMT_TO_STR(WINED3DFMT_D16_LOCKABLE);
1246 FMT_TO_STR(WINED3DFMT_D32_UNORM);
1247 FMT_TO_STR(WINED3DFMT_S1_UINT_D15_UNORM);
1248 FMT_TO_STR(WINED3DFMT_X8D24_UNORM);
1249 FMT_TO_STR(WINED3DFMT_S4X4_UINT_D24_UNORM);
1250 FMT_TO_STR(WINED3DFMT_L16_UNORM);
1251 FMT_TO_STR(WINED3DFMT_S8_UINT_D24_FLOAT);
1252 FMT_TO_STR(WINED3DFMT_VERTEXDATA);
1253 FMT_TO_STR(WINED3DFMT_R8G8_SNORM_Cx);
1254 FMT_TO_STR(WINED3DFMT_ATI2N);
1255 FMT_TO_STR(WINED3DFMT_NVHU);
1256 FMT_TO_STR(WINED3DFMT_NVHS);
1257 FMT_TO_STR(WINED3DFMT_R32G32B32A32_TYPELESS);
1258 FMT_TO_STR(WINED3DFMT_R32G32B32A32_FLOAT);
1259 FMT_TO_STR(WINED3DFMT_R32G32B32A32_UINT);
1260 FMT_TO_STR(WINED3DFMT_R32G32B32A32_SINT);
1261 FMT_TO_STR(WINED3DFMT_R32G32B32_TYPELESS);
1262 FMT_TO_STR(WINED3DFMT_R32G32B32_FLOAT);
1263 FMT_TO_STR(WINED3DFMT_R32G32B32_UINT);
1264 FMT_TO_STR(WINED3DFMT_R32G32B32_SINT);
1265 FMT_TO_STR(WINED3DFMT_R16G16B16A16_TYPELESS);
1266 FMT_TO_STR(WINED3DFMT_R16G16B16A16_FLOAT);
1267 FMT_TO_STR(WINED3DFMT_R16G16B16A16_UNORM);
1268 FMT_TO_STR(WINED3DFMT_R16G16B16A16_UINT);
1269 FMT_TO_STR(WINED3DFMT_R16G16B16A16_SNORM);
1270 FMT_TO_STR(WINED3DFMT_R16G16B16A16_SINT);
1271 FMT_TO_STR(WINED3DFMT_R32G32_TYPELESS);
1272 FMT_TO_STR(WINED3DFMT_R32G32_FLOAT);
1273 FMT_TO_STR(WINED3DFMT_R32G32_UINT);
1274 FMT_TO_STR(WINED3DFMT_R32G32_SINT);
1275 FMT_TO_STR(WINED3DFMT_R32G8X24_TYPELESS);
1276 FMT_TO_STR(WINED3DFMT_D32_FLOAT_S8X24_UINT);
1277 FMT_TO_STR(WINED3DFMT_R32_FLOAT_X8X24_TYPELESS);
1278 FMT_TO_STR(WINED3DFMT_X32_TYPELESS_G8X24_UINT);
1279 FMT_TO_STR(WINED3DFMT_R10G10B10A2_TYPELESS);
1280 FMT_TO_STR(WINED3DFMT_R10G10B10A2_UNORM);
1281 FMT_TO_STR(WINED3DFMT_R10G10B10A2_UINT);
1282 FMT_TO_STR(WINED3DFMT_R10G10B10A2_SNORM);
1283 FMT_TO_STR(WINED3DFMT_R11G11B10_FLOAT);
1284 FMT_TO_STR(WINED3DFMT_R8G8B8A8_TYPELESS);
1285 FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM);
1286 FMT_TO_STR(WINED3DFMT_R8G8B8A8_UNORM_SRGB);
1287 FMT_TO_STR(WINED3DFMT_R8G8B8A8_UINT);
1288 FMT_TO_STR(WINED3DFMT_R8G8B8A8_SNORM);
1289 FMT_TO_STR(WINED3DFMT_R8G8B8A8_SINT);
1290 FMT_TO_STR(WINED3DFMT_R16G16_TYPELESS);
1291 FMT_TO_STR(WINED3DFMT_R16G16_FLOAT);
1292 FMT_TO_STR(WINED3DFMT_R16G16_UNORM);
1293 FMT_TO_STR(WINED3DFMT_R16G16_UINT);
1294 FMT_TO_STR(WINED3DFMT_R16G16_SNORM);
1295 FMT_TO_STR(WINED3DFMT_R16G16_SINT);
1296 FMT_TO_STR(WINED3DFMT_R32_TYPELESS);
1297 FMT_TO_STR(WINED3DFMT_D32_FLOAT);
1298 FMT_TO_STR(WINED3DFMT_R32_FLOAT);
1299 FMT_TO_STR(WINED3DFMT_R32_UINT);
1300 FMT_TO_STR(WINED3DFMT_R32_SINT);
1301 FMT_TO_STR(WINED3DFMT_R24G8_TYPELESS);
1302 FMT_TO_STR(WINED3DFMT_D24_UNORM_S8_UINT);
1303 FMT_TO_STR(WINED3DFMT_R24_UNORM_X8_TYPELESS);
1304 FMT_TO_STR(WINED3DFMT_X24_TYPELESS_G8_UINT);
1305 FMT_TO_STR(WINED3DFMT_R8G8_TYPELESS);
1306 FMT_TO_STR(WINED3DFMT_R8G8_UNORM);
1307 FMT_TO_STR(WINED3DFMT_R8G8_UINT);
1308 FMT_TO_STR(WINED3DFMT_R8G8_SNORM);
1309 FMT_TO_STR(WINED3DFMT_R8G8_SINT);
1310 FMT_TO_STR(WINED3DFMT_R16_TYPELESS);
1311 FMT_TO_STR(WINED3DFMT_R16_FLOAT);
1312 FMT_TO_STR(WINED3DFMT_D16_UNORM);
1313 FMT_TO_STR(WINED3DFMT_R16_UNORM);
1314 FMT_TO_STR(WINED3DFMT_R16_UINT);
1315 FMT_TO_STR(WINED3DFMT_R16_SNORM);
1316 FMT_TO_STR(WINED3DFMT_R16_SINT);
1317 FMT_TO_STR(WINED3DFMT_R8_TYPELESS);
1318 FMT_TO_STR(WINED3DFMT_R8_UNORM);
1319 FMT_TO_STR(WINED3DFMT_R8_UINT);
1320 FMT_TO_STR(WINED3DFMT_R8_SNORM);
1321 FMT_TO_STR(WINED3DFMT_R8_SINT);
1322 FMT_TO_STR(WINED3DFMT_A8_UNORM);
1323 FMT_TO_STR(WINED3DFMT_R1_UNORM);
1324 FMT_TO_STR(WINED3DFMT_R9G9B9E5_SHAREDEXP);
1325 FMT_TO_STR(WINED3DFMT_R8G8_B8G8_UNORM);
1326 FMT_TO_STR(WINED3DFMT_G8R8_G8B8_UNORM);
1327 FMT_TO_STR(WINED3DFMT_BC1_TYPELESS);
1328 FMT_TO_STR(WINED3DFMT_BC1_UNORM);
1329 FMT_TO_STR(WINED3DFMT_BC1_UNORM_SRGB);
1330 FMT_TO_STR(WINED3DFMT_BC2_TYPELESS);
1331 FMT_TO_STR(WINED3DFMT_BC2_UNORM);
1332 FMT_TO_STR(WINED3DFMT_BC2_UNORM_SRGB);
1333 FMT_TO_STR(WINED3DFMT_BC3_TYPELESS);
1334 FMT_TO_STR(WINED3DFMT_BC3_UNORM);
1335 FMT_TO_STR(WINED3DFMT_BC3_UNORM_SRGB);
1336 FMT_TO_STR(WINED3DFMT_BC4_TYPELESS);
1337 FMT_TO_STR(WINED3DFMT_BC4_UNORM);
1338 FMT_TO_STR(WINED3DFMT_BC4_SNORM);
1339 FMT_TO_STR(WINED3DFMT_BC5_TYPELESS);
1340 FMT_TO_STR(WINED3DFMT_BC5_UNORM);
1341 FMT_TO_STR(WINED3DFMT_BC5_SNORM);
1342 FMT_TO_STR(WINED3DFMT_B5G6R5_UNORM);
1343 FMT_TO_STR(WINED3DFMT_B5G5R5A1_UNORM);
1344 FMT_TO_STR(WINED3DFMT_B8G8R8A8_UNORM);
1345 FMT_TO_STR(WINED3DFMT_B8G8R8X8_UNORM);
1350 fourcc[0] = (char)(fmt);
1351 fourcc[1] = (char)(fmt >> 8);
1352 fourcc[2] = (char)(fmt >> 16);
1353 fourcc[3] = (char)(fmt >> 24);
1355 if( isprint(fourcc[0]) && isprint(fourcc[1]) && isprint(fourcc[2]) && isprint(fourcc[3]) )
1356 FIXME("Unrecognized %u (as fourcc: %s) WINED3DFORMAT!\n", fmt, fourcc);
1358 FIXME("Unrecognized %u WINED3DFORMAT!\n", fmt);
1360 return "unrecognized";
1364 const char* debug_d3ddevicetype(WINED3DDEVTYPE devtype) {
1366 #define DEVTYPE_TO_STR(dev) case dev: return #dev
1367 DEVTYPE_TO_STR(WINED3DDEVTYPE_HAL);
1368 DEVTYPE_TO_STR(WINED3DDEVTYPE_REF);
1369 DEVTYPE_TO_STR(WINED3DDEVTYPE_SW);
1370 #undef DEVTYPE_TO_STR
1372 FIXME("Unrecognized %u WINED3DDEVTYPE!\n", devtype);
1373 return "unrecognized";
1377 const char *debug_d3dusage(DWORD usage)
1382 #define WINED3DUSAGE_TO_STR(u) if (usage & u) { strcat(buf, " | "#u); usage &= ~u; }
1383 WINED3DUSAGE_TO_STR(WINED3DUSAGE_RENDERTARGET);
1384 WINED3DUSAGE_TO_STR(WINED3DUSAGE_DEPTHSTENCIL);
1385 WINED3DUSAGE_TO_STR(WINED3DUSAGE_WRITEONLY);
1386 WINED3DUSAGE_TO_STR(WINED3DUSAGE_SOFTWAREPROCESSING);
1387 WINED3DUSAGE_TO_STR(WINED3DUSAGE_DONOTCLIP);
1388 WINED3DUSAGE_TO_STR(WINED3DUSAGE_POINTS);
1389 WINED3DUSAGE_TO_STR(WINED3DUSAGE_RTPATCHES);
1390 WINED3DUSAGE_TO_STR(WINED3DUSAGE_NPATCHES);
1391 WINED3DUSAGE_TO_STR(WINED3DUSAGE_DYNAMIC);
1392 WINED3DUSAGE_TO_STR(WINED3DUSAGE_AUTOGENMIPMAP);
1393 WINED3DUSAGE_TO_STR(WINED3DUSAGE_DMAP);
1394 #undef WINED3DUSAGE_TO_STR
1395 if (usage) FIXME("Unrecognized usage flag(s) %#x\n", usage);
1397 return buf[0] ? wine_dbg_sprintf("%s", &buf[3]) : "0";
1400 const char *debug_d3dusagequery(DWORD usagequery)
1405 #define WINED3DUSAGEQUERY_TO_STR(u) if (usagequery & u) { strcat(buf, " | "#u); usagequery &= ~u; }
1406 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_FILTER);
1407 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_LEGACYBUMPMAP);
1408 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_POSTPIXELSHADER_BLENDING);
1409 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_SRGBREAD);
1410 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_SRGBWRITE);
1411 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_VERTEXTEXTURE);
1412 WINED3DUSAGEQUERY_TO_STR(WINED3DUSAGE_QUERY_WRAPANDMIP);
1413 #undef WINED3DUSAGEQUERY_TO_STR
1414 if (usagequery) FIXME("Unrecognized usage query flag(s) %#x\n", usagequery);
1416 return buf[0] ? wine_dbg_sprintf("%s", &buf[3]) : "0";
1419 const char* debug_d3ddeclmethod(WINED3DDECLMETHOD method) {
1421 #define WINED3DDECLMETHOD_TO_STR(u) case u: return #u
1422 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_DEFAULT);
1423 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_PARTIALU);
1424 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_PARTIALV);
1425 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_CROSSUV);
1426 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_UV);
1427 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_LOOKUP);
1428 WINED3DDECLMETHOD_TO_STR(WINED3DDECLMETHOD_LOOKUPPRESAMPLED);
1429 #undef WINED3DDECLMETHOD_TO_STR
1431 FIXME("Unrecognized %u declaration method!\n", method);
1432 return "unrecognized";
1436 const char* debug_d3ddeclusage(BYTE usage) {
1438 #define WINED3DDECLUSAGE_TO_STR(u) case u: return #u
1439 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_POSITION);
1440 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_BLENDWEIGHT);
1441 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_BLENDINDICES);
1442 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_NORMAL);
1443 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_PSIZE);
1444 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_TEXCOORD);
1445 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_TANGENT);
1446 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_BINORMAL);
1447 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_TESSFACTOR);
1448 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_POSITIONT);
1449 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_COLOR);
1450 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_FOG);
1451 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_DEPTH);
1452 WINED3DDECLUSAGE_TO_STR(WINED3DDECLUSAGE_SAMPLE);
1453 #undef WINED3DDECLUSAGE_TO_STR
1455 FIXME("Unrecognized %u declaration usage!\n", usage);
1456 return "unrecognized";
1460 const char* debug_d3dresourcetype(WINED3DRESOURCETYPE res) {
1462 #define RES_TO_STR(res) case res: return #res
1463 RES_TO_STR(WINED3DRTYPE_SURFACE);
1464 RES_TO_STR(WINED3DRTYPE_VOLUME);
1465 RES_TO_STR(WINED3DRTYPE_TEXTURE);
1466 RES_TO_STR(WINED3DRTYPE_VOLUMETEXTURE);
1467 RES_TO_STR(WINED3DRTYPE_CUBETEXTURE);
1468 RES_TO_STR(WINED3DRTYPE_BUFFER);
1471 FIXME("Unrecognized %u WINED3DRESOURCETYPE!\n", res);
1472 return "unrecognized";
1476 const char* debug_d3dprimitivetype(WINED3DPRIMITIVETYPE PrimitiveType) {
1477 switch (PrimitiveType) {
1478 #define PRIM_TO_STR(prim) case prim: return #prim
1479 PRIM_TO_STR(WINED3DPT_UNDEFINED);
1480 PRIM_TO_STR(WINED3DPT_POINTLIST);
1481 PRIM_TO_STR(WINED3DPT_LINELIST);
1482 PRIM_TO_STR(WINED3DPT_LINESTRIP);
1483 PRIM_TO_STR(WINED3DPT_TRIANGLELIST);
1484 PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP);
1485 PRIM_TO_STR(WINED3DPT_TRIANGLEFAN);
1486 PRIM_TO_STR(WINED3DPT_LINELIST_ADJ);
1487 PRIM_TO_STR(WINED3DPT_LINESTRIP_ADJ);
1488 PRIM_TO_STR(WINED3DPT_TRIANGLELIST_ADJ);
1489 PRIM_TO_STR(WINED3DPT_TRIANGLESTRIP_ADJ);
1492 FIXME("Unrecognized %u WINED3DPRIMITIVETYPE!\n", PrimitiveType);
1493 return "unrecognized";
1497 const char* debug_d3drenderstate(DWORD state) {
1499 #define D3DSTATE_TO_STR(u) case u: return #u
1500 D3DSTATE_TO_STR(WINED3DRS_ANTIALIAS );
1501 D3DSTATE_TO_STR(WINED3DRS_TEXTUREPERSPECTIVE );
1502 D3DSTATE_TO_STR(WINED3DRS_WRAPU );
1503 D3DSTATE_TO_STR(WINED3DRS_WRAPV );
1504 D3DSTATE_TO_STR(WINED3DRS_ZENABLE );
1505 D3DSTATE_TO_STR(WINED3DRS_FILLMODE );
1506 D3DSTATE_TO_STR(WINED3DRS_SHADEMODE );
1507 D3DSTATE_TO_STR(WINED3DRS_LINEPATTERN );
1508 D3DSTATE_TO_STR(WINED3DRS_MONOENABLE );
1509 D3DSTATE_TO_STR(WINED3DRS_ROP2 );
1510 D3DSTATE_TO_STR(WINED3DRS_PLANEMASK );
1511 D3DSTATE_TO_STR(WINED3DRS_ZWRITEENABLE );
1512 D3DSTATE_TO_STR(WINED3DRS_ALPHATESTENABLE );
1513 D3DSTATE_TO_STR(WINED3DRS_LASTPIXEL );
1514 D3DSTATE_TO_STR(WINED3DRS_SRCBLEND );
1515 D3DSTATE_TO_STR(WINED3DRS_DESTBLEND );
1516 D3DSTATE_TO_STR(WINED3DRS_CULLMODE );
1517 D3DSTATE_TO_STR(WINED3DRS_ZFUNC );
1518 D3DSTATE_TO_STR(WINED3DRS_ALPHAREF );
1519 D3DSTATE_TO_STR(WINED3DRS_ALPHAFUNC );
1520 D3DSTATE_TO_STR(WINED3DRS_DITHERENABLE );
1521 D3DSTATE_TO_STR(WINED3DRS_ALPHABLENDENABLE );
1522 D3DSTATE_TO_STR(WINED3DRS_FOGENABLE );
1523 D3DSTATE_TO_STR(WINED3DRS_SPECULARENABLE );
1524 D3DSTATE_TO_STR(WINED3DRS_ZVISIBLE );
1525 D3DSTATE_TO_STR(WINED3DRS_SUBPIXEL );
1526 D3DSTATE_TO_STR(WINED3DRS_SUBPIXELX );
1527 D3DSTATE_TO_STR(WINED3DRS_STIPPLEDALPHA );
1528 D3DSTATE_TO_STR(WINED3DRS_FOGCOLOR );
1529 D3DSTATE_TO_STR(WINED3DRS_FOGTABLEMODE );
1530 D3DSTATE_TO_STR(WINED3DRS_FOGSTART );
1531 D3DSTATE_TO_STR(WINED3DRS_FOGEND );
1532 D3DSTATE_TO_STR(WINED3DRS_FOGDENSITY );
1533 D3DSTATE_TO_STR(WINED3DRS_STIPPLEENABLE );
1534 D3DSTATE_TO_STR(WINED3DRS_EDGEANTIALIAS );
1535 D3DSTATE_TO_STR(WINED3DRS_COLORKEYENABLE );
1536 D3DSTATE_TO_STR(WINED3DRS_MIPMAPLODBIAS );
1537 D3DSTATE_TO_STR(WINED3DRS_ZBIAS );
1538 D3DSTATE_TO_STR(WINED3DRS_RANGEFOGENABLE );
1539 D3DSTATE_TO_STR(WINED3DRS_ANISOTROPY );
1540 D3DSTATE_TO_STR(WINED3DRS_FLUSHBATCH );
1541 D3DSTATE_TO_STR(WINED3DRS_TRANSLUCENTSORTINDEPENDENT);
1542 D3DSTATE_TO_STR(WINED3DRS_STENCILENABLE );
1543 D3DSTATE_TO_STR(WINED3DRS_STENCILFAIL );
1544 D3DSTATE_TO_STR(WINED3DRS_STENCILZFAIL );
1545 D3DSTATE_TO_STR(WINED3DRS_STENCILPASS );
1546 D3DSTATE_TO_STR(WINED3DRS_STENCILFUNC );
1547 D3DSTATE_TO_STR(WINED3DRS_STENCILREF );
1548 D3DSTATE_TO_STR(WINED3DRS_STENCILMASK );
1549 D3DSTATE_TO_STR(WINED3DRS_STENCILWRITEMASK );
1550 D3DSTATE_TO_STR(WINED3DRS_TEXTUREFACTOR );
1551 D3DSTATE_TO_STR(WINED3DRS_WRAP0 );
1552 D3DSTATE_TO_STR(WINED3DRS_WRAP1 );
1553 D3DSTATE_TO_STR(WINED3DRS_WRAP2 );
1554 D3DSTATE_TO_STR(WINED3DRS_WRAP3 );
1555 D3DSTATE_TO_STR(WINED3DRS_WRAP4 );
1556 D3DSTATE_TO_STR(WINED3DRS_WRAP5 );
1557 D3DSTATE_TO_STR(WINED3DRS_WRAP6 );
1558 D3DSTATE_TO_STR(WINED3DRS_WRAP7 );
1559 D3DSTATE_TO_STR(WINED3DRS_CLIPPING );
1560 D3DSTATE_TO_STR(WINED3DRS_LIGHTING );
1561 D3DSTATE_TO_STR(WINED3DRS_EXTENTS );
1562 D3DSTATE_TO_STR(WINED3DRS_AMBIENT );
1563 D3DSTATE_TO_STR(WINED3DRS_FOGVERTEXMODE );
1564 D3DSTATE_TO_STR(WINED3DRS_COLORVERTEX );
1565 D3DSTATE_TO_STR(WINED3DRS_LOCALVIEWER );
1566 D3DSTATE_TO_STR(WINED3DRS_NORMALIZENORMALS );
1567 D3DSTATE_TO_STR(WINED3DRS_COLORKEYBLENDENABLE );
1568 D3DSTATE_TO_STR(WINED3DRS_DIFFUSEMATERIALSOURCE );
1569 D3DSTATE_TO_STR(WINED3DRS_SPECULARMATERIALSOURCE );
1570 D3DSTATE_TO_STR(WINED3DRS_AMBIENTMATERIALSOURCE );
1571 D3DSTATE_TO_STR(WINED3DRS_EMISSIVEMATERIALSOURCE );
1572 D3DSTATE_TO_STR(WINED3DRS_VERTEXBLEND );
1573 D3DSTATE_TO_STR(WINED3DRS_CLIPPLANEENABLE );
1574 D3DSTATE_TO_STR(WINED3DRS_SOFTWAREVERTEXPROCESSING );
1575 D3DSTATE_TO_STR(WINED3DRS_POINTSIZE );
1576 D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MIN );
1577 D3DSTATE_TO_STR(WINED3DRS_POINTSPRITEENABLE );
1578 D3DSTATE_TO_STR(WINED3DRS_POINTSCALEENABLE );
1579 D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_A );
1580 D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_B );
1581 D3DSTATE_TO_STR(WINED3DRS_POINTSCALE_C );
1582 D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEANTIALIAS );
1583 D3DSTATE_TO_STR(WINED3DRS_MULTISAMPLEMASK );
1584 D3DSTATE_TO_STR(WINED3DRS_PATCHEDGESTYLE );
1585 D3DSTATE_TO_STR(WINED3DRS_PATCHSEGMENTS );
1586 D3DSTATE_TO_STR(WINED3DRS_DEBUGMONITORTOKEN );
1587 D3DSTATE_TO_STR(WINED3DRS_POINTSIZE_MAX );
1588 D3DSTATE_TO_STR(WINED3DRS_INDEXEDVERTEXBLENDENABLE );
1589 D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE );
1590 D3DSTATE_TO_STR(WINED3DRS_TWEENFACTOR );
1591 D3DSTATE_TO_STR(WINED3DRS_BLENDOP );
1592 D3DSTATE_TO_STR(WINED3DRS_POSITIONDEGREE );
1593 D3DSTATE_TO_STR(WINED3DRS_NORMALDEGREE );
1594 D3DSTATE_TO_STR(WINED3DRS_SCISSORTESTENABLE );
1595 D3DSTATE_TO_STR(WINED3DRS_SLOPESCALEDEPTHBIAS );
1596 D3DSTATE_TO_STR(WINED3DRS_ANTIALIASEDLINEENABLE );
1597 D3DSTATE_TO_STR(WINED3DRS_MINTESSELLATIONLEVEL );
1598 D3DSTATE_TO_STR(WINED3DRS_MAXTESSELLATIONLEVEL );
1599 D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_X );
1600 D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Y );
1601 D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_Z );
1602 D3DSTATE_TO_STR(WINED3DRS_ADAPTIVETESS_W );
1603 D3DSTATE_TO_STR(WINED3DRS_ENABLEADAPTIVETESSELLATION);
1604 D3DSTATE_TO_STR(WINED3DRS_TWOSIDEDSTENCILMODE );
1605 D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFAIL );
1606 D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILZFAIL );
1607 D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILPASS );
1608 D3DSTATE_TO_STR(WINED3DRS_CCW_STENCILFUNC );
1609 D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE1 );
1610 D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE2 );
1611 D3DSTATE_TO_STR(WINED3DRS_COLORWRITEENABLE3 );
1612 D3DSTATE_TO_STR(WINED3DRS_BLENDFACTOR );
1613 D3DSTATE_TO_STR(WINED3DRS_SRGBWRITEENABLE );
1614 D3DSTATE_TO_STR(WINED3DRS_DEPTHBIAS );
1615 D3DSTATE_TO_STR(WINED3DRS_WRAP8 );
1616 D3DSTATE_TO_STR(WINED3DRS_WRAP9 );
1617 D3DSTATE_TO_STR(WINED3DRS_WRAP10 );
1618 D3DSTATE_TO_STR(WINED3DRS_WRAP11 );
1619 D3DSTATE_TO_STR(WINED3DRS_WRAP12 );
1620 D3DSTATE_TO_STR(WINED3DRS_WRAP13 );
1621 D3DSTATE_TO_STR(WINED3DRS_WRAP14 );
1622 D3DSTATE_TO_STR(WINED3DRS_WRAP15 );
1623 D3DSTATE_TO_STR(WINED3DRS_SEPARATEALPHABLENDENABLE );
1624 D3DSTATE_TO_STR(WINED3DRS_SRCBLENDALPHA );
1625 D3DSTATE_TO_STR(WINED3DRS_DESTBLENDALPHA );
1626 D3DSTATE_TO_STR(WINED3DRS_BLENDOPALPHA );
1627 #undef D3DSTATE_TO_STR
1629 FIXME("Unrecognized %u render state!\n", state);
1630 return "unrecognized";
1634 const char* debug_d3dsamplerstate(DWORD state) {
1636 #define D3DSTATE_TO_STR(u) case u: return #u
1637 D3DSTATE_TO_STR(WINED3DSAMP_BORDERCOLOR );
1638 D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSU );
1639 D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSV );
1640 D3DSTATE_TO_STR(WINED3DSAMP_ADDRESSW );
1641 D3DSTATE_TO_STR(WINED3DSAMP_MAGFILTER );
1642 D3DSTATE_TO_STR(WINED3DSAMP_MINFILTER );
1643 D3DSTATE_TO_STR(WINED3DSAMP_MIPFILTER );
1644 D3DSTATE_TO_STR(WINED3DSAMP_MIPMAPLODBIAS);
1645 D3DSTATE_TO_STR(WINED3DSAMP_MAXMIPLEVEL );
1646 D3DSTATE_TO_STR(WINED3DSAMP_MAXANISOTROPY);
1647 D3DSTATE_TO_STR(WINED3DSAMP_SRGBTEXTURE );
1648 D3DSTATE_TO_STR(WINED3DSAMP_ELEMENTINDEX );
1649 D3DSTATE_TO_STR(WINED3DSAMP_DMAPOFFSET );
1650 #undef D3DSTATE_TO_STR
1652 FIXME("Unrecognized %u sampler state!\n", state);
1653 return "unrecognized";
1657 const char *debug_d3dtexturefiltertype(WINED3DTEXTUREFILTERTYPE filter_type) {
1658 switch (filter_type) {
1659 #define D3DTEXTUREFILTERTYPE_TO_STR(u) case u: return #u
1660 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_NONE);
1661 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_POINT);
1662 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_LINEAR);
1663 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_ANISOTROPIC);
1664 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_FLATCUBIC);
1665 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_GAUSSIANCUBIC);
1666 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_PYRAMIDALQUAD);
1667 D3DTEXTUREFILTERTYPE_TO_STR(WINED3DTEXF_GAUSSIANQUAD);
1668 #undef D3DTEXTUREFILTERTYPE_TO_STR
1670 FIXME("Unrecognied texture filter type 0x%08x\n", filter_type);
1671 return "unrecognized";
1675 const char* debug_d3dtexturestate(DWORD state) {
1677 #define D3DSTATE_TO_STR(u) case u: return #u
1678 D3DSTATE_TO_STR(WINED3DTSS_COLOROP );
1679 D3DSTATE_TO_STR(WINED3DTSS_COLORARG1 );
1680 D3DSTATE_TO_STR(WINED3DTSS_COLORARG2 );
1681 D3DSTATE_TO_STR(WINED3DTSS_ALPHAOP );
1682 D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG1 );
1683 D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG2 );
1684 D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT00 );
1685 D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT01 );
1686 D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT10 );
1687 D3DSTATE_TO_STR(WINED3DTSS_BUMPENVMAT11 );
1688 D3DSTATE_TO_STR(WINED3DTSS_TEXCOORDINDEX );
1689 D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLSCALE );
1690 D3DSTATE_TO_STR(WINED3DTSS_BUMPENVLOFFSET );
1691 D3DSTATE_TO_STR(WINED3DTSS_TEXTURETRANSFORMFLAGS );
1692 D3DSTATE_TO_STR(WINED3DTSS_COLORARG0 );
1693 D3DSTATE_TO_STR(WINED3DTSS_ALPHAARG0 );
1694 D3DSTATE_TO_STR(WINED3DTSS_RESULTARG );
1695 D3DSTATE_TO_STR(WINED3DTSS_CONSTANT );
1696 #undef D3DSTATE_TO_STR
1698 FIXME("Unrecognized %u texture state!\n", state);
1699 return "unrecognized";
1703 const char* debug_d3dtop(WINED3DTEXTUREOP d3dtop) {
1705 #define D3DTOP_TO_STR(u) case u: return #u
1706 D3DTOP_TO_STR(WINED3DTOP_DISABLE);
1707 D3DTOP_TO_STR(WINED3DTOP_SELECTARG1);
1708 D3DTOP_TO_STR(WINED3DTOP_SELECTARG2);
1709 D3DTOP_TO_STR(WINED3DTOP_MODULATE);
1710 D3DTOP_TO_STR(WINED3DTOP_MODULATE2X);
1711 D3DTOP_TO_STR(WINED3DTOP_MODULATE4X);
1712 D3DTOP_TO_STR(WINED3DTOP_ADD);
1713 D3DTOP_TO_STR(WINED3DTOP_ADDSIGNED);
1714 D3DTOP_TO_STR(WINED3DTOP_ADDSIGNED2X);
1715 D3DTOP_TO_STR(WINED3DTOP_SUBTRACT);
1716 D3DTOP_TO_STR(WINED3DTOP_ADDSMOOTH);
1717 D3DTOP_TO_STR(WINED3DTOP_BLENDDIFFUSEALPHA);
1718 D3DTOP_TO_STR(WINED3DTOP_BLENDTEXTUREALPHA);
1719 D3DTOP_TO_STR(WINED3DTOP_BLENDFACTORALPHA);
1720 D3DTOP_TO_STR(WINED3DTOP_BLENDTEXTUREALPHAPM);
1721 D3DTOP_TO_STR(WINED3DTOP_BLENDCURRENTALPHA);
1722 D3DTOP_TO_STR(WINED3DTOP_PREMODULATE);
1723 D3DTOP_TO_STR(WINED3DTOP_MODULATEALPHA_ADDCOLOR);
1724 D3DTOP_TO_STR(WINED3DTOP_MODULATECOLOR_ADDALPHA);
1725 D3DTOP_TO_STR(WINED3DTOP_MODULATEINVALPHA_ADDCOLOR);
1726 D3DTOP_TO_STR(WINED3DTOP_MODULATEINVCOLOR_ADDALPHA);
1727 D3DTOP_TO_STR(WINED3DTOP_BUMPENVMAP);
1728 D3DTOP_TO_STR(WINED3DTOP_BUMPENVMAPLUMINANCE);
1729 D3DTOP_TO_STR(WINED3DTOP_DOTPRODUCT3);
1730 D3DTOP_TO_STR(WINED3DTOP_MULTIPLYADD);
1731 D3DTOP_TO_STR(WINED3DTOP_LERP);
1732 #undef D3DTOP_TO_STR
1734 FIXME("Unrecognized %u WINED3DTOP\n", d3dtop);
1735 return "unrecognized";
1739 const char* debug_d3dtstype(WINED3DTRANSFORMSTATETYPE tstype) {
1741 #define TSTYPE_TO_STR(tstype) case tstype: return #tstype
1742 TSTYPE_TO_STR(WINED3DTS_VIEW);
1743 TSTYPE_TO_STR(WINED3DTS_PROJECTION);
1744 TSTYPE_TO_STR(WINED3DTS_TEXTURE0);
1745 TSTYPE_TO_STR(WINED3DTS_TEXTURE1);
1746 TSTYPE_TO_STR(WINED3DTS_TEXTURE2);
1747 TSTYPE_TO_STR(WINED3DTS_TEXTURE3);
1748 TSTYPE_TO_STR(WINED3DTS_TEXTURE4);
1749 TSTYPE_TO_STR(WINED3DTS_TEXTURE5);
1750 TSTYPE_TO_STR(WINED3DTS_TEXTURE6);
1751 TSTYPE_TO_STR(WINED3DTS_TEXTURE7);
1752 TSTYPE_TO_STR(WINED3DTS_WORLDMATRIX(0));
1753 #undef TSTYPE_TO_STR
1755 if (tstype > 256 && tstype < 512) {
1756 FIXME("WINED3DTS_WORLDMATRIX(%u). 1..255 not currently supported\n", tstype);
1757 return ("WINED3DTS_WORLDMATRIX > 0");
1759 FIXME("Unrecognized %u WINED3DTS\n", tstype);
1760 return "unrecognized";
1764 const char *debug_d3dstate(DWORD state)
1766 if (STATE_IS_RENDER(state))
1767 return wine_dbg_sprintf("STATE_RENDER(%s)", debug_d3drenderstate(state - STATE_RENDER(0)));
1768 if (STATE_IS_TEXTURESTAGE(state))
1770 DWORD texture_stage = (state - STATE_TEXTURESTAGE(0, 0)) / (WINED3D_HIGHEST_TEXTURE_STATE + 1);
1771 DWORD texture_state = state - STATE_TEXTURESTAGE(texture_stage, 0);
1772 return wine_dbg_sprintf("STATE_TEXTURESTAGE(%#x, %s)",
1773 texture_stage, debug_d3dtexturestate(texture_state));
1775 if (STATE_IS_SAMPLER(state))
1776 return wine_dbg_sprintf("STATE_SAMPLER(%#x)", state - STATE_SAMPLER(0));
1777 if (STATE_IS_PIXELSHADER(state))
1778 return "STATE_PIXELSHADER";
1779 if (STATE_IS_TRANSFORM(state))
1780 return wine_dbg_sprintf("STATE_TRANSFORM(%s)", debug_d3dtstype(state - STATE_TRANSFORM(0)));
1781 if (STATE_IS_STREAMSRC(state))
1782 return "STATE_STREAMSRC";
1783 if (STATE_IS_INDEXBUFFER(state))
1784 return "STATE_INDEXBUFFER";
1785 if (STATE_IS_VDECL(state))
1786 return "STATE_VDECL";
1787 if (STATE_IS_VSHADER(state))
1788 return "STATE_VSHADER";
1789 if (STATE_IS_VIEWPORT(state))
1790 return "STATE_VIEWPORT";
1791 if (STATE_IS_VERTEXSHADERCONSTANT(state))
1792 return "STATE_VERTEXSHADERCONSTANT";
1793 if (STATE_IS_PIXELSHADERCONSTANT(state))
1794 return "STATE_PIXELSHADERCONSTANT";
1795 if (STATE_IS_ACTIVELIGHT(state))
1796 return wine_dbg_sprintf("STATE_ACTIVELIGHT(%#x)", state - STATE_ACTIVELIGHT(0));
1797 if (STATE_IS_SCISSORRECT(state))
1798 return "STATE_SCISSORRECT";
1799 if (STATE_IS_CLIPPLANE(state))
1800 return wine_dbg_sprintf("STATE_CLIPPLANE(%#x)", state - STATE_CLIPPLANE(0));
1801 if (STATE_IS_MATERIAL(state))
1802 return "STATE_MATERIAL";
1803 if (STATE_IS_FRONTFACE(state))
1804 return "STATE_FRONTFACE";
1806 return wine_dbg_sprintf("UNKNOWN_STATE(%#x)", state);
1809 const char* debug_d3dpool(WINED3DPOOL Pool) {
1811 #define POOL_TO_STR(p) case p: return #p
1812 POOL_TO_STR(WINED3DPOOL_DEFAULT);
1813 POOL_TO_STR(WINED3DPOOL_MANAGED);
1814 POOL_TO_STR(WINED3DPOOL_SYSTEMMEM);
1815 POOL_TO_STR(WINED3DPOOL_SCRATCH);
1818 FIXME("Unrecognized %u WINED3DPOOL!\n", Pool);
1819 return "unrecognized";
1823 const char *debug_fbostatus(GLenum status) {
1825 #define FBOSTATUS_TO_STR(u) case u: return #u
1826 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_COMPLETE);
1827 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT);
1828 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT);
1829 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT);
1830 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_FORMATS_EXT);
1831 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER);
1832 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER);
1833 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE);
1834 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_UNSUPPORTED);
1835 FBOSTATUS_TO_STR(GL_FRAMEBUFFER_UNDEFINED);
1836 #undef FBOSTATUS_TO_STR
1838 FIXME("Unrecognied FBO status 0x%08x\n", status);
1839 return "unrecognized";
1843 const char *debug_glerror(GLenum error) {
1845 #define GLERROR_TO_STR(u) case u: return #u
1846 GLERROR_TO_STR(GL_NO_ERROR);
1847 GLERROR_TO_STR(GL_INVALID_ENUM);
1848 GLERROR_TO_STR(GL_INVALID_VALUE);
1849 GLERROR_TO_STR(GL_INVALID_OPERATION);
1850 GLERROR_TO_STR(GL_STACK_OVERFLOW);
1851 GLERROR_TO_STR(GL_STACK_UNDERFLOW);
1852 GLERROR_TO_STR(GL_OUT_OF_MEMORY);
1853 GLERROR_TO_STR(GL_INVALID_FRAMEBUFFER_OPERATION);
1854 #undef GLERROR_TO_STR
1856 FIXME("Unrecognied GL error 0x%08x\n", error);
1857 return "unrecognized";
1861 const char *debug_d3dbasis(WINED3DBASISTYPE basis) {
1863 case WINED3DBASIS_BEZIER: return "WINED3DBASIS_BEZIER";
1864 case WINED3DBASIS_BSPLINE: return "WINED3DBASIS_BSPLINE";
1865 case WINED3DBASIS_INTERPOLATE: return "WINED3DBASIS_INTERPOLATE";
1866 default: return "unrecognized";
1870 const char *debug_d3ddegree(WINED3DDEGREETYPE degree) {
1872 case WINED3DDEGREE_LINEAR: return "WINED3DDEGREE_LINEAR";
1873 case WINED3DDEGREE_QUADRATIC: return "WINED3DDEGREE_QUADRATIC";
1874 case WINED3DDEGREE_CUBIC: return "WINED3DDEGREE_CUBIC";
1875 case WINED3DDEGREE_QUINTIC: return "WINED3DDEGREE_QUINTIC";
1876 default: return "unrecognized";
1880 static const char *debug_fixup_channel_source(enum fixup_channel_source source)
1884 #define WINED3D_TO_STR(x) case x: return #x
1885 WINED3D_TO_STR(CHANNEL_SOURCE_ZERO);
1886 WINED3D_TO_STR(CHANNEL_SOURCE_ONE);
1887 WINED3D_TO_STR(CHANNEL_SOURCE_X);
1888 WINED3D_TO_STR(CHANNEL_SOURCE_Y);
1889 WINED3D_TO_STR(CHANNEL_SOURCE_Z);
1890 WINED3D_TO_STR(CHANNEL_SOURCE_W);
1891 WINED3D_TO_STR(CHANNEL_SOURCE_COMPLEX0);
1892 WINED3D_TO_STR(CHANNEL_SOURCE_COMPLEX1);
1893 #undef WINED3D_TO_STR
1895 FIXME("Unrecognized fixup_channel_source %#x\n", source);
1896 return "unrecognized";
1900 static const char *debug_complex_fixup(enum complex_fixup fixup)
1904 #define WINED3D_TO_STR(x) case x: return #x
1905 WINED3D_TO_STR(COMPLEX_FIXUP_YUY2);
1906 WINED3D_TO_STR(COMPLEX_FIXUP_UYVY);
1907 WINED3D_TO_STR(COMPLEX_FIXUP_YV12);
1908 WINED3D_TO_STR(COMPLEX_FIXUP_P8);
1909 #undef WINED3D_TO_STR
1911 FIXME("Unrecognized complex fixup %#x\n", fixup);
1912 return "unrecognized";
1916 void dump_color_fixup_desc(struct color_fixup_desc fixup)
1918 if (is_complex_fixup(fixup))
1920 TRACE("\tComplex: %s\n", debug_complex_fixup(get_complex_fixup(fixup)));
1924 TRACE("\tX: %s%s\n", debug_fixup_channel_source(fixup.x_source), fixup.x_sign_fixup ? ", SIGN_FIXUP" : "");
1925 TRACE("\tY: %s%s\n", debug_fixup_channel_source(fixup.y_source), fixup.y_sign_fixup ? ", SIGN_FIXUP" : "");
1926 TRACE("\tZ: %s%s\n", debug_fixup_channel_source(fixup.z_source), fixup.z_sign_fixup ? ", SIGN_FIXUP" : "");
1927 TRACE("\tW: %s%s\n", debug_fixup_channel_source(fixup.w_source), fixup.w_sign_fixup ? ", SIGN_FIXUP" : "");
1930 const char *debug_surflocation(DWORD flag) {
1934 if(flag & SFLAG_INSYSMEM) strcat(buf, " | SFLAG_INSYSMEM");
1935 if(flag & SFLAG_INDRAWABLE) strcat(buf, " | SFLAG_INDRAWABLE");
1936 if(flag & SFLAG_INTEXTURE) strcat(buf, " | SFLAG_INTEXTURE");
1937 if(flag & SFLAG_INSRGBTEX) strcat(buf, " | SFLAG_INSRGBTEX");
1938 return wine_dbg_sprintf("%s", buf[0] ? buf + 3 : "0");
1941 /*****************************************************************************
1942 * Useful functions mapping GL <-> D3D values
1944 GLenum StencilOp(DWORD op) {
1946 case WINED3DSTENCILOP_KEEP : return GL_KEEP;
1947 case WINED3DSTENCILOP_ZERO : return GL_ZERO;
1948 case WINED3DSTENCILOP_REPLACE : return GL_REPLACE;
1949 case WINED3DSTENCILOP_INCRSAT : return GL_INCR;
1950 case WINED3DSTENCILOP_DECRSAT : return GL_DECR;
1951 case WINED3DSTENCILOP_INVERT : return GL_INVERT;
1952 case WINED3DSTENCILOP_INCR : return GL_INCR_WRAP_EXT;
1953 case WINED3DSTENCILOP_DECR : return GL_DECR_WRAP_EXT;
1955 FIXME("Unrecognized stencil op %d\n", op);
1960 GLenum CompareFunc(DWORD func) {
1961 switch ((WINED3DCMPFUNC)func) {
1962 case WINED3DCMP_NEVER : return GL_NEVER;
1963 case WINED3DCMP_LESS : return GL_LESS;
1964 case WINED3DCMP_EQUAL : return GL_EQUAL;
1965 case WINED3DCMP_LESSEQUAL : return GL_LEQUAL;
1966 case WINED3DCMP_GREATER : return GL_GREATER;
1967 case WINED3DCMP_NOTEQUAL : return GL_NOTEQUAL;
1968 case WINED3DCMP_GREATEREQUAL : return GL_GEQUAL;
1969 case WINED3DCMP_ALWAYS : return GL_ALWAYS;
1971 FIXME("Unrecognized WINED3DCMPFUNC value %d\n", func);
1976 BOOL is_invalid_op(IWineD3DDeviceImpl *This, int stage, WINED3DTEXTUREOP op, DWORD arg1, DWORD arg2, DWORD arg3) {
1977 if (op == WINED3DTOP_DISABLE) return FALSE;
1978 if (This->stateBlock->textures[stage]) return FALSE;
1980 if ((arg1 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
1981 && op != WINED3DTOP_SELECTARG2) return TRUE;
1982 if ((arg2 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
1983 && op != WINED3DTOP_SELECTARG1) return TRUE;
1984 if ((arg3 & WINED3DTA_SELECTMASK) == WINED3DTA_TEXTURE
1985 && (op == WINED3DTOP_MULTIPLYADD || op == WINED3DTOP_LERP)) return TRUE;
1990 /* Setup this textures matrix according to the texture flags*/
1991 /* GL locking is done by the caller (state handler) */
1992 void set_texture_matrix(const float *smat, DWORD flags, BOOL calculatedCoords, BOOL transformed,
1993 WINED3DFORMAT vtx_fmt, BOOL ffp_proj_control)
1997 glMatrixMode(GL_TEXTURE);
1998 checkGLcall("glMatrixMode(GL_TEXTURE)");
2000 if (flags == WINED3DTTFF_DISABLE || flags == WINED3DTTFF_COUNT1 || transformed) {
2002 checkGLcall("glLoadIdentity()");
2006 if (flags == (WINED3DTTFF_COUNT1|WINED3DTTFF_PROJECTED)) {
2007 ERR("Invalid texture transform flags: WINED3DTTFF_COUNT1|WINED3DTTFF_PROJECTED\n");
2011 memcpy(mat, smat, 16 * sizeof(float));
2013 if (flags & WINED3DTTFF_PROJECTED) {
2014 if(!ffp_proj_control) {
2015 switch (flags & ~WINED3DTTFF_PROJECTED) {
2016 case WINED3DTTFF_COUNT2:
2017 mat[3] = mat[1], mat[7] = mat[5], mat[11] = mat[9], mat[15] = mat[13];
2018 mat[1] = mat[5] = mat[9] = mat[13] = 0;
2020 case WINED3DTTFF_COUNT3:
2021 mat[3] = mat[2], mat[7] = mat[6], mat[11] = mat[10], mat[15] = mat[14];
2022 mat[2] = mat[6] = mat[10] = mat[14] = 0;
2026 } else { /* under directx the R/Z coord can be used for translation, under opengl we use the Q coord instead */
2027 if(!calculatedCoords) {
2030 case WINED3DFMT_R32_FLOAT:
2031 /* Direct3D passes the default 1.0 in the 2nd coord, while gl passes it in the 4th.
2032 * swap 2nd and 4th coord. No need to store the value of mat[12] in mat[4] because
2033 * the input value to the transformation will be 0, so the matrix value is irrelevant
2040 case WINED3DFMT_R32G32_FLOAT:
2041 /* See above, just 3rd and 4th coord
2048 case WINED3DFMT_R32G32B32_FLOAT: /* Opengl defaults match dx defaults */
2049 case WINED3DFMT_R32G32B32A32_FLOAT: /* No defaults apply, all app defined */
2051 /* This is to prevent swapping the matrix lines and put the default 4th coord = 1.0
2052 * into a bad place. The division elimination below will apply to make sure the
2053 * 1.0 doesn't do anything bad. The caller will set this value if the stride is 0
2055 case WINED3DFMT_UNKNOWN: /* No texture coords, 0/0/0/1 defaults are passed */
2058 FIXME("Unexpected fixed function texture coord input\n");
2061 if(!ffp_proj_control) {
2062 switch (flags & ~WINED3DTTFF_PROJECTED) {
2063 /* case WINED3DTTFF_COUNT1: Won't ever get here */
2064 case WINED3DTTFF_COUNT2: mat[2] = mat[6] = mat[10] = mat[14] = 0;
2065 /* OpenGL divides the first 3 vertex coord by the 4th by default,
2066 * which is essentially the same as D3DTTFF_PROJECTED. Make sure that
2067 * the 4th coord evaluates to 1.0 to eliminate that.
2069 * If the fixed function pipeline is used, the 4th value remains unused,
2070 * so there is no danger in doing this. With vertex shaders we have a
2071 * problem. Should an app hit that problem, the code here would have to
2072 * check for pixel shaders, and the shader has to undo the default gl divide.
2074 * A more serious problem occurs if the app passes 4 coordinates in, and the
2075 * 4th is != 1.0(opengl default). This would have to be fixed in drawStridedSlow
2076 * or a replacement shader
2078 default: mat[3] = mat[7] = mat[11] = 0; mat[15] = 1;
2084 checkGLcall("glLoadMatrixf(mat)");
2087 /* This small helper function is used to convert a bitmask into the number of masked bits */
2088 unsigned int count_bits(unsigned int mask)
2091 for (count = 0; mask; ++count)
2098 /* Helper function for retrieving color info for ChoosePixelFormat and wglChoosePixelFormatARB.
2099 * The later function requires individual color components. */
2100 BOOL getColorBits(const struct wined3d_format_desc *format_desc,
2101 short *redSize, short *greenSize, short *blueSize, short *alphaSize, short *totalSize)
2103 TRACE("fmt: %s\n", debug_d3dformat(format_desc->format));
2104 switch(format_desc->format)
2106 case WINED3DFMT_B8G8R8X8_UNORM:
2107 case WINED3DFMT_B8G8R8_UNORM:
2108 case WINED3DFMT_B8G8R8A8_UNORM:
2109 case WINED3DFMT_R8G8B8A8_UNORM:
2110 case WINED3DFMT_B10G10R10A2_UNORM:
2111 case WINED3DFMT_B5G5R5X1_UNORM:
2112 case WINED3DFMT_B5G5R5A1_UNORM:
2113 case WINED3DFMT_B5G6R5_UNORM:
2114 case WINED3DFMT_B4G4R4X4_UNORM:
2115 case WINED3DFMT_B4G4R4A4_UNORM:
2116 case WINED3DFMT_B2G3R3_UNORM:
2117 case WINED3DFMT_P8_UINT_A8_UNORM:
2118 case WINED3DFMT_P8_UINT:
2121 ERR("Unsupported format: %s\n", debug_d3dformat(format_desc->format));
2125 *redSize = count_bits(format_desc->red_mask);
2126 *greenSize = count_bits(format_desc->green_mask);
2127 *blueSize = count_bits(format_desc->blue_mask);
2128 *alphaSize = count_bits(format_desc->alpha_mask);
2129 *totalSize = *redSize + *greenSize + *blueSize + *alphaSize;
2131 TRACE("Returning red: %d, green: %d, blue: %d, alpha: %d, total: %d for fmt=%s\n",
2132 *redSize, *greenSize, *blueSize, *alphaSize, *totalSize, debug_d3dformat(format_desc->format));
2136 /* Helper function for retrieving depth/stencil info for ChoosePixelFormat and wglChoosePixelFormatARB */
2137 BOOL getDepthStencilBits(const struct wined3d_format_desc *format_desc, short *depthSize, short *stencilSize)
2139 TRACE("fmt: %s\n", debug_d3dformat(format_desc->format));
2140 switch(format_desc->format)
2142 case WINED3DFMT_D16_LOCKABLE:
2143 case WINED3DFMT_D16_UNORM:
2144 case WINED3DFMT_S1_UINT_D15_UNORM:
2145 case WINED3DFMT_X8D24_UNORM:
2146 case WINED3DFMT_S4X4_UINT_D24_UNORM:
2147 case WINED3DFMT_D24_UNORM_S8_UINT:
2148 case WINED3DFMT_S8_UINT_D24_FLOAT:
2149 case WINED3DFMT_D32_UNORM:
2150 case WINED3DFMT_D32_FLOAT:
2153 FIXME("Unsupported stencil format: %s\n", debug_d3dformat(format_desc->format));
2157 *depthSize = format_desc->depth_size;
2158 *stencilSize = format_desc->stencil_size;
2160 TRACE("Returning depthSize: %d and stencilSize: %d for fmt=%s\n",
2161 *depthSize, *stencilSize, debug_d3dformat(format_desc->format));
2165 DWORD color_convert_argb_to_fmt(DWORD color, WINED3DFORMAT destfmt)
2167 unsigned int r, g, b, a;
2170 if (destfmt == WINED3DFMT_B8G8R8A8_UNORM
2171 || destfmt == WINED3DFMT_B8G8R8X8_UNORM
2172 || destfmt == WINED3DFMT_B8G8R8_UNORM)
2175 TRACE("Converting color %08x to format %s\n", color, debug_d3dformat(destfmt));
2177 a = (color & 0xff000000) >> 24;
2178 r = (color & 0x00ff0000) >> 16;
2179 g = (color & 0x0000ff00) >> 8;
2180 b = (color & 0x000000ff) >> 0;
2184 case WINED3DFMT_B5G6R5_UNORM:
2185 if(r == 0xff && g == 0xff && b == 0xff) return 0xffff;
2192 TRACE("Returning %08x\n", ret);
2195 case WINED3DFMT_B5G5R5X1_UNORM:
2196 case WINED3DFMT_B5G5R5A1_UNORM:
2205 TRACE("Returning %08x\n", ret);
2208 case WINED3DFMT_A8_UNORM:
2209 TRACE("Returning %08x\n", a);
2212 case WINED3DFMT_B4G4R4X4_UNORM:
2213 case WINED3DFMT_B4G4R4A4_UNORM:
2222 TRACE("Returning %08x\n", ret);
2225 case WINED3DFMT_B2G3R3_UNORM:
2232 TRACE("Returning %08x\n", ret);
2235 case WINED3DFMT_R8G8B8X8_UNORM:
2236 case WINED3DFMT_R8G8B8A8_UNORM:
2241 TRACE("Returning %08x\n", ret);
2244 case WINED3DFMT_B10G10R10A2_UNORM:
2246 r = (r * 1024) / 256;
2247 g = (g * 1024) / 256;
2248 b = (b * 1024) / 256;
2253 TRACE("Returning %08x\n", ret);
2256 case WINED3DFMT_R10G10B10A2_UNORM:
2258 r = (r * 1024) / 256;
2259 g = (g * 1024) / 256;
2260 b = (b * 1024) / 256;
2265 TRACE("Returning %08x\n", ret);
2269 FIXME("Add a COLORFILL conversion for format %s\n", debug_d3dformat(destfmt));
2274 /* DirectDraw stuff */
2275 WINED3DFORMAT pixelformat_for_depth(DWORD depth) {
2277 case 8: return WINED3DFMT_P8_UINT;
2278 case 15: return WINED3DFMT_B5G5R5X1_UNORM;
2279 case 16: return WINED3DFMT_B5G6R5_UNORM;
2280 case 24: return WINED3DFMT_B8G8R8X8_UNORM; /* Robots needs 24bit to be WINED3DFMT_B8G8R8X8_UNORM */
2281 case 32: return WINED3DFMT_B8G8R8X8_UNORM; /* EVE online and the Fur demo need 32bit AdapterDisplayMode to return WINED3DFMT_B8G8R8X8_UNORM */
2282 default: return WINED3DFMT_UNKNOWN;
2286 void multiply_matrix(WINED3DMATRIX *dest, const WINED3DMATRIX *src1, const WINED3DMATRIX *src2) {
2289 /* Now do the multiplication 'by hand'.
2290 I know that all this could be optimised, but this will be done later :-) */
2291 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);
2292 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);
2293 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);
2294 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);
2296 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);
2297 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);
2298 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);
2299 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);
2301 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);
2302 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);
2303 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);
2304 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);
2306 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);
2307 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);
2308 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);
2309 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);
2311 /* And copy the new matrix in the good storage.. */
2312 memcpy(dest, &temp, 16 * sizeof(float));
2315 DWORD get_flexible_vertex_size(DWORD d3dvtVertexType) {
2318 int numTextures = (d3dvtVertexType & WINED3DFVF_TEXCOUNT_MASK) >> WINED3DFVF_TEXCOUNT_SHIFT;
2320 if (d3dvtVertexType & WINED3DFVF_NORMAL) size += 3 * sizeof(float);
2321 if (d3dvtVertexType & WINED3DFVF_DIFFUSE) size += sizeof(DWORD);
2322 if (d3dvtVertexType & WINED3DFVF_SPECULAR) size += sizeof(DWORD);
2323 if (d3dvtVertexType & WINED3DFVF_PSIZE) size += sizeof(DWORD);
2324 switch (d3dvtVertexType & WINED3DFVF_POSITION_MASK) {
2325 case WINED3DFVF_XYZ: size += 3 * sizeof(float); break;
2326 case WINED3DFVF_XYZRHW: size += 4 * sizeof(float); break;
2327 case WINED3DFVF_XYZB1: size += 4 * sizeof(float); break;
2328 case WINED3DFVF_XYZB2: size += 5 * sizeof(float); break;
2329 case WINED3DFVF_XYZB3: size += 6 * sizeof(float); break;
2330 case WINED3DFVF_XYZB4: size += 7 * sizeof(float); break;
2331 case WINED3DFVF_XYZB5: size += 8 * sizeof(float); break;
2332 case WINED3DFVF_XYZW: size += 4 * sizeof(float); break;
2333 default: ERR("Unexpected position mask\n");
2335 for (i = 0; i < numTextures; i++) {
2336 size += GET_TEXCOORD_SIZE_FROM_FVF(d3dvtVertexType, i) * sizeof(float);
2342 void gen_ffp_frag_op(IWineD3DStateBlockImpl *stateblock, struct ffp_frag_settings *settings, BOOL ignore_textype) {
2346 static const unsigned char args[WINED3DTOP_LERP + 1] = {
2348 /* D3DTOP_DISABLE */ 0,
2349 /* D3DTOP_SELECTARG1 */ ARG1,
2350 /* D3DTOP_SELECTARG2 */ ARG2,
2351 /* D3DTOP_MODULATE */ ARG1 | ARG2,
2352 /* D3DTOP_MODULATE2X */ ARG1 | ARG2,
2353 /* D3DTOP_MODULATE4X */ ARG1 | ARG2,
2354 /* D3DTOP_ADD */ ARG1 | ARG2,
2355 /* D3DTOP_ADDSIGNED */ ARG1 | ARG2,
2356 /* D3DTOP_ADDSIGNED2X */ ARG1 | ARG2,
2357 /* D3DTOP_SUBTRACT */ ARG1 | ARG2,
2358 /* D3DTOP_ADDSMOOTH */ ARG1 | ARG2,
2359 /* D3DTOP_BLENDDIFFUSEALPHA */ ARG1 | ARG2,
2360 /* D3DTOP_BLENDTEXTUREALPHA */ ARG1 | ARG2,
2361 /* D3DTOP_BLENDFACTORALPHA */ ARG1 | ARG2,
2362 /* D3DTOP_BLENDTEXTUREALPHAPM */ ARG1 | ARG2,
2363 /* D3DTOP_BLENDCURRENTALPHA */ ARG1 | ARG2,
2364 /* D3DTOP_PREMODULATE */ ARG1 | ARG2,
2365 /* D3DTOP_MODULATEALPHA_ADDCOLOR */ ARG1 | ARG2,
2366 /* D3DTOP_MODULATECOLOR_ADDALPHA */ ARG1 | ARG2,
2367 /* D3DTOP_MODULATEINVALPHA_ADDCOLOR */ ARG1 | ARG2,
2368 /* D3DTOP_MODULATEINVCOLOR_ADDALPHA */ ARG1 | ARG2,
2369 /* D3DTOP_BUMPENVMAP */ ARG1 | ARG2,
2370 /* D3DTOP_BUMPENVMAPLUMINANCE */ ARG1 | ARG2,
2371 /* D3DTOP_DOTPRODUCT3 */ ARG1 | ARG2,
2372 /* D3DTOP_MULTIPLYADD */ ARG1 | ARG2 | ARG0,
2373 /* D3DTOP_LERP */ ARG1 | ARG2 | ARG0
2377 DWORD cop, aop, carg0, carg1, carg2, aarg0, aarg1, aarg2;
2378 IWineD3DDeviceImpl *device = stateblock->device;
2379 const struct wined3d_gl_info *gl_info = &device->adapter->gl_info;
2381 for (i = 0; i < gl_info->limits.texture_stages; ++i)
2383 IWineD3DBaseTextureImpl *texture;
2384 settings->op[i].padding = 0;
2385 if(stateblock->textureState[i][WINED3DTSS_COLOROP] == WINED3DTOP_DISABLE) {
2386 settings->op[i].cop = WINED3DTOP_DISABLE;
2387 settings->op[i].aop = WINED3DTOP_DISABLE;
2388 settings->op[i].carg0 = settings->op[i].carg1 = settings->op[i].carg2 = ARG_UNUSED;
2389 settings->op[i].aarg0 = settings->op[i].aarg1 = settings->op[i].aarg2 = ARG_UNUSED;
2390 settings->op[i].color_fixup = COLOR_FIXUP_IDENTITY;
2391 settings->op[i].dst = resultreg;
2392 settings->op[i].tex_type = tex_1d;
2393 settings->op[i].projected = proj_none;
2398 texture = (IWineD3DBaseTextureImpl *) stateblock->textures[i];
2400 settings->op[i].color_fixup = texture->resource.format_desc->color_fixup;
2401 if(ignore_textype) {
2402 settings->op[i].tex_type = tex_1d;
2404 switch (IWineD3DBaseTexture_GetTextureDimensions((IWineD3DBaseTexture *)texture)) {
2406 settings->op[i].tex_type = tex_1d;
2409 settings->op[i].tex_type = tex_2d;
2412 settings->op[i].tex_type = tex_3d;
2414 case GL_TEXTURE_CUBE_MAP_ARB:
2415 settings->op[i].tex_type = tex_cube;
2417 case GL_TEXTURE_RECTANGLE_ARB:
2418 settings->op[i].tex_type = tex_rect;
2423 settings->op[i].color_fixup = COLOR_FIXUP_IDENTITY;
2424 settings->op[i].tex_type = tex_1d;
2427 cop = stateblock->textureState[i][WINED3DTSS_COLOROP];
2428 aop = stateblock->textureState[i][WINED3DTSS_ALPHAOP];
2430 carg1 = (args[cop] & ARG1) ? stateblock->textureState[i][WINED3DTSS_COLORARG1] : ARG_UNUSED;
2431 carg2 = (args[cop] & ARG2) ? stateblock->textureState[i][WINED3DTSS_COLORARG2] : ARG_UNUSED;
2432 carg0 = (args[cop] & ARG0) ? stateblock->textureState[i][WINED3DTSS_COLORARG0] : ARG_UNUSED;
2434 if(is_invalid_op(device, i, cop, carg1, carg2, carg0)) {
2437 carg1 = WINED3DTA_CURRENT;
2438 cop = WINED3DTOP_SELECTARG1;
2441 if(cop == WINED3DTOP_DOTPRODUCT3) {
2442 /* A dotproduct3 on the colorop overwrites the alphaop operation and replicates
2443 * the color result to the alpha component of the destination
2450 aarg1 = (args[aop] & ARG1) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG1] : ARG_UNUSED;
2451 aarg2 = (args[aop] & ARG2) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG2] : ARG_UNUSED;
2452 aarg0 = (args[aop] & ARG0) ? stateblock->textureState[i][WINED3DTSS_ALPHAARG0] : ARG_UNUSED;
2455 if (i == 0 && stateblock->textures[0] && stateblock->renderState[WINED3DRS_COLORKEYENABLE])
2457 UINT texture_dimensions = IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[0]);
2459 if (texture_dimensions == GL_TEXTURE_2D || texture_dimensions == GL_TEXTURE_RECTANGLE_ARB)
2461 IWineD3DSurfaceImpl *surf;
2462 surf = (IWineD3DSurfaceImpl *) ((IWineD3DTextureImpl *) stateblock->textures[0])->surfaces[0];
2464 if (surf->CKeyFlags & WINEDDSD_CKSRCBLT && !surf->resource.format_desc->alpha_mask)
2466 if (aop == WINED3DTOP_DISABLE)
2468 aarg1 = WINED3DTA_TEXTURE;
2469 aop = WINED3DTOP_SELECTARG1;
2471 else if (aop == WINED3DTOP_SELECTARG1 && aarg1 != WINED3DTA_TEXTURE)
2473 if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
2475 aarg2 = WINED3DTA_TEXTURE;
2476 aop = WINED3DTOP_MODULATE;
2478 else aarg1 = WINED3DTA_TEXTURE;
2480 else if (aop == WINED3DTOP_SELECTARG2 && aarg2 != WINED3DTA_TEXTURE)
2482 if (stateblock->renderState[WINED3DRS_ALPHABLENDENABLE])
2484 aarg1 = WINED3DTA_TEXTURE;
2485 aop = WINED3DTOP_MODULATE;
2487 else aarg2 = WINED3DTA_TEXTURE;
2493 if(is_invalid_op(device, i, aop, aarg1, aarg2, aarg0)) {
2496 aarg1 = WINED3DTA_CURRENT;
2497 aop = WINED3DTOP_SELECTARG1;
2500 if(carg1 == WINED3DTA_TEXTURE || carg2 == WINED3DTA_TEXTURE || carg0 == WINED3DTA_TEXTURE ||
2501 aarg1 == WINED3DTA_TEXTURE || aarg2 == WINED3DTA_TEXTURE || aarg0 == WINED3DTA_TEXTURE) {
2502 ttff = stateblock->textureState[i][WINED3DTSS_TEXTURETRANSFORMFLAGS];
2503 if(ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT3)) {
2504 settings->op[i].projected = proj_count3;
2505 } else if(ttff == (WINED3DTTFF_PROJECTED | WINED3DTTFF_COUNT4)) {
2506 settings->op[i].projected = proj_count4;
2508 settings->op[i].projected = proj_none;
2511 settings->op[i].projected = proj_none;
2514 settings->op[i].cop = cop;
2515 settings->op[i].aop = aop;
2516 settings->op[i].carg0 = carg0;
2517 settings->op[i].carg1 = carg1;
2518 settings->op[i].carg2 = carg2;
2519 settings->op[i].aarg0 = aarg0;
2520 settings->op[i].aarg1 = aarg1;
2521 settings->op[i].aarg2 = aarg2;
2523 if(stateblock->textureState[i][WINED3DTSS_RESULTARG] == WINED3DTA_TEMP) {
2524 settings->op[i].dst = tempreg;
2526 settings->op[i].dst = resultreg;
2530 /* Clear unsupported stages */
2531 for(; i < MAX_TEXTURES; i++) {
2532 memset(&settings->op[i], 0xff, sizeof(settings->op[i]));
2535 if(stateblock->renderState[WINED3DRS_FOGENABLE] == FALSE) {
2536 settings->fog = FOG_OFF;
2537 } else if(stateblock->renderState[WINED3DRS_FOGTABLEMODE] == WINED3DFOG_NONE) {
2538 if(use_vs(stateblock) || ((IWineD3DVertexDeclarationImpl *) stateblock->vertexDecl)->position_transformed) {
2539 settings->fog = FOG_LINEAR;
2541 switch(stateblock->renderState[WINED3DRS_FOGVERTEXMODE]) {
2542 case WINED3DFOG_NONE:
2543 case WINED3DFOG_LINEAR:
2544 settings->fog = FOG_LINEAR;
2546 case WINED3DFOG_EXP:
2547 settings->fog = FOG_EXP;
2549 case WINED3DFOG_EXP2:
2550 settings->fog = FOG_EXP2;
2555 switch(stateblock->renderState[WINED3DRS_FOGTABLEMODE]) {
2556 case WINED3DFOG_LINEAR:
2557 settings->fog = FOG_LINEAR;
2559 case WINED3DFOG_EXP:
2560 settings->fog = FOG_EXP;
2562 case WINED3DFOG_EXP2:
2563 settings->fog = FOG_EXP2;
2567 if(stateblock->renderState[WINED3DRS_SRGBWRITEENABLE]) {
2568 settings->sRGB_write = 1;
2570 settings->sRGB_write = 0;
2572 if(device->vs_clipping || !use_vs(stateblock) || !stateblock->renderState[WINED3DRS_CLIPPING] ||
2573 !stateblock->renderState[WINED3DRS_CLIPPLANEENABLE]) {
2574 /* No need to emulate clipplanes if GL supports native vertex shader clipping or if
2575 * the fixed function vertex pipeline is used(which always supports clipplanes), or
2576 * if no clipplane is enabled
2578 settings->emul_clipplanes = 0;
2580 settings->emul_clipplanes = 1;
2584 const struct ffp_frag_desc *find_ffp_frag_shader(const struct wine_rb_tree *fragment_shaders,
2585 const struct ffp_frag_settings *settings)
2587 struct wine_rb_entry *entry = wine_rb_get(fragment_shaders, settings);
2588 return entry ? WINE_RB_ENTRY_VALUE(entry, struct ffp_frag_desc, entry) : NULL;
2591 void add_ffp_frag_shader(struct wine_rb_tree *shaders, struct ffp_frag_desc *desc)
2593 /* Note that the key is the implementation independent part of the ffp_frag_desc structure,
2594 * whereas desc points to an extended structure with implementation specific parts. */
2595 if (wine_rb_put(shaders, &desc->settings, &desc->entry) == -1)
2597 ERR("Failed to insert ffp frag shader.\n");
2601 /* Activates the texture dimension according to the bound D3D texture.
2602 * Does not care for the colorop or correct gl texture unit(when using nvrc)
2603 * Requires the caller to activate the correct unit before
2605 /* GL locking is done by the caller (state handler) */
2606 void texture_activate_dimensions(DWORD stage, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
2608 const struct wined3d_gl_info *gl_info = context->gl_info;
2610 if (stateblock->textures[stage])
2612 switch (IWineD3DBaseTexture_GetTextureDimensions(stateblock->textures[stage])) {
2614 glDisable(GL_TEXTURE_3D);
2615 checkGLcall("glDisable(GL_TEXTURE_3D)");
2616 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2618 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2619 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2621 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2623 glDisable(GL_TEXTURE_RECTANGLE_ARB);
2624 checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2626 glEnable(GL_TEXTURE_2D);
2627 checkGLcall("glEnable(GL_TEXTURE_2D)");
2629 case GL_TEXTURE_RECTANGLE_ARB:
2630 glDisable(GL_TEXTURE_2D);
2631 checkGLcall("glDisable(GL_TEXTURE_2D)");
2632 glDisable(GL_TEXTURE_3D);
2633 checkGLcall("glDisable(GL_TEXTURE_3D)");
2634 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2636 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2637 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2639 glEnable(GL_TEXTURE_RECTANGLE_ARB);
2640 checkGLcall("glEnable(GL_TEXTURE_RECTANGLE_ARB)");
2643 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2645 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2646 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2648 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2650 glDisable(GL_TEXTURE_RECTANGLE_ARB);
2651 checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2653 glDisable(GL_TEXTURE_2D);
2654 checkGLcall("glDisable(GL_TEXTURE_2D)");
2655 glEnable(GL_TEXTURE_3D);
2656 checkGLcall("glEnable(GL_TEXTURE_3D)");
2658 case GL_TEXTURE_CUBE_MAP_ARB:
2659 glDisable(GL_TEXTURE_2D);
2660 checkGLcall("glDisable(GL_TEXTURE_2D)");
2661 glDisable(GL_TEXTURE_3D);
2662 checkGLcall("glDisable(GL_TEXTURE_3D)");
2663 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2665 glDisable(GL_TEXTURE_RECTANGLE_ARB);
2666 checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2668 glEnable(GL_TEXTURE_CUBE_MAP_ARB);
2669 checkGLcall("glEnable(GL_TEXTURE_CUBE_MAP_ARB)");
2673 glEnable(GL_TEXTURE_2D);
2674 checkGLcall("glEnable(GL_TEXTURE_2D)");
2675 glDisable(GL_TEXTURE_3D);
2676 checkGLcall("glDisable(GL_TEXTURE_3D)");
2677 if (gl_info->supported[ARB_TEXTURE_CUBE_MAP])
2679 glDisable(GL_TEXTURE_CUBE_MAP_ARB);
2680 checkGLcall("glDisable(GL_TEXTURE_CUBE_MAP_ARB)");
2682 if (gl_info->supported[ARB_TEXTURE_RECTANGLE])
2684 glDisable(GL_TEXTURE_RECTANGLE_ARB);
2685 checkGLcall("glDisable(GL_TEXTURE_RECTANGLE_ARB)");
2687 /* Binding textures is done by samplers. A dummy texture will be bound */
2691 /* GL locking is done by the caller (state handler) */
2692 void sampler_texdim(DWORD state, IWineD3DStateBlockImpl *stateblock, struct wined3d_context *context)
2694 DWORD sampler = state - STATE_SAMPLER(0);
2695 DWORD mapped_stage = stateblock->device->texUnitMap[sampler];
2697 /* No need to enable / disable anything here for unused samplers. The tex_colorop
2698 * handler takes care. Also no action is needed with pixel shaders, or if tex_colorop
2699 * will take care of this business
2701 if (mapped_stage == WINED3D_UNMAPPED_STAGE || mapped_stage >= context->gl_info->limits.textures) return;
2702 if(sampler >= stateblock->lowest_disabled_stage) return;
2703 if(isStateDirty(context, STATE_TEXTURESTAGE(sampler, WINED3DTSS_COLOROP))) return;
2705 texture_activate_dimensions(sampler, stateblock, context);
2708 void *wined3d_rb_alloc(size_t size)
2710 return HeapAlloc(GetProcessHeap(), 0, size);
2713 void *wined3d_rb_realloc(void *ptr, size_t size)
2715 return HeapReAlloc(GetProcessHeap(), 0, ptr, size);
2718 void wined3d_rb_free(void *ptr)
2720 HeapFree(GetProcessHeap(), 0, ptr);
2723 static int ffp_frag_program_key_compare(const void *key, const struct wine_rb_entry *entry)
2725 const struct ffp_frag_settings *ka = key;
2726 const struct ffp_frag_settings *kb = &WINE_RB_ENTRY_VALUE(entry, const struct ffp_frag_desc, entry)->settings;
2728 return memcmp(ka, kb, sizeof(*ka));
2731 const struct wine_rb_functions wined3d_ffp_frag_program_rb_functions =
2736 ffp_frag_program_key_compare,
2739 UINT wined3d_log2i(UINT32 x)
2741 static const UINT l[] =
2743 ~0U, 0, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3,
2744 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
2745 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
2746 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
2747 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2748 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2749 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2750 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
2751 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2752 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2753 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2754 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2755 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2756 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2757 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2758 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
2762 return (i = x >> 16) ? (x = i >> 8) ? l[x] + 24 : l[i] + 16 : (i = x >> 8) ? l[i] + 8 : l[x];
2765 /* Set the shader type for this device, depending on the given capabilities
2766 * and the user preferences in wined3d_settings. */
2767 void select_shader_mode(const struct wined3d_gl_info *gl_info, int *ps_selected, int *vs_selected)
2769 if (wined3d_settings.vs_mode == VS_NONE) *vs_selected = SHADER_NONE;
2770 else if (gl_info->supported[ARB_VERTEX_SHADER] && wined3d_settings.glslRequested)
2772 /* Geforce4 cards support GLSL but for vertex shaders only. Further its reported GLSL caps are
2773 * wrong. This combined with the fact that glsl won't offer more features or performance, use ARB
2774 * shaders only on this card. */
2775 if (gl_info->supported[NV_VERTEX_PROGRAM] && !gl_info->supported[NV_VERTEX_PROGRAM2]) *vs_selected = SHADER_ARB;
2776 else *vs_selected = SHADER_GLSL;
2778 else if (gl_info->supported[ARB_VERTEX_PROGRAM]) *vs_selected = SHADER_ARB;
2779 else *vs_selected = SHADER_NONE;
2781 if (wined3d_settings.ps_mode == PS_NONE) *ps_selected = SHADER_NONE;
2782 else if (gl_info->supported[ARB_FRAGMENT_SHADER] && wined3d_settings.glslRequested) *ps_selected = SHADER_GLSL;
2783 else if (gl_info->supported[ARB_FRAGMENT_PROGRAM]) *ps_selected = SHADER_ARB;
2784 else if (gl_info->supported[ATI_FRAGMENT_SHADER]) *ps_selected = SHADER_ATI;
2785 else *ps_selected = SHADER_NONE;