mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-07-23 14:19:46 -06:00
Shader Disk Cache implementation for D3D. Saves generated shaders on disk. Eliminates "freeze jerks" in D3D plugin the _second_ and later times you play something.... not much to do about the first time. The D3D shader compiler is just slow.
Also assorted cleanup around the shader code. git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@4869 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
@ -31,7 +31,7 @@ PIXELSHADERUID last_pixel_shader_uid;
|
||||
// a unique identifier, basically containing all the bits. Yup, it's a lot ....
|
||||
// It would likely be a lot more efficient to build this incrementally as the attributes
|
||||
// are set...
|
||||
void GetPixelShaderId(PIXELSHADERUID &uid, u32 texturemask, u32 dstAlphaEnable)
|
||||
void GetPixelShaderId(PIXELSHADERUID *uid, u32 texturemask, u32 dstAlphaEnable)
|
||||
{
|
||||
u32 projtexcoords = 0;
|
||||
for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; i++)
|
||||
@ -43,7 +43,7 @@ void GetPixelShaderId(PIXELSHADERUID &uid, u32 texturemask, u32 dstAlphaEnable)
|
||||
projtexcoords |= 1 << texcoord;
|
||||
}
|
||||
}
|
||||
uid.values[0] = (u32)bpmem.genMode.numtevstages |
|
||||
uid->values[0] = (u32)bpmem.genMode.numtevstages |
|
||||
((u32)bpmem.genMode.numindstages << 4) |
|
||||
((u32)bpmem.genMode.numtexgens << 7) |
|
||||
((u32)dstAlphaEnable << 11) |
|
||||
@ -51,21 +51,21 @@ void GetPixelShaderId(PIXELSHADERUID &uid, u32 texturemask, u32 dstAlphaEnable)
|
||||
(projtexcoords << 20) |
|
||||
((u32)bpmem.ztex2.op << 28);
|
||||
|
||||
uid.values[0] = (uid.values[0] & ~0x0ff00000) | (projtexcoords << 20);
|
||||
uid->values[0] = (uid->values[0] & ~0x0ff00000) | (projtexcoords << 20);
|
||||
// swap table
|
||||
for (int i = 0; i < 8; i += 2)
|
||||
((u8*)&uid.values[1])[i / 2] = (bpmem.tevksel[i].hex & 0xf) | ((bpmem.tevksel[i + 1].hex & 0xf) << 4);
|
||||
((u8*)&uid->values[1])[i / 2] = (bpmem.tevksel[i].hex & 0xf) | ((bpmem.tevksel[i + 1].hex & 0xf) << 4);
|
||||
|
||||
uid.values[2] = texturemask;
|
||||
uid->values[2] = texturemask;
|
||||
|
||||
u32 enableZTexture = (!bpmem.zcontrol.zcomploc && bpmem.zmode.testenable && bpmem.zmode.updateenable)?1:0;
|
||||
|
||||
uid.values[3] = (u32)bpmem.fog.c_proj_fsel.fsel |
|
||||
uid->values[3] = (u32)bpmem.fog.c_proj_fsel.fsel |
|
||||
((u32)bpmem.fog.c_proj_fsel.proj << 3) |
|
||||
((u32)enableZTexture << 4);
|
||||
|
||||
int hdr = 4;
|
||||
u32* pcurvalue = &uid.values[hdr];
|
||||
u32 *pcurvalue = &uid->values[hdr];
|
||||
for (u32 i = 0; i < (u32)bpmem.genMode.numtevstages + 1; ++i)
|
||||
{
|
||||
TevStageCombiner::ColorCombiner &cc = bpmem.combiners[i].colorC;
|
||||
@ -119,7 +119,7 @@ void GetPixelShaderId(PIXELSHADERUID &uid, u32 texturemask, u32 dstAlphaEnable)
|
||||
if ((bpmem.genMode.numtevstages % 3) != 2)
|
||||
++pcurvalue;
|
||||
|
||||
uid.tevstages = (u32)(pcurvalue - &uid.values[0] - hdr);
|
||||
uid->tevstages = (u32)(pcurvalue - &uid->values[0] - hdr);
|
||||
|
||||
for (u32 i = 0; i < bpmem.genMode.numindstages; ++i)
|
||||
{
|
||||
@ -134,7 +134,7 @@ void GetPixelShaderId(PIXELSHADERUID &uid, u32 texturemask, u32 dstAlphaEnable)
|
||||
}
|
||||
|
||||
// yeah, well ....
|
||||
uid.indstages = (u32)(pcurvalue - &uid.values[0] - (hdr - 1) - uid.tevstages);
|
||||
uid->indstages = (u32)(pcurvalue - &uid->values[0] - (hdr - 1) - uid->tevstages);
|
||||
}
|
||||
|
||||
// old tev->pixelshader notes
|
||||
@ -385,7 +385,7 @@ static void BuildSwapModeTable()
|
||||
}
|
||||
}
|
||||
|
||||
const char *GeneratePixelShader(u32 texture_mask, bool dstAlphaEnable, u32 HLSL)
|
||||
const char *GeneratePixelShaderCode(u32 texture_mask, bool dstAlphaEnable, u32 HLSL)
|
||||
{
|
||||
setlocale(LC_NUMERIC, "C"); // Reset locale for compilation
|
||||
text[sizeof(text) - 1] = 0x7C; // canary
|
||||
|
@ -42,6 +42,7 @@
|
||||
#define C_COLORMATRIX (C_FOG + 2)
|
||||
#define PIXELSHADERUID_MAX_VALUES (5 + 32 + 6 + 11)
|
||||
|
||||
// DO NOT make anything in this class virtual.
|
||||
class PIXELSHADERUID
|
||||
{
|
||||
public:
|
||||
@ -100,8 +101,9 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
const char *GeneratePixelShader(u32 texture_mask, bool dstAlphaEnable, u32 HLSL = 0);
|
||||
void GetPixelShaderId(PIXELSHADERUID &, u32 texturemask, u32 dstAlphaEnable);
|
||||
const char *GeneratePixelShaderCode(u32 texture_mask, bool dstAlphaEnable, u32 HLSL = 0);
|
||||
void GetPixelShaderId(PIXELSHADERUID *uid, u32 texturemask, u32 dstAlphaEnable);
|
||||
|
||||
extern PIXELSHADERUID last_pixel_shader_uid;
|
||||
|
||||
#endif // GCOGL_PIXELSHADER_H
|
||||
|
@ -25,7 +25,7 @@ namespace TextureConversionShader
|
||||
{
|
||||
u16 GetEncodedSampleCount(u32 format);
|
||||
|
||||
const char *GenerateEncodingShader(u32 format,bool HLSL = false);
|
||||
const char *GenerateEncodingShader(u32 format, bool HLSL = false);
|
||||
|
||||
void SetShaderParameters(float width, float height, float offsetX, float offsetY, float widthStride, float heightStride,float buffW = 0.0f,float buffH = 0.0f);
|
||||
|
||||
|
@ -29,27 +29,27 @@ VERTEXSHADERUID last_vertex_shader_uid;
|
||||
|
||||
// Mash together all the inputs that contribute to the code of a generated vertex shader into
|
||||
// a unique identifier, basically containing all the bits. Yup, it's a lot ....
|
||||
void GetVertexShaderId(VERTEXSHADERUID& vid, u32 components)
|
||||
void GetVertexShaderId(VERTEXSHADERUID *uid, u32 components)
|
||||
{
|
||||
vid.values[0] = components |
|
||||
uid->values[0] = components |
|
||||
(xfregs.numTexGens << 23) |
|
||||
(xfregs.nNumChans << 27) |
|
||||
((u32)xfregs.bEnableDualTexTransform << 29);
|
||||
|
||||
for (int i = 0; i < 2; ++i) {
|
||||
vid.values[1+i] = xfregs.colChans[i].color.enablelighting ?
|
||||
uid->values[1+i] = xfregs.colChans[i].color.enablelighting ?
|
||||
(u32)xfregs.colChans[i].color.hex :
|
||||
(u32)xfregs.colChans[i].color.matsource;
|
||||
vid.values[1+i] |= (xfregs.colChans[i].alpha.enablelighting ?
|
||||
uid->values[1+i] |= (xfregs.colChans[i].alpha.enablelighting ?
|
||||
(u32)xfregs.colChans[i].alpha.hex :
|
||||
(u32)xfregs.colChans[i].alpha.matsource) << 15;
|
||||
}
|
||||
|
||||
// fog
|
||||
vid.values[1] |= (((u32)bpmem.fog.c_proj_fsel.fsel & 3) << 30);
|
||||
vid.values[2] |= (((u32)bpmem.fog.c_proj_fsel.fsel >> 2) << 30);
|
||||
uid->values[1] |= (((u32)bpmem.fog.c_proj_fsel.fsel & 3) << 30);
|
||||
uid->values[2] |= (((u32)bpmem.fog.c_proj_fsel.fsel >> 2) << 30);
|
||||
|
||||
u32* pcurvalue = &vid.values[3];
|
||||
u32 *pcurvalue = &uid->values[3];
|
||||
for (int i = 0; i < xfregs.numTexGens; ++i) {
|
||||
TexMtxInfo tinfo = xfregs.texcoords[i].texmtxinfo;
|
||||
if (tinfo.texgentype != XF_TEXGEN_EMBOSS_MAP)
|
||||
@ -78,16 +78,16 @@ static char text[16384];
|
||||
|
||||
#define LIGHTS_POS ""
|
||||
|
||||
char *GenerateLightShader(char* p, int index, const LitChannel& chan, const char* dest, int coloralpha);
|
||||
char *GenerateLightShader(char *p, int index, const LitChannel& chan, const char *dest, int coloralpha);
|
||||
|
||||
const char *GenerateVertexShader(u32 components, bool D3D)
|
||||
const char *GenerateVertexShaderCode(u32 components, bool D3D)
|
||||
{
|
||||
setlocale(LC_NUMERIC, "C"); // Reset locale for compilation
|
||||
text[sizeof(text) - 1] = 0x7C; // canary
|
||||
DVSTARTPROFILE();
|
||||
|
||||
_assert_( bpmem.genMode.numtexgens == xfregs.numTexGens);
|
||||
_assert_( bpmem.genMode.numcolchans == xfregs.nNumChans);
|
||||
_assert_(bpmem.genMode.numtexgens == xfregs.numTexGens);
|
||||
_assert_(bpmem.genMode.numcolchans == xfregs.nNumChans);
|
||||
|
||||
u32 lightMask = 0;
|
||||
if (xfregs.nNumChans > 0)
|
||||
@ -125,9 +125,8 @@ const char *GenerateVertexShader(u32 components, bool D3D)
|
||||
WRITE(p, "};\n");
|
||||
|
||||
// uniforms
|
||||
// bool bTexMtx = ((components & VB_HAS_TEXMTXIDXALL)<<VB_HAS_UVTEXMTXSHIFT)!=0; unused TODO: keep?
|
||||
|
||||
WRITE(p, "uniform s_"I_TRANSFORMMATRICES" "I_TRANSFORMMATRICES" : register(c%d);\n", C_TRANSFORMMATRICES);
|
||||
WRITE(p, "uniform s_"I_TRANSFORMMATRICES" "I_TRANSFORMMATRICES" : register(c%d);\n", C_TRANSFORMMATRICES);
|
||||
WRITE(p, "uniform s_"I_TEXMATRICES" "I_TEXMATRICES" : register(c%d);\n", C_TEXMATRICES); // also using tex matrices
|
||||
WRITE(p, "uniform s_"I_NORMALMATRICES" "I_NORMALMATRICES" : register(c%d);\n", C_NORMALMATRICES);
|
||||
WRITE(p, "uniform s_"I_POSNORMALMATRIX" "I_POSNORMALMATRIX" : register(c%d);\n", C_POSNORMALMATRIX);
|
||||
@ -406,7 +405,7 @@ const char *GenerateVertexShader(u32 components, bool D3D)
|
||||
break;
|
||||
}
|
||||
|
||||
if(xfregs.bEnableDualTexTransform && texinfo.texgentype == XF_TEXGEN_REGULAR) { // only works for regular tex gen types?
|
||||
if (xfregs.bEnableDualTexTransform && texinfo.texgentype == XF_TEXGEN_REGULAR) { // only works for regular tex gen types?
|
||||
int postidx = xfregs.texcoords[i].postmtxinfo.index;
|
||||
WRITE(p, "float4 P0 = "I_POSTTRANSFORMMATRICES".T[%d].t;\n"
|
||||
"float4 P1 = "I_POSTTRANSFORMMATRICES".T[%d].t;\n"
|
||||
@ -461,7 +460,7 @@ const char *GenerateVertexShader(u32 components, bool D3D)
|
||||
}
|
||||
|
||||
// coloralpha - 1 if color, 2 if alpha
|
||||
char* GenerateLightShader(char* p, int index, const LitChannel& chan, const char* dest, int coloralpha)
|
||||
char *GenerateLightShader(char *p, int index, const LitChannel& chan, const char *dest, int coloralpha)
|
||||
{
|
||||
const char* swizzle = "xyzw";
|
||||
if (coloralpha == 1 ) swizzle = "xyz";
|
||||
|
@ -99,8 +99,10 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
const char *GenerateVertexShader(u32 components, bool D3D);
|
||||
void GetVertexShaderId(VERTEXSHADERUID& vid, u32 components);
|
||||
// components is included in the uid.
|
||||
const char *GenerateVertexShaderCode(u32 components, bool D3D);
|
||||
void GetVertexShaderId(VERTEXSHADERUID *uid, u32 components);
|
||||
|
||||
extern VERTEXSHADERUID last_vertex_shader_uid;
|
||||
|
||||
#endif // GCOGL_VERTEXSHADER_H
|
||||
|
Reference in New Issue
Block a user