summaryrefslogtreecommitdiff
path: root/Source
diff options
context:
space:
mode:
authordegasus <wickmarkus@web.de>2014-12-13 01:51:14 +0100
committerdegasus <wickmarkus@web.de>2014-12-21 14:12:43 +0100
commit809117102e1c8007345c48aba5eabfec9cff26ee (patch)
tree72b2e6ce801a0daf3e67e73faf44889a6ad8bfdc /Source
parenta71c8158d91c7ee0976b9b16eeba5ea3ac18ff99 (diff)
VideoCommon: split VertexLoaderBase from VertexLoader
Diffstat (limited to 'Source')
-rw-r--r--Source/Core/VideoBackends/OGL/Render.cpp1
-rw-r--r--Source/Core/VideoBackends/OGL/main.cpp1
-rw-r--r--Source/Core/VideoBackends/Software/NativeVertexFormat.h8
-rw-r--r--Source/Core/VideoBackends/Software/SWVertexLoader.cpp12
-rw-r--r--Source/Core/VideoBackends/Software/SWVertexLoader.h6
-rw-r--r--Source/Core/VideoCommon/BPStructs.cpp1
-rw-r--r--Source/Core/VideoCommon/CMakeLists.txt1
-rw-r--r--Source/Core/VideoCommon/CPMemory.h4
-rw-r--r--Source/Core/VideoCommon/NativeVertexFormat.h8
-rw-r--r--Source/Core/VideoCommon/VertexLoader.cpp112
-rw-r--r--Source/Core/VideoCommon/VertexLoader.h97
-rw-r--r--Source/Core/VideoCommon/VertexLoaderBase.cpp139
-rw-r--r--Source/Core/VideoCommon/VertexLoaderBase.h103
-rw-r--r--Source/Core/VideoCommon/VertexLoaderManager.cpp14
-rw-r--r--Source/Core/VideoCommon/VideoCommon.vcxproj2
-rw-r--r--Source/Core/VideoCommon/VideoCommon.vcxproj.filters6
-rw-r--r--Source/UnitTests/VideoCommon/VertexLoaderTest.cpp45
17 files changed, 309 insertions, 251 deletions
diff --git a/Source/Core/VideoBackends/OGL/Render.cpp b/Source/Core/VideoBackends/OGL/Render.cpp
index af344c344c..a03f8cd61d 100644
--- a/Source/Core/VideoBackends/OGL/Render.cpp
+++ b/Source/Core/VideoBackends/OGL/Render.cpp
@@ -43,7 +43,6 @@
#include "VideoCommon/OnScreenDisplay.h"
#include "VideoCommon/PixelEngine.h"
#include "VideoCommon/Statistics.h"
-#include "VideoCommon/VertexLoader.h"
#include "VideoCommon/VertexLoaderManager.h"
#include "VideoCommon/VertexShaderGen.h"
#include "VideoCommon/VertexShaderManager.h"
diff --git a/Source/Core/VideoBackends/OGL/main.cpp b/Source/Core/VideoBackends/OGL/main.cpp
index 8642d78cc1..6969b97ba4 100644
--- a/Source/Core/VideoBackends/OGL/main.cpp
+++ b/Source/Core/VideoBackends/OGL/main.cpp
@@ -74,7 +74,6 @@ Make AA apply instantly during gameplay if possible
#include "VideoCommon/OpcodeDecoding.h"
#include "VideoCommon/PixelEngine.h"
#include "VideoCommon/PixelShaderManager.h"
-#include "VideoCommon/VertexLoader.h"
#include "VideoCommon/VertexLoaderManager.h"
#include "VideoCommon/VertexShaderManager.h"
#include "VideoCommon/VideoConfig.h"
diff --git a/Source/Core/VideoBackends/Software/NativeVertexFormat.h b/Source/Core/VideoBackends/Software/NativeVertexFormat.h
index ad71e2caf9..c4f140cac4 100644
--- a/Source/Core/VideoBackends/Software/NativeVertexFormat.h
+++ b/Source/Core/VideoBackends/Software/NativeVertexFormat.h
@@ -7,14 +7,6 @@
#include "Common/ChunkFile.h"
#include "VideoBackends/Software/Vec3.h"
-#ifdef WIN32
-#define LOADERDECL __cdecl
-#else
-#define LOADERDECL
-#endif
-
-typedef void (LOADERDECL *TPipelineFunction)();
-
struct Vec4
{
float x;
diff --git a/Source/Core/VideoBackends/Software/SWVertexLoader.cpp b/Source/Core/VideoBackends/Software/SWVertexLoader.cpp
index fecfb94abe..2523b5b01a 100644
--- a/Source/Core/VideoBackends/Software/SWVertexLoader.cpp
+++ b/Source/Core/VideoBackends/Software/SWVertexLoader.cpp
@@ -13,12 +13,8 @@
#include "VideoBackends/Software/TransformUnit.h"
#include "VideoBackends/Software/XFMemLoader.h"
-#include "VideoCommon/VertexLoader.h"
-#include "VideoCommon/VertexLoader_Color.h"
-#include "VideoCommon/VertexLoader_Normal.h"
-#include "VideoCommon/VertexLoader_Position.h"
-#include "VideoCommon/VertexLoader_TextCoord.h"
-#include "VideoCommon/VertexManagerBase.h"
+#include "VideoCommon/VertexLoaderBase.h"
+#include "VideoCommon/VertexLoaderUtils.h"
SWVertexLoader::SWVertexLoader() :
m_VertexSize(0)
@@ -42,8 +38,8 @@ void SWVertexLoader::SetFormat(u8 attributeIndex, u8 primitiveType)
if (!m_CurrentLoader)
{
- m_CurrentLoader = new VertexLoader(g_main_cp_state.vtx_desc, g_main_cp_state.vtx_attr[m_attributeIndex]);
- m_VertexLoaderMap[uid] = std::unique_ptr<VertexLoader>(m_CurrentLoader);
+ m_CurrentLoader = VertexLoaderBase::CreateVertexLoader(g_main_cp_state.vtx_desc, g_main_cp_state.vtx_attr[m_attributeIndex]);
+ m_VertexLoaderMap[uid] = std::unique_ptr<VertexLoaderBase>(m_CurrentLoader);
}
m_VertexSize = m_CurrentLoader->m_VertexSize;
diff --git a/Source/Core/VideoBackends/Software/SWVertexLoader.h b/Source/Core/VideoBackends/Software/SWVertexLoader.h
index fe4e5347ba..890d1fa52d 100644
--- a/Source/Core/VideoBackends/Software/SWVertexLoader.h
+++ b/Source/Core/VideoBackends/Software/SWVertexLoader.h
@@ -9,7 +9,7 @@
#include "VideoBackends/Software/CPMemLoader.h"
#include "VideoBackends/Software/NativeVertexFormat.h"
-#include "VideoCommon/VertexLoader.h"
+#include "VideoCommon/VertexLoaderBase.h"
class PointerWrap;
class SetupUnit;
@@ -28,9 +28,9 @@ class SWVertexLoader
bool m_TexGenSpecialCase;
- std::unordered_map<VertexLoaderUID, std::unique_ptr<VertexLoader>> m_VertexLoaderMap;
+ std::unordered_map<VertexLoaderUID, std::unique_ptr<VertexLoaderBase>> m_VertexLoaderMap;
std::vector<u8> m_LoadedVertices;
- VertexLoader* m_CurrentLoader;
+ VertexLoaderBase* m_CurrentLoader;
u8 m_attributeIndex;
u8 m_primitiveType;
diff --git a/Source/Core/VideoCommon/BPStructs.cpp b/Source/Core/VideoCommon/BPStructs.cpp
index 6c4ad70331..44f6964cfb 100644
--- a/Source/Core/VideoCommon/BPStructs.cpp
+++ b/Source/Core/VideoCommon/BPStructs.cpp
@@ -21,7 +21,6 @@
#include "VideoCommon/RenderBase.h"
#include "VideoCommon/Statistics.h"
#include "VideoCommon/TextureDecoder.h"
-#include "VideoCommon/VertexLoader.h"
#include "VideoCommon/VertexShaderManager.h"
#include "VideoCommon/VideoCommon.h"
#include "VideoCommon/VideoConfig.h"
diff --git a/Source/Core/VideoCommon/CMakeLists.txt b/Source/Core/VideoCommon/CMakeLists.txt
index 95ebaf7433..a450a8e379 100644
--- a/Source/Core/VideoCommon/CMakeLists.txt
+++ b/Source/Core/VideoCommon/CMakeLists.txt
@@ -28,6 +28,7 @@ set(SRCS BoundingBox.cpp
TextureConversionShader.cpp
TextureDecoder_Common.cpp
VertexLoader.cpp
+ VertexLoaderBase.cpp
VertexLoaderManager.cpp
VertexLoader_Color.cpp
VertexLoader_Normal.cpp
diff --git a/Source/Core/VideoCommon/CPMemory.h b/Source/Core/VideoCommon/CPMemory.h
index d61fbb02c4..e348f7f38d 100644
--- a/Source/Core/VideoCommon/CPMemory.h
+++ b/Source/Core/VideoCommon/CPMemory.h
@@ -232,7 +232,7 @@ struct VAT
UVAT_group2 g2;
};
-class VertexLoader;
+class VertexLoaderBase;
// STATE_TO_SAVE
struct CPState final
@@ -247,7 +247,7 @@ struct CPState final
// Attributes that actually belong to VertexLoaderManager:
BitSet32 attr_dirty;
- VertexLoader* vertex_loaders[8];
+ VertexLoaderBase* vertex_loaders[8];
};
class PointerWrap;
diff --git a/Source/Core/VideoCommon/NativeVertexFormat.h b/Source/Core/VideoCommon/NativeVertexFormat.h
index 612f671f5d..024f4f070d 100644
--- a/Source/Core/VideoCommon/NativeVertexFormat.h
+++ b/Source/Core/VideoCommon/NativeVertexFormat.h
@@ -44,14 +44,6 @@ enum
VB_HAS_UVTEXMTXSHIFT=13,
};
-#ifdef WIN32
-#define LOADERDECL __cdecl
-#else
-#define LOADERDECL
-#endif
-
-typedef void (LOADERDECL *TPipelineFunction)();
-
enum VarType
{
VAR_UNSIGNED_BYTE, // GX_U8 = 0
diff --git a/Source/Core/VideoCommon/VertexLoader.cpp b/Source/Core/VideoCommon/VertexLoader.cpp
index ddf5097986..32cb95607b 100644
--- a/Source/Core/VideoCommon/VertexLoader.cpp
+++ b/Source/Core/VideoCommon/VertexLoader.cpp
@@ -4,7 +4,6 @@
#include "Common/CommonTypes.h"
#include "Common/MemoryUtil.h"
-#include "Common/StringUtil.h"
#include "Common/x64ABI.h"
#include "Common/x64Emitter.h"
@@ -109,19 +108,13 @@ static void LOADERDECL TexMtx_Write_Float4()
}
VertexLoader::VertexLoader(const TVtxDesc &vtx_desc, const VAT &vtx_attr)
+: VertexLoaderBase(vtx_desc, vtx_attr)
{
m_compiledCode = nullptr;
- m_numLoadedVertices = 0;
- m_VertexSize = 0;
- m_native_vertex_format = nullptr;
VertexLoader_Normal::Init();
VertexLoader_Position::Init();
VertexLoader_TextCoord::Init();
- m_VtxDesc = vtx_desc;
- m_vat = vtx_attr;
- SetVAT(vtx_attr);
-
#ifdef USE_VERTEX_LOADER_JIT
AllocCodeSpace(COMPILED_CODE_SIZE);
CompileVertexTranslator();
@@ -130,7 +123,6 @@ VertexLoader::VertexLoader(const TVtxDesc &vtx_desc, const VAT &vtx_attr)
m_numPipelineStages = 0;
CompileVertexTranslator();
#endif
-
}
VertexLoader::~VertexLoader()
@@ -489,105 +481,3 @@ int VertexLoader::RunVertices(int primitive, int count, DataReader src, DataRead
ConvertVertices(count);
return count;
}
-
-void VertexLoader::SetVAT(const VAT& vat)
-{
- m_VtxAttr.PosElements = vat.g0.PosElements;
- m_VtxAttr.PosFormat = vat.g0.PosFormat;
- m_VtxAttr.PosFrac = vat.g0.PosFrac;
- m_VtxAttr.NormalElements = vat.g0.NormalElements;
- m_VtxAttr.NormalFormat = vat.g0.NormalFormat;
- m_VtxAttr.color[0].Elements = vat.g0.Color0Elements;
- m_VtxAttr.color[0].Comp = vat.g0.Color0Comp;
- m_VtxAttr.color[1].Elements = vat.g0.Color1Elements;
- m_VtxAttr.color[1].Comp = vat.g0.Color1Comp;
- m_VtxAttr.texCoord[0].Elements = vat.g0.Tex0CoordElements;
- m_VtxAttr.texCoord[0].Format = vat.g0.Tex0CoordFormat;
- m_VtxAttr.texCoord[0].Frac = vat.g0.Tex0Frac;
- m_VtxAttr.ByteDequant = vat.g0.ByteDequant;
- m_VtxAttr.NormalIndex3 = vat.g0.NormalIndex3;
-
- m_VtxAttr.texCoord[1].Elements = vat.g1.Tex1CoordElements;
- m_VtxAttr.texCoord[1].Format = vat.g1.Tex1CoordFormat;
- m_VtxAttr.texCoord[1].Frac = vat.g1.Tex1Frac;
- m_VtxAttr.texCoord[2].Elements = vat.g1.Tex2CoordElements;
- m_VtxAttr.texCoord[2].Format = vat.g1.Tex2CoordFormat;
- m_VtxAttr.texCoord[2].Frac = vat.g1.Tex2Frac;
- m_VtxAttr.texCoord[3].Elements = vat.g1.Tex3CoordElements;
- m_VtxAttr.texCoord[3].Format = vat.g1.Tex3CoordFormat;
- m_VtxAttr.texCoord[3].Frac = vat.g1.Tex3Frac;
- m_VtxAttr.texCoord[4].Elements = vat.g1.Tex4CoordElements;
- m_VtxAttr.texCoord[4].Format = vat.g1.Tex4CoordFormat;
-
- m_VtxAttr.texCoord[4].Frac = vat.g2.Tex4Frac;
- m_VtxAttr.texCoord[5].Elements = vat.g2.Tex5CoordElements;
- m_VtxAttr.texCoord[5].Format = vat.g2.Tex5CoordFormat;
- m_VtxAttr.texCoord[5].Frac = vat.g2.Tex5Frac;
- m_VtxAttr.texCoord[6].Elements = vat.g2.Tex6CoordElements;
- m_VtxAttr.texCoord[6].Format = vat.g2.Tex6CoordFormat;
- m_VtxAttr.texCoord[6].Frac = vat.g2.Tex6Frac;
- m_VtxAttr.texCoord[7].Elements = vat.g2.Tex7CoordElements;
- m_VtxAttr.texCoord[7].Format = vat.g2.Tex7CoordFormat;
- m_VtxAttr.texCoord[7].Frac = vat.g2.Tex7Frac;
-
- if (!m_VtxAttr.ByteDequant)
- {
- ERROR_LOG(VIDEO, "ByteDequant is set to zero");
- }
-};
-
-void VertexLoader::AppendToString(std::string *dest) const
-{
- dest->reserve(250);
- static const char *posMode[4] = {
- "Inv",
- "Dir",
- "I8",
- "I16",
- };
- static const char *posFormats[5] = {
- "u8", "s8", "u16", "s16", "flt",
- };
- static const char *colorFormat[8] = {
- "565",
- "888",
- "888x",
- "4444",
- "6666",
- "8888",
- "Inv",
- "Inv",
- };
-
- dest->append(StringFromFormat("%ib skin: %i P: %i %s-%s ",
- m_VertexSize, (u32)m_VtxDesc.PosMatIdx,
- m_VtxAttr.PosElements ? 3 : 2, posMode[m_VtxDesc.Position], posFormats[m_VtxAttr.PosFormat]));
-
- if (m_VtxDesc.Normal)
- {
- dest->append(StringFromFormat("Nrm: %i %s-%s ",
- m_VtxAttr.NormalElements, posMode[m_VtxDesc.Normal], posFormats[m_VtxAttr.NormalFormat]));
- }
-
- u64 color_mode[2] = {m_VtxDesc.Color0, m_VtxDesc.Color1};
- for (int i = 0; i < 2; i++)
- {
- if (color_mode[i])
- {
- dest->append(StringFromFormat("C%i: %i %s-%s ", i, m_VtxAttr.color[i].Elements, posMode[color_mode[i]], colorFormat[m_VtxAttr.color[i].Comp]));
- }
- }
- u64 tex_mode[8] = {
- m_VtxDesc.Tex0Coord, m_VtxDesc.Tex1Coord, m_VtxDesc.Tex2Coord, m_VtxDesc.Tex3Coord,
- m_VtxDesc.Tex4Coord, m_VtxDesc.Tex5Coord, m_VtxDesc.Tex6Coord, m_VtxDesc.Tex7Coord
- };
- for (int i = 0; i < 8; i++)
- {
- if (tex_mode[i])
- {
- dest->append(StringFromFormat("T%i: %i %s-%s ",
- i, m_VtxAttr.texCoord[i].Elements, posMode[tex_mode[i]], posFormats[m_VtxAttr.texCoord[i].Format]));
- }
- }
- dest->append(StringFromFormat(" - %i v\n", m_numLoadedVertices));
-}
diff --git a/Source/Core/VideoCommon/VertexLoader.h b/Source/Core/VideoCommon/VertexLoader.h
index 0e1f60792a..0d886735ca 100644
--- a/Source/Core/VideoCommon/VertexLoader.h
+++ b/Source/Core/VideoCommon/VertexLoader.h
@@ -16,6 +16,7 @@
#include "VideoCommon/CPMemory.h"
#include "VideoCommon/DataReader.h"
#include "VideoCommon/NativeVertexFormat.h"
+#include "VideoCommon/VertexLoaderBase.h"
#include "VideoCommon/VertexLoaderUtils.h"
#if _M_SSE >= 0x401
@@ -29,6 +30,14 @@
#define USE_VERTEX_LOADER_JIT
#endif
+#ifdef WIN32
+#define LOADERDECL __cdecl
+#else
+#define LOADERDECL
+#endif
+
+typedef void (LOADERDECL *TPipelineFunction)();
+
// They are used for the communication with the loader functions
extern int tcIndex;
extern int colIndex;
@@ -36,105 +45,31 @@ extern int colElements[2];
GC_ALIGNED128(extern float posScale[4]);
GC_ALIGNED64(extern float tcScale[8][2]);
-class VertexLoaderUID
-{
- u32 vid[5];
- size_t hash;
-public:
- VertexLoaderUID()
- {
- }
-
- VertexLoaderUID(const TVtxDesc& vtx_desc, const VAT& vat)
- {
- vid[0] = vtx_desc.Hex & 0xFFFFFFFF;
- vid[1] = vtx_desc.Hex >> 32;
- vid[2] = vat.g0.Hex;
- vid[3] = vat.g1.Hex;
- vid[4] = vat.g2.Hex;
- hash = CalculateHash();
- }
-
- bool operator == (const VertexLoaderUID& rh) const
- {
- return hash == rh.hash && std::equal(vid, vid + sizeof(vid) / sizeof(vid[0]), rh.vid);
- }
-
- size_t GetHash() const
- {
- return hash;
- }
-
-private:
-
- size_t CalculateHash()
- {
- size_t h = -1;
-
- for (auto word : vid)
- {
- h = h * 137 + word;
- }
-
- return h;
- }
-};
-
-namespace std
-{
-template <> struct hash<VertexLoaderUID>
-{
- size_t operator()(const VertexLoaderUID& uid) const
- {
- return uid.GetHash();
- }
-};
-}
-
// ARMTODO: This should be done in a better way
#ifndef _M_GENERIC
-class VertexLoader : public Gen::X64CodeBlock
+class VertexLoader : public Gen::X64CodeBlock, public VertexLoaderBase
#else
-class VertexLoader
+class VertexLoader : public VertexLoaderBase
#endif
{
public:
VertexLoader(const TVtxDesc &vtx_desc, const VAT &vtx_attr);
~VertexLoader();
- void SetupRunVertices(int primitive, int const count);
- int RunVertices(int primitive, int count, DataReader src, DataReader dst);
-
- // For debugging / profiling
- void AppendToString(std::string *dest) const;
-
- // per loader public state
- int m_VertexSize; // number of bytes of a raw GC vertex
- PortableVertexDeclaration m_native_vtx_decl;
- u32 m_native_components;
-
- // used by VertexLoaderManager
- NativeVertexFormat* m_native_vertex_format;
- int m_numLoadedVertices;
+ int RunVertices(int primitive, int count, DataReader src, DataReader dst) override;
+ std::string GetName() const override { return "OldLoader"; }
+ bool IsInitialized() override { return true; } // This vertex loader supports all formats
private:
- // GC vertex format
- TVtxAttr m_VtxAttr; // VAT decoded into easy format
- TVtxDesc m_VtxDesc; // Not really used currently - or well it is, but could be easily avoided.
- VAT m_vat;
-
#ifndef USE_VERTEX_LOADER_JIT
// Pipeline.
TPipelineFunction m_PipelineStages[64]; // TODO - figure out real max. it's lower.
int m_numPipelineStages;
#endif
- const u8 *m_compiledCode;
-
- void SetVAT(const VAT& vat);
-
void CompileVertexTranslator();
void ConvertVertices(int count);
+ void SetupRunVertices(int primitive, int const count);
void WriteCall(TPipelineFunction);
@@ -142,6 +77,8 @@ private:
void WriteGetVariable(int bits, Gen::OpArg dest, void *address);
void WriteSetVariable(int bits, void *address, Gen::OpArg dest);
#endif
+
+ const u8 *m_compiledCode;
};
#if _M_SSE >= 0x301
diff --git a/Source/Core/VideoCommon/VertexLoaderBase.cpp b/Source/Core/VideoCommon/VertexLoaderBase.cpp
new file mode 100644
index 0000000000..4372729506
--- /dev/null
+++ b/Source/Core/VideoCommon/VertexLoaderBase.cpp
@@ -0,0 +1,139 @@
+// Copyright 2014 Dolphin Emulator Project
+// Licensed under GPLv2
+// Refer to the license.txt file included.
+
+#include "Common/StringUtil.h"
+
+#include "VideoCommon/VertexLoader.h"
+#include "VideoCommon/VertexLoaderBase.h"
+
+VertexLoaderBase::VertexLoaderBase(const TVtxDesc &vtx_desc, const VAT &vtx_attr)
+{
+ m_numLoadedVertices = 0;
+ m_VertexSize = 0;
+ m_native_vertex_format = nullptr;
+
+ SetVAT(vtx_attr);
+ m_VtxDesc = vtx_desc;
+ m_vat = vtx_attr;
+}
+
+void VertexLoaderBase::SetVAT(const VAT& vat)
+{
+ m_VtxAttr.PosElements = vat.g0.PosElements;
+ m_VtxAttr.PosFormat = vat.g0.PosFormat;
+ m_VtxAttr.PosFrac = vat.g0.PosFrac;
+ m_VtxAttr.NormalElements = vat.g0.NormalElements;
+ m_VtxAttr.NormalFormat = vat.g0.NormalFormat;
+ m_VtxAttr.color[0].Elements = vat.g0.Color0Elements;
+ m_VtxAttr.color[0].Comp = vat.g0.Color0Comp;
+ m_VtxAttr.color[1].Elements = vat.g0.Color1Elements;
+ m_VtxAttr.color[1].Comp = vat.g0.Color1Comp;
+ m_VtxAttr.texCoord[0].Elements = vat.g0.Tex0CoordElements;
+ m_VtxAttr.texCoord[0].Format = vat.g0.Tex0CoordFormat;
+ m_VtxAttr.texCoord[0].Frac = vat.g0.Tex0Frac;
+ m_VtxAttr.ByteDequant = vat.g0.ByteDequant;
+ m_VtxAttr.NormalIndex3 = vat.g0.NormalIndex3;
+
+ m_VtxAttr.texCoord[1].Elements = vat.g1.Tex1CoordElements;
+ m_VtxAttr.texCoord[1].Format = vat.g1.Tex1CoordFormat;
+ m_VtxAttr.texCoord[1].Frac = vat.g1.Tex1Frac;
+ m_VtxAttr.texCoord[2].Elements = vat.g1.Tex2CoordElements;
+ m_VtxAttr.texCoord[2].Format = vat.g1.Tex2CoordFormat;
+ m_VtxAttr.texCoord[2].Frac = vat.g1.Tex2Frac;
+ m_VtxAttr.texCoord[3].Elements = vat.g1.Tex3CoordElements;
+ m_VtxAttr.texCoord[3].Format = vat.g1.Tex3CoordFormat;
+ m_VtxAttr.texCoord[3].Frac = vat.g1.Tex3Frac;
+ m_VtxAttr.texCoord[4].Elements = vat.g1.Tex4CoordElements;
+ m_VtxAttr.texCoord[4].Format = vat.g1.Tex4CoordFormat;
+
+ m_VtxAttr.texCoord[4].Frac = vat.g2.Tex4Frac;
+ m_VtxAttr.texCoord[5].Elements = vat.g2.Tex5CoordElements;
+ m_VtxAttr.texCoord[5].Format = vat.g2.Tex5CoordFormat;
+ m_VtxAttr.texCoord[5].Frac = vat.g2.Tex5Frac;
+ m_VtxAttr.texCoord[6].Elements = vat.g2.Tex6CoordElements;
+ m_VtxAttr.texCoord[6].Format = vat.g2.Tex6CoordFormat;
+ m_VtxAttr.texCoord[6].Frac = vat.g2.Tex6Frac;
+ m_VtxAttr.texCoord[7].Elements = vat.g2.Tex7CoordElements;
+ m_VtxAttr.texCoord[7].Format = vat.g2.Tex7CoordFormat;
+ m_VtxAttr.texCoord[7].Frac = vat.g2.Tex7Frac;
+
+ if (!m_VtxAttr.ByteDequant)
+ {
+ ERROR_LOG(VIDEO, "ByteDequant is set to zero");
+ }
+};
+
+void VertexLoaderBase::AppendToString(std::string *dest) const
+{
+ dest->reserve(250);
+
+ dest->append(GetName());
+ dest->append(": ");
+
+ static const char *posMode[4] = {
+ "Inv",
+ "Dir",
+ "I8",
+ "I16",
+ };
+ static const char *posFormats[5] = {
+ "u8", "s8", "u16", "s16", "flt",
+ };
+ static const char *colorFormat[8] = {
+ "565",
+ "888",
+ "888x",
+ "4444",
+ "6666",
+ "8888",
+ "Inv",
+ "Inv",
+ };
+
+ dest->append(StringFromFormat("%ib skin: %i P: %i %s-%s ",
+ m_VertexSize, (u32)m_VtxDesc.PosMatIdx,
+ m_VtxAttr.PosElements ? 3 : 2, posMode[m_VtxDesc.Position], posFormats[m_VtxAttr.PosFormat]));
+
+ if (m_VtxDesc.Normal)
+ {
+ dest->append(StringFromFormat("Nrm: %i %s-%s ",
+ m_VtxAttr.NormalElements, posMode[m_VtxDesc.Normal], posFormats[m_VtxAttr.NormalFormat]));
+ }
+
+ u64 color_mode[2] = {m_VtxDesc.Color0, m_VtxDesc.Color1};
+ for (int i = 0; i < 2; i++)
+ {
+ if (color_mode[i])
+ {
+ dest->append(StringFromFormat("C%i: %i %s-%s ", i, m_VtxAttr.color[i].Elements, posMode[color_mode[i]], colorFormat[m_VtxAttr.color[i].Comp]));
+ }
+ }
+ u64 tex_mode[8] = {
+ m_VtxDesc.Tex0Coord, m_VtxDesc.Tex1Coord, m_VtxDesc.Tex2Coord, m_VtxDesc.Tex3Coord,
+ m_VtxDesc.Tex4Coord, m_VtxDesc.Tex5Coord, m_VtxDesc.Tex6Coord, m_VtxDesc.Tex7Coord
+ };
+ for (int i = 0; i < 8; i++)
+ {
+ if (tex_mode[i])
+ {
+ dest->append(StringFromFormat("T%i: %i %s-%s ",
+ i, m_VtxAttr.texCoord[i].Elements, posMode[tex_mode[i]], posFormats[m_VtxAttr.texCoord[i].Format]));
+ }
+ }
+ dest->append(StringFromFormat(" - %i v\n", m_numLoadedVertices));
+}
+
+VertexLoaderBase* VertexLoaderBase::CreateVertexLoader(const TVtxDesc& vtx_desc, const VAT& vtx_attr)
+{
+ VertexLoaderBase* loader;
+
+ // last try: The old VertexLoader
+ loader = new VertexLoader(vtx_desc, vtx_attr);
+ if (loader->IsInitialized())
+ return loader;
+ delete loader;
+
+ PanicAlert("No Vertex Loader found.");
+ return nullptr;
+}
diff --git a/Source/Core/VideoCommon/VertexLoaderBase.h b/Source/Core/VideoCommon/VertexLoaderBase.h
new file mode 100644
index 0000000000..7da2d866f9
--- /dev/null
+++ b/Source/Core/VideoCommon/VertexLoaderBase.h
@@ -0,0 +1,103 @@
+// Copyright 2014 Dolphin Emulator Project
+// Licensed under GPLv2
+// Refer to the license.txt file included.
+
+#pragma once
+
+#include <array>
+#include <string>
+
+#include "Common/CommonTypes.h"
+
+#include "VideoCommon/CPMemory.h"
+#include "VideoCommon/DataReader.h"
+#include "VideoCommon/NativeVertexFormat.h"
+
+class VertexLoaderUID
+{
+ std::array<u32, 5> vid;
+ size_t hash;
+public:
+ VertexLoaderUID()
+ {
+ }
+
+ VertexLoaderUID(const TVtxDesc& vtx_desc, const VAT& vat)
+ {
+ vid[0] = vtx_desc.Hex & 0xFFFFFFFF;
+ vid[1] = vtx_desc.Hex >> 32;
+ vid[2] = vat.g0.Hex;
+ vid[3] = vat.g1.Hex;
+ vid[4] = vat.g2.Hex;
+ hash = CalculateHash();
+ }
+
+ bool operator == (const VertexLoaderUID& rh) const
+ {
+ return vid == rh.vid;
+ }
+
+ size_t GetHash() const
+ {
+ return hash;
+ }
+
+private:
+
+ size_t CalculateHash() const
+ {
+ size_t h = -1;
+
+ for (auto word : vid)
+ {
+ h = h * 137 + word;
+ }
+
+ return h;
+ }
+};
+
+namespace std
+{
+template <> struct hash<VertexLoaderUID>
+{
+ size_t operator()(const VertexLoaderUID& uid) const
+ {
+ return uid.GetHash();
+ }
+};
+}
+
+class VertexLoaderBase
+{
+public:
+ static VertexLoaderBase* CreateVertexLoader(const TVtxDesc &vtx_desc, const VAT &vtx_attr);
+ virtual ~VertexLoaderBase() {};
+
+ virtual int RunVertices(int primitive, int count, DataReader src, DataReader dst) = 0;
+
+ virtual bool IsInitialized() = 0;
+
+ // For debugging / profiling
+ void AppendToString(std::string *dest) const;
+
+ virtual std::string GetName() const = 0;
+
+ // per loader public state
+ int m_VertexSize; // number of bytes of a raw GC vertex
+ PortableVertexDeclaration m_native_vtx_decl;
+ u32 m_native_components;
+
+ // used by VertexLoaderManager
+ NativeVertexFormat* m_native_vertex_format;
+ int m_numLoadedVertices;
+
+protected:
+ VertexLoaderBase(const TVtxDesc &vtx_desc, const VAT &vtx_attr);
+ void SetVAT(const VAT& vat);
+
+ // GC vertex format
+ TVtxAttr m_VtxAttr; // VAT decoded into easy format
+ TVtxDesc m_VtxDesc; // Not really used currently - or well it is, but could be easily avoided.
+ VAT m_vat;
+};
diff --git a/Source/Core/VideoCommon/VertexLoaderManager.cpp b/Source/Core/VideoCommon/VertexLoaderManager.cpp
index 98f92e3d10..0ab87b323d 100644
--- a/Source/Core/VideoCommon/VertexLoaderManager.cpp
+++ b/Source/Core/VideoCommon/VertexLoaderManager.cpp
@@ -15,7 +15,7 @@
#include "VideoCommon/BPMemory.h"
#include "VideoCommon/IndexGenerator.h"
#include "VideoCommon/Statistics.h"
-#include "VideoCommon/VertexLoader.h"
+#include "VideoCommon/VertexLoaderBase.h"
#include "VideoCommon/VertexLoaderManager.h"
#include "VideoCommon/VertexManagerBase.h"
#include "VideoCommon/VertexShaderManager.h"
@@ -30,7 +30,7 @@ typedef std::unordered_map<PortableVertexDeclaration, std::unique_ptr<NativeVert
static NativeVertexFormatMap s_native_vertex_map;
static NativeVertexFormat* s_current_vtx_fmt;
-typedef std::unordered_map<VertexLoaderUID, std::unique_ptr<VertexLoader>> VertexLoaderMap;
+typedef std::unordered_map<VertexLoaderUID, std::unique_ptr<VertexLoaderBase>> VertexLoaderMap;
static std::mutex s_vertex_loader_map_lock;
static VertexLoaderMap s_vertex_loader_map;
// TODO - change into array of pointers. Keep a map of all seen so far.
@@ -93,9 +93,9 @@ void MarkAllDirty()
g_preprocess_cp_state.attr_dirty = BitSet32::AllTrue(8);
}
-static VertexLoader* RefreshLoader(int vtx_attr_group, CPState* state)
+static VertexLoaderBase* RefreshLoader(int vtx_attr_group, CPState* state)
{
- VertexLoader* loader;
+ VertexLoaderBase* loader;
if (state->attr_dirty[vtx_attr_group])
{
VertexLoaderUID uid(state->vtx_desc, state->vtx_attr[vtx_attr_group]);
@@ -107,8 +107,8 @@ static VertexLoader* RefreshLoader(int vtx_attr_group, CPState* state)
}
else
{
- loader = new VertexLoader(state->vtx_desc, state->vtx_attr[vtx_attr_group]);
- s_vertex_loader_map[uid] = std::unique_ptr<VertexLoader>(loader);
+ loader = VertexLoaderBase::CreateVertexLoader(state->vtx_desc, state->vtx_attr[vtx_attr_group]);
+ s_vertex_loader_map[uid] = std::unique_ptr<VertexLoaderBase>(loader);
// search for a cached native vertex format
const PortableVertexDeclaration& format = loader->m_native_vtx_decl;
@@ -139,7 +139,7 @@ int RunVertices(int vtx_attr_group, int primitive, int count, DataReader src, bo
CPState* state = &g_main_cp_state;
- VertexLoader* loader = RefreshLoader(vtx_attr_group, state);
+ VertexLoaderBase* loader = RefreshLoader(vtx_attr_group, state);
int size = count * loader->m_VertexSize;
if ((int)src.size() < size)
diff --git a/Source/Core/VideoCommon/VideoCommon.vcxproj b/Source/Core/VideoCommon/VideoCommon.vcxproj
index 65488aa4fa..b4db374e28 100644
--- a/Source/Core/VideoCommon/VideoCommon.vcxproj
+++ b/Source/Core/VideoCommon/VideoCommon.vcxproj
@@ -65,6 +65,7 @@
<ClCompile Include="TextureCacheBase.cpp" />
<ClCompile Include="TextureConversionShader.cpp" />
<ClCompile Include="VertexLoader.cpp" />
+ <ClCompile Include="VertexLoaderBase.cpp" />
<ClCompile Include="VertexLoaderManager.cpp" />
<ClCompile Include="VertexLoader_Color.cpp" />
<ClCompile Include="VertexLoader_Normal.cpp" />
@@ -118,6 +119,7 @@
<ClInclude Include="TextureConversionShader.h" />
<ClInclude Include="TextureDecoder.h" />
<ClInclude Include="VertexLoader.h" />
+ <ClInclude Include="VertexLoaderBase.h" />
<ClInclude Include="VertexLoaderManager.h" />
<ClInclude Include="VertexLoaderUtils.h" />
<ClInclude Include="VertexLoader_Color.h" />
diff --git a/Source/Core/VideoCommon/VideoCommon.vcxproj.filters b/Source/Core/VideoCommon/VideoCommon.vcxproj.filters
index cd4901f303..d00ee5518c 100644
--- a/Source/Core/VideoCommon/VideoCommon.vcxproj.filters
+++ b/Source/Core/VideoCommon/VideoCommon.vcxproj.filters
@@ -119,6 +119,9 @@
<ClCompile Include="VertexLoader.cpp">
<Filter>Vertex Loading</Filter>
</ClCompile>
+ <ClCompile Include="VertexLoaderBase.cpp">
+ <Filter>Vertex Loading</Filter>
+ </ClCompile>
<ClCompile Include="VertexLoader_Color.cpp">
<Filter>Vertex Loading</Filter>
</ClCompile>
@@ -263,6 +266,9 @@
<ClInclude Include="VertexLoader.h">
<Filter>Vertex Loading</Filter>
</ClInclude>
+ <ClInclude Include="VertexLoaderBase.h">
+ <Filter>Vertex Loading</Filter>
+ </ClInclude>
<ClInclude Include="VertexLoader_Color.h">
<Filter>Vertex Loading</Filter>
</ClInclude>
diff --git a/Source/UnitTests/VideoCommon/VertexLoaderTest.cpp b/Source/UnitTests/VideoCommon/VertexLoaderTest.cpp
index d1032ae6f9..601e90dcc2 100644
--- a/Source/UnitTests/VideoCommon/VertexLoaderTest.cpp
+++ b/Source/UnitTests/VideoCommon/VertexLoaderTest.cpp
@@ -2,7 +2,7 @@
#include "Common/Common.h"
#include "VideoCommon/DataReader.h"
-#include "VideoCommon/VertexLoader.h"
+#include "VideoCommon/VertexLoaderBase.h"
// Needs to be included later because it defines a TEST macro that conflicts
// with a TEST method definition in x64Emitter.h.
@@ -93,7 +93,7 @@ TEST_F(VertexLoaderTest, PositionDirectFloatXYZ)
m_vtx_attr.g0.PosElements = 1; // XYZ
m_vtx_attr.g0.PosFormat = 4; // Float
- VertexLoader* loader = new VertexLoader(m_vtx_desc, m_vtx_attr);
+ VertexLoaderBase* loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
ASSERT_EQ(3 * sizeof (float), (u32)loader->m_native_vtx_decl.stride);
ASSERT_EQ(3 * sizeof (float), (u32)loader->m_VertexSize);
@@ -118,7 +118,7 @@ TEST_F(VertexLoaderTest, PositionDirectFloatXYZ)
// Test that scale does nothing for floating point inputs.
Input(1.0f); Input(2.0f); Input(4.0f);
m_vtx_attr.g0.PosFrac = 1;
- loader = new VertexLoader(m_vtx_desc, m_vtx_attr);
+ loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
count = loader->RunVertices(7, 1, src, dst);
src.Skip(1 * loader->m_VertexSize);
dst.Skip(count * loader->m_native_vtx_decl.stride);
@@ -132,7 +132,7 @@ TEST_F(VertexLoaderTest, PositionDirectU16XY)
m_vtx_attr.g0.PosElements = 0; // XY
m_vtx_attr.g0.PosFormat = 2; // U16
- VertexLoader* loader = new VertexLoader(m_vtx_desc, m_vtx_attr);
+ VertexLoaderBase* loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
ASSERT_EQ(3 * sizeof (float), (u32)loader->m_native_vtx_decl.stride);
ASSERT_EQ(2 * sizeof (u16), (u32)loader->m_VertexSize);
@@ -159,7 +159,7 @@ TEST_F(VertexLoaderTest, PositionDirectU16XY)
// Test that scale works on U16 inputs.
Input<u16>(42); Input<u16>(24);
m_vtx_attr.g0.PosFrac = 1;
- loader = new VertexLoader(m_vtx_desc, m_vtx_attr);
+ loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
count = loader->RunVertices(7, 1, src, dst);
src.Skip(1 * loader->m_VertexSize);
dst.Skip(count * loader->m_native_vtx_decl.stride);
@@ -173,18 +173,19 @@ TEST_F(VertexLoaderTest, PositionDirectFloatXYZSpeed)
m_vtx_attr.g0.PosElements = 1; // XYZ
m_vtx_attr.g0.PosFormat = 4; // Float
- VertexLoader loader(m_vtx_desc, m_vtx_attr);
+ VertexLoaderBase* loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
- ASSERT_EQ(3 * sizeof (float), (u32)loader.m_native_vtx_decl.stride);
- ASSERT_EQ(3 * sizeof (float), (u32)loader.m_VertexSize);
+ ASSERT_EQ(3 * sizeof (float), (u32)loader->m_native_vtx_decl.stride);
+ ASSERT_EQ(3 * sizeof (float), (u32)loader->m_VertexSize);
for (int i = 0; i < 1000; ++i)
{
ResetPointers();
- int count = loader.RunVertices(7, 100000, src, dst);
- src.Skip(100000 * loader.m_VertexSize);
- dst.Skip(count * loader.m_native_vtx_decl.stride);
+ int count = loader->RunVertices(7, 100000, src, dst);
+ src.Skip(100000 * loader->m_VertexSize);
+ dst.Skip(count * loader->m_native_vtx_decl.stride);
}
+ delete loader;
}
TEST_F(VertexLoaderTest, PositionDirectU16XYSpeed)
@@ -193,18 +194,19 @@ TEST_F(VertexLoaderTest, PositionDirectU16XYSpeed)
m_vtx_attr.g0.PosElements = 0; // XY
m_vtx_attr.g0.PosFormat = 2; // U16
- VertexLoader loader(m_vtx_desc, m_vtx_attr);
+ VertexLoaderBase* loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
- ASSERT_EQ(3 * sizeof (float), (u32)loader.m_native_vtx_decl.stride);
- ASSERT_EQ(2 * sizeof (u16), (u32)loader.m_VertexSize);
+ ASSERT_EQ(3 * sizeof (float), (u32)loader->m_native_vtx_decl.stride);
+ ASSERT_EQ(2 * sizeof (u16), (u32)loader->m_VertexSize);
for (int i = 0; i < 1000; ++i)
{
ResetPointers();
- int count = loader.RunVertices(7, 100000, src, dst);
- src.Skip(100000 * loader.m_VertexSize);
- dst.Skip(count * loader.m_native_vtx_decl.stride);
+ int count = loader->RunVertices(7, 100000, src, dst);
+ src.Skip(100000 * loader->m_VertexSize);
+ dst.Skip(count * loader->m_native_vtx_decl.stride);
}
+ delete loader;
}
TEST_F(VertexLoaderTest, LargeFloatVertexSpeed)
@@ -257,15 +259,16 @@ TEST_F(VertexLoaderTest, LargeFloatVertexSpeed)
m_vtx_attr.g2.Tex7CoordElements = 1; // ST
m_vtx_attr.g2.Tex7CoordFormat = 4; // Float
- VertexLoader loader(m_vtx_desc, m_vtx_attr);
+ VertexLoaderBase* loader = VertexLoaderBase::CreateVertexLoader(m_vtx_desc, m_vtx_attr);
// This test is only done 100x in a row since it's ~20x slower using the
// current vertex loader implementation.
for (int i = 0; i < 100; ++i)
{
ResetPointers();
- int count = loader.RunVertices(7, 100000, src, dst);
- src.Skip(100000 * loader.m_VertexSize);
- dst.Skip(count * loader.m_native_vtx_decl.stride);
+ int count = loader->RunVertices(7, 100000, src, dst);
+ src.Skip(100000 * loader->m_VertexSize);
+ dst.Skip(count * loader->m_native_vtx_decl.stride);
}
+ delete loader;
}