[WINED3D 4/13] Resend: Further split up GenerateProgramArbHW for
pixelshaders
Jason Green
jave27 at gmail.com
Tue May 9 21:30:11 CDT 2006
-------------- next part --------------
Subject: [PATCH 04/13] wined3d: Further split up GenerateProgramArbHW for pixelshaders
---
dlls/wined3d/pixelshader.c | 229 ++++++++++++++++++++++------------------
dlls/wined3d/vertexshader.c | 2
dlls/wined3d/wined3d_private.h | 8 +
3 files changed, 136 insertions(+), 103 deletions(-)
f034918af7f40b59ed473c81b949a37d4793e46e
diff --git a/dlls/wined3d/pixelshader.c b/dlls/wined3d/pixelshader.c
index 6f51ec7..a93178a 100644
--- a/dlls/wined3d/pixelshader.c
+++ b/dlls/wined3d/pixelshader.c
@@ -617,6 +617,12 @@ void pshader_hw_texreg2ar(SHADER_OPCODE_
void pshader_hw_texreg2gb(SHADER_OPCODE_ARG* arg);
void pshader_hw_texbem(SHADER_OPCODE_ARG* arg);
void pshader_hw_def(SHADER_OPCODE_ARG* arg);
+void pshader_hw_texm3x2pad(SHADER_OPCODE_ARG* arg);
+void pshader_hw_texm3x2tex(SHADER_OPCODE_ARG* arg);
+void pshader_hw_texm3x3pad(SHADER_OPCODE_ARG* arg);
+void pshader_hw_texm3x3tex(SHADER_OPCODE_ARG* arg);
+void pshader_hw_texm3x3spec(SHADER_OPCODE_ARG* arg);
+void pshader_hw_texm3x3vspec(SHADER_OPCODE_ARG* arg);
/**
* log, exp, frc, m*x* seems to be macros ins ... to see
@@ -709,13 +715,13 @@ CONST SHADER_OPCODE IWineD3DPixelShaderI
{D3DSIO_TEXREG2AR,"texreg2ar","undefined", 2, pshader_texreg2ar, pshader_hw_texreg2ar, D3DPS_VERSION(1,1), D3DPS_VERSION(1,3)},
{D3DSIO_TEXREG2GB,"texreg2gb","undefined", 2, pshader_texreg2gb, pshader_hw_texreg2gb, D3DPS_VERSION(1,2), D3DPS_VERSION(1,3)},
{D3DSIO_TEXREG2RGB, "texreg2rgb", GLNAME_REQUIRE_GLSL, 2, pshader_texreg2rgb, NULL, D3DPS_VERSION(1,2), D3DPS_VERSION(1,3)},
- {D3DSIO_TEXM3x2PAD, "texm3x2pad", "undefined", 2, pshader_texm3x2pad, NULL, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
- {D3DSIO_TEXM3x2TEX, "texm3x2tex", "undefined", 2, pshader_texm3x2tex, NULL, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
- {D3DSIO_TEXM3x3PAD, "texm3x3pad", "undefined", 2, pshader_texm3x3pad, NULL, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
+ {D3DSIO_TEXM3x2PAD, "texm3x2pad", "undefined", 2, pshader_texm3x2pad, pshader_hw_texm3x2pad, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
+ {D3DSIO_TEXM3x2TEX, "texm3x2tex", "undefined", 2, pshader_texm3x2tex, pshader_hw_texm3x2tex, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
+ {D3DSIO_TEXM3x3PAD, "texm3x3pad", "undefined", 2, pshader_texm3x3pad, pshader_hw_texm3x3pad, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
{D3DSIO_TEXM3x3DIFF, "texm3x3diff", GLNAME_REQUIRE_GLSL, 2, pshader_texm3x3diff, NULL, D3DPS_VERSION(0,0), D3DPS_VERSION(0,0)},
- {D3DSIO_TEXM3x3SPEC, "texm3x3spec", "undefined", 3, pshader_texm3x3spec, NULL, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
- {D3DSIO_TEXM3x3VSPEC, "texm3x3vspe", "undefined", 2, pshader_texm3x3vspec, NULL, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
- {D3DSIO_TEXM3x3TEX, "texm3x3tex", "undefined", 2, pshader_texm3x3tex, NULL, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
+ {D3DSIO_TEXM3x3SPEC, "texm3x3spec", "undefined", 3, pshader_texm3x3spec, pshader_hw_texm3x3spec, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
+ {D3DSIO_TEXM3x3VSPEC, "texm3x3vspe", "undefined", 2, pshader_texm3x3vspec, pshader_hw_texm3x3vspec, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
+ {D3DSIO_TEXM3x3TEX, "texm3x3tex", "undefined", 2, pshader_texm3x3tex, pshader_hw_texm3x3tex, D3DPS_VERSION(1,0), D3DPS_VERSION(1,3)},
{D3DSIO_TEXDP3TEX, "texdp3tex", GLNAME_REQUIRE_GLSL, 2, pshader_texdp3tex, NULL, D3DPS_VERSION(1,2), D3DPS_VERSION(1,3)},
{D3DSIO_TEXM3x2DEPTH, "texm3x2depth", GLNAME_REQUIRE_GLSL, 2, pshader_texm3x2depth, NULL, D3DPS_VERSION(1,3), D3DPS_VERSION(1,3)},
{D3DSIO_TEXDP3, "texdp3", GLNAME_REQUIRE_GLSL, 2, pshader_texdp3, NULL, D3DPS_VERSION(1,2), D3DPS_VERSION(1,3)},
@@ -1180,6 +1186,119 @@ void pshader_hw_def(SHADER_OPCODE_ARG* a
shader->constants[reg] = 1;
}
+
+void pshader_hw_texm3x2pad(SHADER_OPCODE_ARG* arg) {
+
+ IWineD3DPixelShaderImpl* shader = (IWineD3DPixelShaderImpl*) arg->shader;
+ DWORD reg = arg->dst & D3DSP_REGNUM_MASK;
+ SHADER_BUFFER* buffer = arg->buffer;
+ char tmpLine[256];
+ char buf[50];
+
+ if (gen_input_modifier_line(arg->src[0], 0, buf, tmpLine, shader->constants))
+ shader_addline(buffer, tmpLine);
+ shader_addline(buffer, "DP3 TMP.x, T%lu, %s;\n", reg, buf);
+}
+
+void pshader_hw_texm3x2tex(SHADER_OPCODE_ARG* arg) {
+
+ IWineD3DPixelShaderImpl* shader = (IWineD3DPixelShaderImpl*) arg->shader;
+ DWORD reg = arg->dst & D3DSP_REGNUM_MASK;
+ SHADER_BUFFER* buffer = arg->buffer;
+ char tmpLine[256];
+ char buf[50];
+
+ if (gen_input_modifier_line(arg->src[0], 0, buf, tmpLine, shader->constants))
+ shader_addline(buffer, tmpLine);
+ shader_addline(buffer, "DP3 TMP.y, T%lu, %s;\n", reg, buf);
+ shader_addline(buffer, "TEX T%lu, TMP, texture[%lu], 2D;\n", reg, reg);
+}
+
+void pshader_hw_texm3x3pad(SHADER_OPCODE_ARG* arg) {
+
+ IWineD3DPixelShaderImpl* shader = (IWineD3DPixelShaderImpl*) arg->shader;
+ DWORD reg = arg->dst & D3DSP_REGNUM_MASK;
+ SHADER_BUFFER* buffer = arg->buffer;
+ SHADER_PARSE_STATE current_state = shader->baseShader.parse_state;
+ char tmpLine[256];
+ char buf[50];
+
+ if (gen_input_modifier_line(arg->src[0], 0, buf, tmpLine, shader->constants))
+ shader_addline(buffer, tmpLine);
+ shader_addline(buffer, "DP3 TMP.%c, T%lu, %s;\n", 'x' + current_state.current_row, reg, buf);
+ current_state.texcoord_w[current_state.current_row++] = reg;
+}
+
+void pshader_hw_texm3x3tex(SHADER_OPCODE_ARG* arg) {
+
+ IWineD3DPixelShaderImpl* shader = (IWineD3DPixelShaderImpl*) arg->shader;
+ DWORD reg = arg->dst & D3DSP_REGNUM_MASK;
+ SHADER_BUFFER* buffer = arg->buffer;
+ SHADER_PARSE_STATE current_state = shader->baseShader.parse_state;
+ char tmpLine[256];
+ char buf[50];
+
+ if (gen_input_modifier_line(arg->src[0], 0, buf, tmpLine, shader->constants))
+ shader_addline(buffer, tmpLine);
+ shader_addline(buffer, "DP3 TMP.z, T%lu, %s;\n", reg, buf);
+
+ /* Cubemap textures will be more used than 3D ones. */
+ shader_addline(buffer, "TEX T%lu, TMP, texture[%lu], CUBE;\n", reg, reg);
+ current_state.current_row = 0;
+}
+
+void pshader_hw_texm3x3vspec(SHADER_OPCODE_ARG* arg) {
+
+ IWineD3DPixelShaderImpl* shader = (IWineD3DPixelShaderImpl*) arg->shader;
+ DWORD reg = arg->dst & D3DSP_REGNUM_MASK;
+ SHADER_BUFFER* buffer = arg->buffer;
+ SHADER_PARSE_STATE current_state = shader->baseShader.parse_state;
+ char tmpLine[256];
+ char buf[50];
+
+ if (gen_input_modifier_line(arg->src[0], 0, buf, tmpLine, shader->constants))
+ shader_addline(buffer, tmpLine);
+ shader_addline(buffer, "DP3 TMP.z, T%lu, %s;\n", reg, buf);
+
+ /* Construct the eye-ray vector from w coordinates */
+ shader_addline(buffer, "MOV TMP2.x, fragment.texcoord[%lu].w;\n", current_state.texcoord_w[0]);
+ shader_addline(buffer, "MOV TMP2.y, fragment.texcoord[%lu].w;\n", current_state.texcoord_w[1]);
+ shader_addline(buffer, "MOV TMP2.z, fragment.texcoord[%lu].w;\n", reg);
+
+ /* Calculate reflection vector (Assume normal is normalized): RF = 2*(N.E)*N -E */
+ shader_addline(buffer, "DP3 TMP.w, TMP, TMP2;\n");
+ shader_addline(buffer, "MUL TMP, TMP.w, TMP;\n");
+ shader_addline(buffer, "MAD TMP, coefmul.x, TMP, -TMP2;\n");
+
+ /* Cubemap textures will be more used than 3D ones. */
+ shader_addline(buffer, "TEX T%lu, TMP, texture[%lu], CUBE;\n", reg, reg);
+ current_state.current_row = 0;
+}
+
+void pshader_hw_texm3x3spec(SHADER_OPCODE_ARG* arg) {
+
+ IWineD3DPixelShaderImpl* shader = (IWineD3DPixelShaderImpl*) arg->shader;
+ DWORD reg = arg->dst & D3DSP_REGNUM_MASK;
+ DWORD reg3 = arg->src[1] & D3DSP_REGNUM_MASK;
+ SHADER_PARSE_STATE current_state = shader->baseShader.parse_state;
+ SHADER_BUFFER* buffer = arg->buffer;
+ char tmpLine[256];
+ char buf[50];
+
+ if (gen_input_modifier_line(arg->src[0], 0, buf, tmpLine, shader->constants))
+ shader_addline(buffer, tmpLine);
+ shader_addline(buffer, "DP3 TMP.z, T%lu, %s;\n", reg, buf);
+
+ /* Calculate reflection vector (Assume normal is normalized): RF = 2*(N.E)*N -E */
+ shader_addline(buffer, "DP3 TMP.w, TMP, C[%lu];\n", reg3);
+ shader_addline(buffer, "MUL TMP, TMP.w, TMP;\n");
+ shader_addline(buffer, "MAD TMP, coefmul.x, TMP, -C[%lu];\n", reg3);
+
+ /* Cubemap textures will be more used than 3D ones. */
+ shader_addline(buffer, "TEX T%lu, TMP, texture[%lu], CUBE;\n", reg, reg);
+ current_state.current_row = 0;
+}
+
/* NOTE: A description of how to parse tokens can be found at http://msdn.microsoft.com/library/default.asp?url=/library/en-us/graphics/hh/graphics/usermodedisplaydriver_shader_cc8e4e05-f5c3-4ec0-8853-8ce07c1551b2.xml.asp */
inline static VOID IWineD3DPixelShaderImpl_GenerateProgramArbHW(IWineD3DPixelShader *iface, CONST DWORD *pFunction) {
@@ -1187,15 +1306,14 @@ inline static VOID IWineD3DPixelShaderIm
const DWORD *pToken = pFunction;
const SHADER_OPCODE *curOpcode = NULL;
DWORD i;
- char tmpLine[255];
SHADER_BUFFER buffer;
- int row = 0; /* not sure, something to do with macros? */
- DWORD tcw[2];
-
/* Keep bitmaps of used temporary and texture registers */
DWORD tempsUsed, texUsed;
+ /* Initialize current parsing state */
+ This->baseShader.parse_state.current_row = 0;
+
#if 0 /* FIXME: Use the buffer that is held by the device, this is ok since fixups will be skipped for software shaders
it also requires entering a critical section but cuts down the runtime footprint of wined3d and any memory fragmentation that may occur... */
if (This->device->fixupVertexBufferSize < SHADER_PGMSIZE) {
@@ -1320,98 +1438,7 @@ inline static VOID IWineD3DPixelShaderIm
/* Build opcode for GL vertex_program */
switch (curOpcode->opcode) {
case D3DSIO_NOP:
- case D3DSIO_PHASE:
break;
- case D3DSIO_TEXM3x2PAD:
- {
- DWORD reg = *pToken & D3DSP_REGNUM_MASK;
- char buf[50];
- if (gen_input_modifier_line(*++pToken, 0, buf, tmpLine, This->constants))
- shader_addline(&buffer, tmpLine);
- shader_addline(&buffer, "DP3 TMP.x, T%lu, %s;\n", reg, buf);
- ++pToken;
- }
- break;
- case D3DSIO_TEXM3x2TEX:
- {
- DWORD reg = *pToken & D3DSP_REGNUM_MASK;
- char buf[50];
- if (gen_input_modifier_line(*++pToken, 0, buf, tmpLine, This->constants))
- shader_addline(&buffer, tmpLine);
- shader_addline(&buffer, "DP3 TMP.y, T%lu, %s;\n", reg, buf);
- shader_addline(&buffer, "TEX T%lu, TMP, texture[%lu], 2D;\n", reg, reg);
- ++pToken;
- }
- break;
- case D3DSIO_TEXM3x3PAD:
- {
- DWORD reg = *pToken & D3DSP_REGNUM_MASK;
- char buf[50];
- if (gen_input_modifier_line(*++pToken, 0, buf, tmpLine, This->constants))
- shader_addline(&buffer, tmpLine);
- shader_addline(&buffer, "DP3 TMP.%c, T%lu, %s;\n", 'x'+row, reg, buf);
- tcw[row++] = reg;
- ++pToken;
- }
- break;
- case D3DSIO_TEXM3x3TEX:
- {
- DWORD reg = *pToken & D3DSP_REGNUM_MASK;
- char buf[50];
- if (gen_input_modifier_line(*++pToken, 0, buf, tmpLine, This->constants))
- shader_addline(&buffer, tmpLine);
- shader_addline(&buffer, "DP3 TMP.z, T%lu, %s;\n", reg, buf);
-
- /* Cubemap textures will be more used than 3D ones. */
- shader_addline(&buffer, "TEX T%lu, TMP, texture[%lu], CUBE;\n", reg, reg);
- row = 0;
- ++pToken;
- }
- break;
- case D3DSIO_TEXM3x3VSPEC:
- {
- DWORD reg = *pToken & D3DSP_REGNUM_MASK;
- char buf[50];
- if (gen_input_modifier_line(*++pToken, 0, buf, tmpLine, This->constants))
- shader_addline(&buffer, tmpLine);
- shader_addline(&buffer, "DP3 TMP.z, T%lu, %s;\n", reg, buf);
-
- /* Construct the eye-ray vector from w coordinates */
- shader_addline(&buffer, "MOV TMP2.x, fragment.texcoord[%lu].w;\n", tcw[0]);
- shader_addline(&buffer, "MOV TMP2.y, fragment.texcoord[%lu].w;\n", tcw[1]);
- shader_addline(&buffer, "MOV TMP2.z, fragment.texcoord[%lu].w;\n", reg);
-
- /* Calculate reflection vector (Assume normal is normalized): RF = 2*(N.E)*N -E */
- shader_addline(&buffer, "DP3 TMP.w, TMP, TMP2;\n");
- shader_addline(&buffer, "MUL TMP, TMP.w, TMP;\n");
- shader_addline(&buffer, "MAD TMP, coefmul.x, TMP, -TMP2;\n");
-
- /* Cubemap textures will be more used than 3D ones. */
- shader_addline(&buffer, "TEX T%lu, TMP, texture[%lu], CUBE;\n", reg, reg);
- row = 0;
- ++pToken;
- }
- break;
- case D3DSIO_TEXM3x3SPEC:
- {
- DWORD reg = *pToken & D3DSP_REGNUM_MASK;
- DWORD reg3 = *(pToken + 2) & D3DSP_REGNUM_MASK;
- char buf[50];
- if (gen_input_modifier_line(*(pToken + 1), 0, buf, tmpLine, This->constants))
- shader_addline(&buffer, tmpLine);
- shader_addline(&buffer, "DP3 TMP.z, T%lu, %s;\n", reg, buf);
-
- /* Calculate reflection vector (Assume normal is normalized): RF = 2*(N.E)*N -E */
- shader_addline(&buffer, "DP3 TMP.w, TMP, C[%lu];\n", reg3);
- shader_addline(&buffer, "MUL TMP, TMP.w, TMP;\n");
- shader_addline(&buffer, "MAD TMP, coefmul.x, TMP, -C[%lu];\n", reg3);
-
- /* Cubemap textures will be more used than 3D ones. */
- shader_addline(&buffer, "TEX T%lu, TMP, texture[%lu], CUBE;\n", reg, reg);
- row = 0;
- pToken += 3;
- }
- break;
default:
FIXME("Can't handle opcode %s in hwShader\n", curOpcode->name);
diff --git a/dlls/wined3d/vertexshader.c b/dlls/wined3d/vertexshader.c
index 7b11d28..8a67a1a 100644
--- a/dlls/wined3d/vertexshader.c
+++ b/dlls/wined3d/vertexshader.c
@@ -1136,7 +1136,6 @@ inline static VOID IWineD3DVertexShaderI
const SHADER_OPCODE* curOpcode = NULL;
DWORD i;
SHADER_BUFFER buffer;
- char tmpLine[255];
DWORD addressUsed, tempsUsed;
#if 0 /* FIXME: Use the buffer that is held by the device, this is ok since fixups will be skipped for software shaders
@@ -1191,7 +1190,6 @@ inline static VOID IWineD3DVertexShaderI
if (NULL != pToken) {
while (1) {
- tmpLine[0] = 0;
if (D3DVS_END() == *pToken)
break;
diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h
index d02974a..31a8b83 100644
--- a/dlls/wined3d/wined3d_private.h
+++ b/dlls/wined3d/wined3d_private.h
@@ -1236,6 +1236,13 @@ typedef struct SHADER_LIMITS {
unsigned int address;
} SHADER_LIMITS;
+/** Keeps track of details for TEX_M#x# shader opcodes which need to
+ maintain state information between multiple codes */
+typedef struct SHADER_PARSE_STATE {
+ unsigned int current_row;
+ DWORD texcoord_w[2];
+} SHADER_PARSE_STATE;
+
/* Base Shader utility functions.
* (may move callers into the same file in the future) */
extern int shader_addline(
@@ -1254,6 +1261,7 @@ typedef struct IWineD3DBaseShaderClass
DWORD version;
DWORD hex_version;
SHADER_LIMITS limits;
+ SHADER_PARSE_STATE parse_state;
CONST SHADER_OPCODE *shader_ins;
CONST DWORD *function;
UINT functionLength;
--
1.1.3
More information about the wine-patches
mailing list