diff options
| author | comex <comexk@gmail.com> | 2014-08-24 23:53:28 -0400 |
|---|---|---|
| committer | comex <comexk@gmail.com> | 2014-09-28 21:23:28 -0400 |
| commit | 63c62b277d6850279bd2a982535d5abde824e6e2 (patch) | |
| tree | def4ef41a504dd09c16f02cea82407b4f5d0edfc /Source/Core/VideoCommon/VertexLoaderManager.cpp | |
| parent | 431fb4d82a9fa9597df3c35c27e55714ff3e27c0 (diff) | |
Some changes to VertexLoaderManager:
- Lazily create the native vertex format (which involves GL calls) from
RunVertices rather than RefreshLoader itself, freeing the latter to be
run from the CPU thread (hopefully).
- In order to avoid useless allocations while doing so, store the native
format inside the VertexLoader rather than using a cache entry.
- Wrap the s_vertex_loader_map in a lock, for similar reasons.
Diffstat (limited to 'Source/Core/VideoCommon/VertexLoaderManager.cpp')
| -rw-r--r-- | Source/Core/VideoCommon/VertexLoaderManager.cpp | 88 |
1 files changed, 36 insertions, 52 deletions
diff --git a/Source/Core/VideoCommon/VertexLoaderManager.cpp b/Source/Core/VideoCommon/VertexLoaderManager.cpp index dbf22c9c3d..b3a1c97c3f 100644 --- a/Source/Core/VideoCommon/VertexLoaderManager.cpp +++ b/Source/Core/VideoCommon/VertexLoaderManager.cpp @@ -4,6 +4,7 @@ #include <algorithm> #include <memory> +#include <mutex> #include <unordered_map> #include <utility> #include <vector> @@ -24,8 +25,7 @@ static int s_attr_dirty; // bitfield static NativeVertexFormat* s_current_vtx_fmt; -typedef std::pair<VertexLoader*, NativeVertexFormat*> VertexLoaderCacheItem; -static VertexLoaderCacheItem s_VertexLoaders[8]; +static VertexLoader* s_VertexLoaders[8]; namespace std { @@ -41,14 +41,13 @@ struct hash<VertexLoaderUID> } -typedef std::unordered_map<VertexLoaderUID, VertexLoaderCacheItem> VertexLoaderMap; -typedef std::map<PortableVertexDeclaration, std::unique_ptr<NativeVertexFormat>> NativeVertexLoaderMap; +typedef std::unordered_map<VertexLoaderUID, std::unique_ptr<VertexLoader>> VertexLoaderMap; namespace VertexLoaderManager { -static VertexLoaderMap s_VertexLoaderMap; -static NativeVertexLoaderMap s_native_vertex_map; +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. void Init() @@ -56,20 +55,16 @@ void Init() MarkAllDirty(); for (auto& map_entry : s_VertexLoaders) { - map_entry.first = nullptr; - map_entry.second = nullptr; + map_entry = nullptr; } RecomputeCachedArraybases(); } void Shutdown() { - for (auto& map_entry : s_VertexLoaderMap) - { - delete map_entry.second.first; - } - s_VertexLoaderMap.clear(); - s_native_vertex_map.clear(); + std::lock_guard<std::mutex> lk(s_vertex_loader_map_lock); + s_vertex_loader_map.clear(); + VertexLoader::ClearNativeVertexFormatCache(); } namespace @@ -87,14 +82,15 @@ struct entry void AppendListToString(std::string *dest) { + std::lock_guard<std::mutex> lk(s_vertex_loader_map_lock); std::vector<entry> entries; size_t total_size = 0; - for (const auto& map_entry : s_VertexLoaderMap) + for (const auto& map_entry : s_vertex_loader_map) { entry e; - map_entry.second.first->AppendToString(&e.text); - e.num_verts = map_entry.second.first->GetNumLoadedVerts(); + map_entry.second->AppendToString(&e.text); + e.num_verts = map_entry.second->GetNumLoadedVerts(); entries.push_back(e); total_size += e.text.size() + 1; } @@ -111,54 +107,39 @@ void MarkAllDirty() s_attr_dirty = 0xff; } -static NativeVertexFormat* GetNativeVertexFormat(const PortableVertexDeclaration& format, - u32 components) -{ - auto& native = s_native_vertex_map[format]; - if (!native) - { - auto raw_pointer = g_vertex_manager->CreateNativeVertexFormat(); - native = std::unique_ptr<NativeVertexFormat>(raw_pointer); - native->Initialize(format); - native->m_components = components; - } - return native.get(); -} - -static VertexLoaderCacheItem RefreshLoader(int vtx_attr_group) +static VertexLoader* RefreshLoader(int vtx_attr_group) { + VertexLoader* loader; if ((s_attr_dirty >> vtx_attr_group) & 1) { VertexLoaderUID uid(g_VtxDesc, g_VtxAttr[vtx_attr_group]); - VertexLoaderMap::iterator iter = s_VertexLoaderMap.find(uid); - if (iter != s_VertexLoaderMap.end()) + std::lock_guard<std::mutex> lk(s_vertex_loader_map_lock); + VertexLoaderMap::iterator iter = s_vertex_loader_map.find(uid); + if (iter != s_vertex_loader_map.end()) { - s_VertexLoaders[vtx_attr_group] = iter->second; + loader = iter->second.get(); } else { - VertexLoader* loader = new VertexLoader(g_VtxDesc, g_VtxAttr[vtx_attr_group]); - - NativeVertexFormat* vtx_fmt = GetNativeVertexFormat( - loader->GetNativeVertexDeclaration(), - loader->GetNativeComponents()); - - s_VertexLoaderMap[uid] = std::make_pair(loader, vtx_fmt); - s_VertexLoaders[vtx_attr_group] = std::make_pair(loader, vtx_fmt); + loader = new VertexLoader(g_VtxDesc, g_VtxAttr[vtx_attr_group]); + s_vertex_loader_map[uid] = std::unique_ptr<VertexLoader>(loader); INCSTAT(stats.numVertexLoaders); } + s_VertexLoaders[vtx_attr_group] = loader; + s_attr_dirty &= ~(1 << vtx_attr_group); + } else { + loader = s_VertexLoaders[vtx_attr_group]; } - s_attr_dirty &= ~(1 << vtx_attr_group); - return s_VertexLoaders[vtx_attr_group]; + return loader; } bool RunVertices(int vtx_attr_group, int primitive, int count, size_t buf_size, bool skip_drawing) { if (!count) return true; - auto loader = RefreshLoader(vtx_attr_group); + VertexLoader* loader = RefreshLoader(vtx_attr_group); - size_t size = count * loader.first->GetVertexSize(); + size_t size = count * loader->GetVertexSize(); if (buf_size < size) return false; @@ -169,15 +150,18 @@ bool RunVertices(int vtx_attr_group, int primitive, int count, size_t buf_size, return true; } + NativeVertexFormat* native = loader->GetNativeVertexFormat(); + + // If the native vertex format changed, force a flush. - if (loader.second != s_current_vtx_fmt) + if (native != s_current_vtx_fmt) VertexManager::Flush(); - s_current_vtx_fmt = loader.second; + s_current_vtx_fmt = native; VertexManager::PrepareForAdditionalData(primitive, count, - loader.first->GetNativeVertexDeclaration().stride); + loader->GetNativeVertexDeclaration().stride); - loader.first->RunVertices(g_VtxAttr[vtx_attr_group], primitive, count); + loader->RunVertices(g_VtxAttr[vtx_attr_group], primitive, count); IndexGenerator::AddIndices(primitive, count); @@ -188,7 +172,7 @@ bool RunVertices(int vtx_attr_group, int primitive, int count, size_t buf_size, int GetVertexSize(int vtx_attr_group) { - return RefreshLoader(vtx_attr_group).first->GetVertexSize(); + return RefreshLoader(vtx_attr_group)->GetVertexSize(); } NativeVertexFormat* GetCurrentVertexFormat() |
