[1/8] wined3d: Move some code specific to the different shader
backends into the respective source files
H. Verbeet
hverbeet at gmail.com
Mon Nov 27 13:50:37 CST 2006
Changelog:
- Move some code specific to the different shader backends into the
respective source files, call it through a function table.
-------------- next part --------------
---
dlls/wined3d/arb_program_shader.c | 110 +++++++++++++++++++++
dlls/wined3d/baseshader.c | 12 ++
dlls/wined3d/drawprim.c | 197 ++++---------------------------------
dlls/wined3d/glsl_shader.c | 79 +++++++++++++++
dlls/wined3d/wined3d_private.h | 13 ++
5 files changed, 233 insertions(+), 178 deletions(-)
diff --git a/dlls/wined3d/arb_program_shader.c b/dlls/wined3d/arb_program_shader.c
index 736edde..a0d0d53 100644
--- a/dlls/wined3d/arb_program_shader.c
+++ b/dlls/wined3d/arb_program_shader.c
@@ -910,3 +910,113 @@ void vshader_hw_map2gl(SHADER_OPCODE_ARG
}
shader_addline(buffer, "%s;\n", tmpLine);
}
+
+static GLuint create_arb_blt_vertex_program(WineD3D_GL_Info *gl_info) {
+ GLuint program_id = 0;
+ const char *blt_vprogram =
+ "!!ARBvp1.0\n"
+ "PARAM c[1] = { { 1, 0.5 } };\n"
+ "MOV result.position, vertex.position;\n"
+ "MOV result.color, c[0].x;\n"
+ "MAD result.texcoord[0].y, -vertex.position, c[0], c[0];\n"
+ "MAD result.texcoord[0].x, vertex.position, c[0].y, c[0].y;\n"
+ "END\n";
+
+ GL_EXTCALL(glGenProgramsARB(1, &program_id));
+ GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, program_id));
+ GL_EXTCALL(glProgramStringARB(GL_VERTEX_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB, strlen(blt_vprogram), blt_vprogram));
+
+ if (glGetError() == GL_INVALID_OPERATION) {
+ GLint pos;
+ glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &pos);
+ FIXME("Vertex program error at position %d: %s\n", pos,
+ debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
+ }
+
+ return program_id;
+}
+
+static GLuint create_arb_blt_fragment_program(WineD3D_GL_Info *gl_info) {
+ GLuint program_id = 0;
+ const char *blt_fprogram =
+ "!!ARBfp1.0\n"
+ "TEMP R0;\n"
+ "TEX R0.x, fragment.texcoord[0], texture[0], 2D;\n"
+ "MOV result.depth.z, R0.x;\n"
+ "END\n";
+
+ GL_EXTCALL(glGenProgramsARB(1, &program_id));
+ GL_EXTCALL(glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB, program_id));
+ GL_EXTCALL(glProgramStringARB(GL_FRAGMENT_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB, strlen(blt_fprogram), blt_fprogram));
+
+ if (glGetError() == GL_INVALID_OPERATION) {
+ GLint pos;
+ glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &pos);
+ FIXME("Fragment program error at position %d: %s\n", pos,
+ debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
+ }
+
+ return program_id;
+}
+
+static void shader_arb_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) {
+ IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+ WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info;
+
+ if (useVS) {
+ TRACE("Using vertex shader\n");
+
+ /* Bind the vertex program */
+ GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB,
+ ((IWineD3DVertexShaderImpl *)This->stateBlock->vertexShader)->baseShader.prgId));
+ checkGLcall("glBindProgramARB(GL_VERTEX_PROGRAM_ARB, vertexShader->prgId);");
+
+ /* Enable OpenGL vertex programs */
+ glEnable(GL_VERTEX_PROGRAM_ARB);
+ checkGLcall("glEnable(GL_VERTEX_PROGRAM_ARB);");
+ TRACE_(d3d_shader)("(%p) : Bound vertex program %u and enabled GL_VERTEX_PROGRAM_ARB\n",
+ This, ((IWineD3DVertexShaderImpl *)This->stateBlock->vertexShader)->baseShader.prgId);
+ }
+
+ if (usePS) {
+ TRACE("Using pixel shader\n");
+
+ /* Bind the fragment program */
+ GL_EXTCALL(glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB,
+ ((IWineD3DPixelShaderImpl *)This->stateBlock->pixelShader)->baseShader.prgId));
+ checkGLcall("glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB, pixelShader->prgId);");
+
+ /* Enable OpenGL fragment programs */
+ glEnable(GL_FRAGMENT_PROGRAM_ARB);
+ checkGLcall("glEnable(GL_FRAGMENT_PROGRAM_ARB);");
+ TRACE_(d3d_shader)("(%p) : Bound fragment program %u and enabled GL_FRAGMENT_PROGRAM_ARB\n",
+ This, ((IWineD3DPixelShaderImpl *)This->stateBlock->pixelShader)->baseShader.prgId);
+ }
+}
+
+static void shader_arb_select_depth_blt(IWineD3DDevice *iface) {
+ IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+ WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info;
+ static GLuint vprogram_id = 0;
+ static GLuint fprogram_id = 0;
+
+ if (!vprogram_id) vprogram_id = create_arb_blt_vertex_program(gl_info);
+ GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, vprogram_id));
+ glEnable(GL_VERTEX_PROGRAM_ARB);
+
+ if (!fprogram_id) fprogram_id = create_arb_blt_fragment_program(gl_info);
+ GL_EXTCALL(glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB, fprogram_id));
+ glEnable(GL_FRAGMENT_PROGRAM_ARB);
+}
+
+static void shader_arb_cleanup(BOOL usePS, BOOL useVS) {
+ if (useVS) glDisable(GL_VERTEX_PROGRAM_ARB);
+ if (usePS) glDisable(GL_FRAGMENT_PROGRAM_ARB);
+}
+
+const shader_backend_t arb_program_shader_backend = {
+ &shader_arb_select,
+ &shader_arb_select_depth_blt,
+ &shader_arb_load_constants,
+ &shader_arb_cleanup
+};
diff --git a/dlls/wined3d/baseshader.c b/dlls/wined3d/baseshader.c
index 1d36454..c1c162b 100644
--- a/dlls/wined3d/baseshader.c
+++ b/dlls/wined3d/baseshader.c
@@ -977,3 +977,15 @@ void shader_delete_constant_list(
HeapFree(GetProcessHeap(), 0, constant);
}
}
+
+static void shader_none_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) {}
+static void shader_none_select_depth_blt(IWineD3DDevice *iface) {}
+static void shader_none_load_constants(IWineD3DDevice *iface, char usePS, char useVS) {}
+static void shader_none_cleanup(BOOL usePS, BOOL useVS) {}
+
+const shader_backend_t none_shader_backend = {
+ &shader_none_select,
+ &shader_none_select_depth_blt,
+ &shader_none_load_constants,
+ &shader_none_cleanup
+};
diff --git a/dlls/wined3d/drawprim.c b/dlls/wined3d/drawprim.c
index 42ad97c..0c708c3 100644
--- a/dlls/wined3d/drawprim.c
+++ b/dlls/wined3d/drawprim.c
@@ -1800,85 +1800,40 @@ #undef BUFFER_OR_DATA
*/
IWineD3DPixelShader_CompileShader(This->stateBlock->pixelShader);
}
- /* If GLSL is used for either pixel or vertex shaders, make a GLSL program
- * Otherwise set NULL, to restore fixed function */
- if ((This->vs_selected_mode == SHADER_GLSL && useVertexShaderFunction) ||
- (This->ps_selected_mode == SHADER_GLSL && usePixelShaderFunction))
- set_glsl_shader_program(iface);
- else
- This->stateBlock->glsl_program = NULL;
- /* If GLSL is used now, or might have been used before, (re)set the program */
+ /* Make any shaders active */
if (This->vs_selected_mode == SHADER_GLSL || This->ps_selected_mode == SHADER_GLSL) {
-
- GLhandleARB progId = This->stateBlock->glsl_program ? This->stateBlock->glsl_program->programId : 0;
- if (progId)
- TRACE_(d3d_shader)("Using GLSL program %u\n", progId);
- GL_EXTCALL(glUseProgramObjectARB(progId));
- checkGLcall("glUseProgramObjectARB");
+ glsl_shader_backend.shader_select(iface, usePixelShaderFunction, useVertexShaderFunction);
+ } else if (This->vs_selected_mode == SHADER_ARB || This->ps_selected_mode == SHADER_ARB) {
+ arb_program_shader_backend.shader_select(iface, usePixelShaderFunction, useVertexShaderFunction);
}
-
- if (useVertexShaderFunction) {
-
- TRACE("Using vertex shader\n");
- if (This->vs_selected_mode == SHADER_ARB) {
- /* Bind the vertex program */
- GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB,
- ((IWineD3DVertexShaderImpl *)This->stateBlock->vertexShader)->baseShader.prgId));
- checkGLcall("glBindProgramARB(GL_VERTEX_PROGRAM_ARB, vertexShader->prgId);");
-
- /* Enable OpenGL vertex programs */
- glEnable(GL_VERTEX_PROGRAM_ARB);
- checkGLcall("glEnable(GL_VERTEX_PROGRAM_ARB);");
- TRACE_(d3d_shader)("(%p) : Bound vertex program %u and enabled GL_VERTEX_PROGRAM_ARB\n",
- This, ((IWineD3DVertexShaderImpl *)This->stateBlock->vertexShader)->baseShader.prgId);
- }
+ /* Load any global constants/uniforms that may have been set by the application */
+ if (This->vs_selected_mode == SHADER_GLSL || This->ps_selected_mode == SHADER_GLSL) {
+ glsl_shader_backend.shader_load_constants(iface, usePixelShaderFunction, useVertexShaderFunction);
+ } else if (This->vs_selected_mode == SHADER_ARB || This->ps_selected_mode == SHADER_ARB) {
+ arb_program_shader_backend.shader_load_constants(iface, usePixelShaderFunction, useVertexShaderFunction);
}
- if (usePixelShaderFunction) {
-
- TRACE("Using pixel shader\n");
-
- if (This->ps_selected_mode == SHADER_ARB) {
- /* Bind the fragment program */
- GL_EXTCALL(glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB,
- ((IWineD3DPixelShaderImpl *)This->stateBlock->pixelShader)->baseShader.prgId));
- checkGLcall("glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB, pixelShader->prgId);");
-
- /* Enable OpenGL fragment programs */
- glEnable(GL_FRAGMENT_PROGRAM_ARB);
- checkGLcall("glEnable(GL_FRAGMENT_PROGRAM_ARB);");
- TRACE_(d3d_shader)("(%p) : Bound fragment program %u and enabled GL_FRAGMENT_PROGRAM_ARB\n",
- This, ((IWineD3DPixelShaderImpl *)This->stateBlock->pixelShader)->baseShader.prgId);
- }
- }
-
- /* Load any global constants/uniforms that may have been set by the application */
- if (This->vs_selected_mode == SHADER_GLSL || This->ps_selected_mode == SHADER_GLSL)
- shader_glsl_load_constants(iface, usePixelShaderFunction, useVertexShaderFunction);
- else if (This->vs_selected_mode == SHADER_ARB || This->ps_selected_mode == SHADER_ARB)
- shader_arb_load_constants(iface, usePixelShaderFunction, useVertexShaderFunction);
-
/* Draw vertex-by-vertex */
if (useDrawStridedSlow)
drawStridedSlow(iface, dataLocations, numberOfIndicies, glPrimType, idxData, idxSize, minIndex, StartIdx);
else
drawStridedFast(iface, numberOfIndicies, glPrimType, idxData, idxSize, minIndex, StartIdx);
- /* Cleanup vertex program */
+ /* Cleanup any shaders */
+ if (This->vs_selected_mode == SHADER_GLSL || This->ps_selected_mode == SHADER_GLSL) {
+ glsl_shader_backend.shader_cleanup(usePixelShaderFunction, useVertexShaderFunction);
+ } else if (This->vs_selected_mode == SHADER_ARB || This->ps_selected_mode == SHADER_ARB) {
+ arb_program_shader_backend.shader_cleanup(usePixelShaderFunction, useVertexShaderFunction);
+ }
+
+ /* Unload vertex data */
if (useVertexShaderFunction) {
unloadNumberedArrays(iface);
-
- if (This->vs_selected_mode == SHADER_ARB)
- glDisable(GL_VERTEX_PROGRAM_ARB);
} else {
unloadVertexData(iface);
}
-
- /* Cleanup fragment program */
- if (usePixelShaderFunction && This->ps_selected_mode == SHADER_ARB)
- glDisable(GL_FRAGMENT_PROGRAM_ARB);
}
inline void drawPrimitiveTraceDataLocations(
@@ -2089,99 +2044,6 @@ static void check_fbo_status(IWineD3DDev
}
}
-static GLuint create_arb_blt_vertex_program(IWineD3DDevice *iface) {
- IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-
- GLuint program_id = 0;
- const char *blt_vprogram =
- "!!ARBvp1.0\n"
- "PARAM c[1] = { { 1, 0.5 } };\n"
- "MOV result.position, vertex.position;\n"
- "MOV result.color, c[0].x;\n"
- "MAD result.texcoord[0].y, -vertex.position, c[0], c[0];\n"
- "MAD result.texcoord[0].x, vertex.position, c[0].y, c[0].y;\n"
- "END\n";
-
- GL_EXTCALL(glGenProgramsARB(1, &program_id));
- GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, program_id));
- GL_EXTCALL(glProgramStringARB(GL_VERTEX_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB, strlen(blt_vprogram), blt_vprogram));
-
- if (glGetError() == GL_INVALID_OPERATION) {
- GLint pos;
- glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &pos);
- FIXME("Vertex program error at position %d: %s\n", pos,
- debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
- }
-
- return program_id;
-}
-
-static GLuint create_arb_blt_fragment_program(IWineD3DDevice *iface) {
- IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-
- GLuint program_id = 0;
- const char *blt_fprogram =
- "!!ARBfp1.0\n"
- "TEMP R0;\n"
- "TEX R0.x, fragment.texcoord[0], texture[0], 2D;\n"
- "MOV result.depth.z, R0.x;\n"
- "END\n";
-
- GL_EXTCALL(glGenProgramsARB(1, &program_id));
- GL_EXTCALL(glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB, program_id));
- GL_EXTCALL(glProgramStringARB(GL_FRAGMENT_PROGRAM_ARB, GL_PROGRAM_FORMAT_ASCII_ARB, strlen(blt_fprogram), blt_fprogram));
-
- if (glGetError() == GL_INVALID_OPERATION) {
- GLint pos;
- glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &pos);
- FIXME("Fragment program error at position %d: %s\n", pos,
- debugstr_a((const char *)glGetString(GL_PROGRAM_ERROR_STRING_ARB)));
- }
-
- return program_id;
-}
-
-static GLhandleARB create_glsl_blt_shader(IWineD3DDevice *iface) {
- IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
-
- GLhandleARB program_id;
- GLhandleARB vshader_id, pshader_id;
- const char *blt_vshader[] = {
- "void main(void)\n"
- "{\n"
- " gl_Position = gl_Vertex;\n"
- " gl_FrontColor = vec4(1.0);\n"
- " gl_TexCoord[0].x = (gl_Vertex.x * 0.5) + 0.5;\n"
- " gl_TexCoord[0].y = (-gl_Vertex.y * 0.5) + 0.5;\n"
- "}\n"
- };
-
- const char *blt_pshader[] = {
- "uniform sampler2D sampler;\n"
- "void main(void)\n"
- "{\n"
- " gl_FragDepth = texture2D(sampler, gl_TexCoord[0].xy).x;\n"
- "}\n"
- };
-
- vshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB));
- GL_EXTCALL(glShaderSourceARB(vshader_id, 1, blt_vshader, NULL));
- GL_EXTCALL(glCompileShaderARB(vshader_id));
-
- pshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB));
- GL_EXTCALL(glShaderSourceARB(pshader_id, 1, blt_pshader, NULL));
- GL_EXTCALL(glCompileShaderARB(pshader_id));
-
- program_id = GL_EXTCALL(glCreateProgramObjectARB());
- GL_EXTCALL(glAttachObjectARB(program_id, vshader_id));
- GL_EXTCALL(glAttachObjectARB(program_id, pshader_id));
- GL_EXTCALL(glLinkProgramARB(program_id));
-
- print_glsl_info_log(&GLINFO_LOCATION, program_id);
-
- return program_id;
-}
-
static void depth_blt(IWineD3DDevice *iface, GLuint texture) {
IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
BOOL glsl_mode = This->vs_selected_mode == SHADER_GLSL || This->ps_selected_mode == SHADER_GLSL;
@@ -2199,29 +2061,8 @@ static void depth_blt(IWineD3DDevice *if
glBindTexture(GL_TEXTURE_2D, texture);
glEnable(GL_TEXTURE_2D);
- if (glsl_mode) {
- static GLhandleARB program_id = 0;
- static GLhandleARB loc = -1;
-
- if (!program_id) {
- program_id = create_glsl_blt_shader(iface);
- loc = GL_EXTCALL(glGetUniformLocationARB(program_id, "sampler"));
- }
-
- GL_EXTCALL(glUseProgramObjectARB(program_id));
- GL_EXTCALL(glUniform1iARB(loc, 0));
- } else {
- static GLuint vprogram_id = 0;
- static GLuint fprogram_id = 0;
-
- if (!vprogram_id) vprogram_id = create_arb_blt_vertex_program(iface);
- GL_EXTCALL(glBindProgramARB(GL_VERTEX_PROGRAM_ARB, vprogram_id));
- glEnable(GL_VERTEX_PROGRAM_ARB);
-
- if (!fprogram_id) fprogram_id = create_arb_blt_fragment_program(iface);
- GL_EXTCALL(glBindProgramARB(GL_FRAGMENT_PROGRAM_ARB, fprogram_id));
- glEnable(GL_FRAGMENT_PROGRAM_ARB);
- }
+ if (glsl_mode) glsl_shader_backend.shader_select_depth_blt(iface);
+ else arb_program_shader_backend.shader_select_depth_blt(iface);
glBegin(GL_TRIANGLE_STRIP);
glVertex2f(-1.0f, -1.0f);
diff --git a/dlls/wined3d/glsl_shader.c b/dlls/wined3d/glsl_shader.c
index 86d9fc9..01b3b75 100644
--- a/dlls/wined3d/glsl_shader.c
+++ b/dlls/wined3d/glsl_shader.c
@@ -1901,3 +1901,82 @@ void vshader_glsl_output_unpack(
}
}
}
+
+static GLhandleARB create_glsl_blt_shader(WineD3D_GL_Info *gl_info) {
+ GLhandleARB program_id;
+ GLhandleARB vshader_id, pshader_id;
+ const char *blt_vshader[] = {
+ "void main(void)\n"
+ "{\n"
+ " gl_Position = gl_Vertex;\n"
+ " gl_FrontColor = vec4(1.0);\n"
+ " gl_TexCoord[0].x = (gl_Vertex.x * 0.5) + 0.5;\n"
+ " gl_TexCoord[0].y = (-gl_Vertex.y * 0.5) + 0.5;\n"
+ "}\n"
+ };
+
+ const char *blt_pshader[] = {
+ "uniform sampler2D sampler;\n"
+ "void main(void)\n"
+ "{\n"
+ " gl_FragDepth = texture2D(sampler, gl_TexCoord[0].xy).x;\n"
+ "}\n"
+ };
+
+ vshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB));
+ GL_EXTCALL(glShaderSourceARB(vshader_id, 1, blt_vshader, NULL));
+ GL_EXTCALL(glCompileShaderARB(vshader_id));
+
+ pshader_id = GL_EXTCALL(glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB));
+ GL_EXTCALL(glShaderSourceARB(pshader_id, 1, blt_pshader, NULL));
+ GL_EXTCALL(glCompileShaderARB(pshader_id));
+
+ program_id = GL_EXTCALL(glCreateProgramObjectARB());
+ GL_EXTCALL(glAttachObjectARB(program_id, vshader_id));
+ GL_EXTCALL(glAttachObjectARB(program_id, pshader_id));
+ GL_EXTCALL(glLinkProgramARB(program_id));
+
+ print_glsl_info_log(&GLINFO_LOCATION, program_id);
+
+ return program_id;
+}
+
+static void shader_glsl_select(IWineD3DDevice *iface, BOOL usePS, BOOL useVS) {
+ IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+ WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info;
+ GLhandleARB program_id = 0;
+
+ if (useVS || usePS) set_glsl_shader_program(iface);
+ else This->stateBlock->glsl_program = NULL;
+
+ program_id = This->stateBlock->glsl_program ? This->stateBlock->glsl_program->programId : 0;
+ if (program_id) TRACE("Using GLSL program %u\n", program_id);
+ GL_EXTCALL(glUseProgramObjectARB(program_id));
+ checkGLcall("glUseProgramObjectARB");
+}
+
+static void shader_glsl_select_depth_blt(IWineD3DDevice *iface) {
+ IWineD3DDeviceImpl *This = (IWineD3DDeviceImpl *)iface;
+ WineD3D_GL_Info *gl_info = &((IWineD3DImpl *)(This->wineD3D))->gl_info;
+ static GLhandleARB program_id = 0;
+ static GLhandleARB loc = -1;
+
+ if (!program_id) {
+ program_id = create_glsl_blt_shader(gl_info);
+ loc = GL_EXTCALL(glGetUniformLocationARB(program_id, "sampler"));
+ }
+
+ GL_EXTCALL(glUseProgramObjectARB(program_id));
+ GL_EXTCALL(glUniform1iARB(loc, 0));
+}
+
+static void shader_glsl_cleanup(BOOL usePS, BOOL useVS) {
+ /* Nothing to do */
+}
+
+const shader_backend_t glsl_shader_backend = {
+ &shader_glsl_select,
+ &shader_glsl_select_depth_blt,
+ &shader_glsl_load_constants,
+ &shader_glsl_cleanup
+};
diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h
index 10ef914..8db15e0 100644
--- a/dlls/wined3d/wined3d_private.h
+++ b/dlls/wined3d/wined3d_private.h
@@ -172,6 +172,19 @@ typedef struct wined3d_settings_s {
extern wined3d_settings_t wined3d_settings;
+/* Shader backends */
+
+typedef struct {
+ void (*shader_select)(IWineD3DDevice *iface, BOOL usePS, BOOL useVS);
+ void (*shader_select_depth_blt)(IWineD3DDevice *iface);
+ void (*shader_load_constants)(IWineD3DDevice *iface, char usePS, char useVS);
+ void (*shader_cleanup)(BOOL usePS, BOOL useVS);
+} shader_backend_t;
+
+extern const shader_backend_t glsl_shader_backend;
+extern const shader_backend_t arb_program_shader_backend;
+extern const shader_backend_t none_shader_backend;
+
/* X11 locking */
extern void (*wine_tsx11_lock_ptr)(void);
More information about the wine-patches
mailing list