Merge pull request #484 from kayru/render_target_pool

Render: Implemented simple render target pool
This commit is contained in:
Pierre Bourdon 2014-09-04 22:58:01 +02:00
commit f9650c52f8
2 changed files with 64 additions and 3 deletions

View File

@ -22,6 +22,7 @@
enum
{
TEXTURE_KILL_THRESHOLD = 200,
RENDER_TARGET_KILL_THRESHOLD = 3,
};
TextureCache *g_texture_cache;
@ -30,6 +31,7 @@ GC_ALIGNED16(u8 *TextureCache::temp) = nullptr;
unsigned int TextureCache::temp_size;
TextureCache::TexCache TextureCache::textures;
TextureCache::RenderTargetPool TextureCache::render_target_pool;
TextureCache::BackupConfig TextureCache::backup_config;
@ -67,6 +69,12 @@ void TextureCache::Invalidate()
delete tex.second;
}
textures.clear();
for (auto& rt : render_target_pool)
{
delete rt;
}
render_target_pool.clear();
}
TextureCache::~TextureCache()
@ -138,6 +146,22 @@ void TextureCache::Cleanup()
++iter;
}
}
for (size_t i = 0; i < render_target_pool.size();)
{
auto rt = render_target_pool[i];
if (frameCount > RENDER_TARGET_KILL_THRESHOLD + rt->frameCount)
{
delete rt;
render_target_pool[i] = render_target_pool.back();
render_target_pool.pop_back();
}
else
{
++i;
}
}
}
void TextureCache::InvalidateRange(u32 start_address, u32 size)
@ -868,8 +892,17 @@ void TextureCache::CopyRenderTargetToTexture(u32 dstAddr, unsigned int dstFormat
}
else if (!(entry->type == TCET_EC_VRAM && entry->virtual_width == scaled_tex_w && entry->virtual_height == scaled_tex_h))
{
// remove it and recreate it as a render target
delete entry;
if (entry->type == TCET_EC_VRAM)
{
// try to re-use this render target later
FreeRenderTarget(entry);
}
else
{
// remove it and recreate it as a render target
delete entry;
}
entry = nullptr;
}
}
@ -877,7 +910,7 @@ void TextureCache::CopyRenderTargetToTexture(u32 dstAddr, unsigned int dstFormat
if (nullptr == entry)
{
// create the texture
textures[dstAddr] = entry = g_texture_cache->CreateRenderTargetTexture(scaled_tex_w, scaled_tex_h);
textures[dstAddr] = entry = AllocateRenderTarget(scaled_tex_w, scaled_tex_h);
// TODO: Using the wrong dstFormat, dumb...
entry->SetGeneralParameters(dstAddr, 0, dstFormat, 1);
@ -890,3 +923,26 @@ void TextureCache::CopyRenderTargetToTexture(u32 dstAddr, unsigned int dstFormat
entry->FromRenderTarget(dstAddr, dstFormat, srcFormat, srcRect, isIntensity, scaleByHalf, cbufid, colmat);
}
TextureCache::TCacheEntryBase* TextureCache::AllocateRenderTarget(unsigned int width, unsigned int height)
{
for (size_t i = 0; i < render_target_pool.size(); ++i)
{
auto rt = render_target_pool[i];
if (rt->virtual_width != width || rt->virtual_height != height)
continue;
render_target_pool[i] = render_target_pool.back();
render_target_pool.pop_back();
return rt;
}
return g_texture_cache->CreateRenderTargetTexture(width, height);
}
void TextureCache::FreeRenderTarget(TCacheEntryBase* entry)
{
render_target_pool.push_back(entry);
}

View File

@ -119,9 +119,14 @@ private:
static PC_TexFormat LoadCustomTexture(u64 tex_hash, int texformat, unsigned int level, unsigned int& width, unsigned int& height);
static void DumpTexture(TCacheEntryBase* entry, unsigned int level);
static TCacheEntryBase* AllocateRenderTarget(unsigned int width, unsigned int height);
static void FreeRenderTarget(TCacheEntryBase* entry);
typedef std::map<u32, TCacheEntryBase*> TexCache;
typedef std::vector<TCacheEntryBase*> RenderTargetPool;
static TexCache textures;
static RenderTargetPool render_target_pool;
// Backup configuration values
static struct BackupConfig