From f81d3915465120acd0f85746bb94a84c92dbe368 Mon Sep 17 00:00:00 2001 From: refractionpcsx2 Date: Sat, 15 Jul 2023 01:58:45 +0100 Subject: [PATCH] GS/HW: Use draw for valid height, preload cached size --- pcsx2/GS/Renderers/HW/GSHwHack.cpp | 2 +- pcsx2/GS/Renderers/HW/GSRendererHW.cpp | 15 +++++++++++---- pcsx2/GS/Renderers/HW/GSRendererHW.h | 1 + pcsx2/GS/Renderers/HW/GSTextureCache.cpp | 18 ++++++++++++++---- pcsx2/GS/Renderers/HW/GSTextureCache.h | 2 +- 5 files changed, 28 insertions(+), 10 deletions(-) diff --git a/pcsx2/GS/Renderers/HW/GSHwHack.cpp b/pcsx2/GS/Renderers/HW/GSHwHack.cpp index 0026da5dae..a5930058c5 100644 --- a/pcsx2/GS/Renderers/HW/GSHwHack.cpp +++ b/pcsx2/GS/Renderers/HW/GSHwHack.cpp @@ -1142,7 +1142,7 @@ static bool GetMoveTargetPair(GSRendererHW& r, GSTextureCache::Target** src, GIF if (req_target) return false; - tdst = g_texture_cache->CreateTarget(dst_desc, tsrc->GetUnscaledSize(), tsrc->GetScale(), dst_type, true, 0, + tdst = g_texture_cache->CreateTarget(dst_desc, tsrc->GetUnscaledSize(), tsrc->GetUnscaledSize(), tsrc->GetScale(), dst_type, true, 0, false, false, true, tsrc->GetUnscaledRect()); if (!tdst) return false; diff --git a/pcsx2/GS/Renderers/HW/GSRendererHW.cpp b/pcsx2/GS/Renderers/HW/GSRendererHW.cpp index 0a9c637c40..a2d67dd00a 100644 --- a/pcsx2/GS/Renderers/HW/GSRendererHW.cpp +++ b/pcsx2/GS/Renderers/HW/GSRendererHW.cpp @@ -721,7 +721,7 @@ float GSRendererHW::GetTextureScaleFactor() return GetUpscaleMultiplier(); } -GSVector2i GSRendererHW::GetTargetSize(const GSTextureCache::Source* tex) +GSVector2i GSRendererHW::GetValidSize(const GSTextureCache::Source* tex) { // Don't blindly expand out to the scissor size if we're not drawing to it. // e.g. Burnout 3, God of War II, etc. @@ -779,7 +779,14 @@ GSVector2i GSRendererHW::GetTargetSize(const GSTextureCache::Source* tex) } } - return g_texture_cache->GetTargetSize(m_cached_ctx.FRAME.Block(), m_cached_ctx.FRAME.FBW, m_cached_ctx.FRAME.PSM, width, height); + return GSVector2i(width, height); +} + +GSVector2i GSRendererHW::GetTargetSize(const GSTextureCache::Source* tex) +{ + const GSVector2i valid_size = GetValidSize(tex); + + return g_texture_cache->GetTargetSize(m_cached_ctx.FRAME.Block(), m_cached_ctx.FRAME.FBW, m_cached_ctx.FRAME.PSM, valid_size.x, valid_size.y); } bool GSRendererHW::IsPossibleChannelShuffle() const @@ -2169,7 +2176,7 @@ void GSRendererHW::Draw() return; } - rt = g_texture_cache->CreateTarget(FRAME_TEX0, t_size, target_scale, GSTextureCache::RenderTarget, true, + rt = g_texture_cache->CreateTarget(FRAME_TEX0, t_size, GetValidSize(src), target_scale, GSTextureCache::RenderTarget, true, fm, false, force_preload, preserve_rt_color, m_r); if (unlikely(!rt)) { @@ -2193,7 +2200,7 @@ void GSRendererHW::Draw() m_cached_ctx.DepthWrite(), 0, false, force_preload, preserve_depth, m_r); if (!ds) { - ds = g_texture_cache->CreateTarget(ZBUF_TEX0, t_size, target_scale, GSTextureCache::DepthStencil, + ds = g_texture_cache->CreateTarget(ZBUF_TEX0, t_size, GetValidSize(src), target_scale, GSTextureCache::DepthStencil, m_cached_ctx.DepthWrite(), 0, false, force_preload, preserve_depth, m_r); if (unlikely(!ds)) { diff --git a/pcsx2/GS/Renderers/HW/GSRendererHW.h b/pcsx2/GS/Renderers/HW/GSRendererHW.h index 43912952b4..42f7b4ec7c 100644 --- a/pcsx2/GS/Renderers/HW/GSRendererHW.h +++ b/pcsx2/GS/Renderers/HW/GSRendererHW.h @@ -195,6 +195,7 @@ public: GSVector4i ComputeBoundingBox(const GSVector2i& rtsize, float rtscale); void MergeSprite(GSTextureCache::Source* tex); float GetTextureScaleFactor() override; + GSVector2i GetValidSize(const GSTextureCache::Source* tex = nullptr); GSVector2i GetTargetSize(const GSTextureCache::Source* tex = nullptr); void Reset(bool hardware_reset) override; diff --git a/pcsx2/GS/Renderers/HW/GSTextureCache.cpp b/pcsx2/GS/Renderers/HW/GSTextureCache.cpp index 5fa95991f2..29a790b3da 100644 --- a/pcsx2/GS/Renderers/HW/GSTextureCache.cpp +++ b/pcsx2/GS/Renderers/HW/GSTextureCache.cpp @@ -113,6 +113,9 @@ void GSTextureCache::AddDirtyRectTarget(Target* target, GSVector4i rect, u32 psm bool skipdirty = false; bool canskip = true; + if (rect.rempty()) + return; + std::vector::iterator it = target->m_dirty.end(); while (it != target->m_dirty.begin()) { @@ -359,6 +362,9 @@ GSVector4i GSTextureCache::TranslateAlignedRectByPage(Target* t, u32 sbp, u32 sp void GSTextureCache::DirtyRectByPage(u32 sbp, u32 spsm, u32 sbw, Target* t, GSVector4i src_r) { + if (src_r.rempty()) + return; + const GSVector2i src_page_size = GSLocalMemory::m_psm[spsm].pgs; const GSVector2i dst_page_size = GSLocalMemory::m_psm[t->m_TEX0.PSM].pgs; const u32 src_bw = std::max(1U, sbw) * 64; @@ -1404,6 +1410,7 @@ GSTextureCache::Target* GSTextureCache::LookupTarget(GIFRegTEX0 TEX0, const GSVe dst->m_32_bits_fmt = dst_match->m_32_bits_fmt; dst->OffsetHack_modxy = dst_match->OffsetHack_modxy; dst->m_end_block = dst_match->m_end_block; // If we're copying the size, we need to keep the end block. + dst->m_valid = dst_match->m_valid; ShaderConvert shader; // m_32_bits_fmt gets set on a shuffle or if the format isn't 16bit. @@ -1486,7 +1493,7 @@ GSTextureCache::Target* GSTextureCache::LookupTarget(GIFRegTEX0 TEX0, const GSVe return dst; } -GSTextureCache::Target* GSTextureCache::CreateTarget(GIFRegTEX0 TEX0, const GSVector2i& size, float scale, int type, +GSTextureCache::Target* GSTextureCache::CreateTarget(GIFRegTEX0 TEX0, const GSVector2i& size, const GSVector2i& valid_size, float scale, int type, bool used, u32 fbmask, bool is_frame, bool preload, bool preserve_target, const GSVector4i draw_rect) { const GSLocalMemory::psm_t& psm_s = GSLocalMemory::m_psm[TEX0.PSM]; @@ -1526,7 +1533,7 @@ GSTextureCache::Target* GSTextureCache::CreateTarget(GIFRegTEX0 TEX0, const GSVe RGBAMask rgba; rgba._u32 = GSUtil::GetChannelMask(TEX0.PSM); - dst->UpdateValidity(newrect); + dst->UpdateValidity(GSVector4i::loadh(valid_size)); if (!is_frame && !forced_preload && !preload) { @@ -1624,6 +1631,9 @@ GSTextureCache::Target* GSTextureCache::CreateTarget(GIFRegTEX0 TEX0, const GSVe AddDirtyRectTarget(dst, newrect, TEX0.PSM, TEX0.TBW, rgba, GSLocalMemory::m_psm[TEX0.PSM].trbpp >= 16); } } + else + dst->UpdateValidity(GSVector4i::loadh(valid_size)); + dst->m_is_frame = is_frame; dst->m_used |= used; @@ -1643,7 +1653,7 @@ GSTextureCache::Target* GSTextureCache::LookupDisplayTarget(GIFRegTEX0 TEX0, con if (dst) return dst; - return CreateTarget(TEX0, size, scale, RenderTarget, true, 0, true); + return CreateTarget(TEX0, size, size, scale, RenderTarget, true, 0, true); } void GSTextureCache::ScaleTargetForDisplay(Target* t, const GIFRegTEX0& dispfb, int real_w, int real_h) @@ -2769,7 +2779,7 @@ bool GSTextureCache::Move(u32 SBP, u32 SBW, u32 SPSM, int sx, int sy, u32 DBP, u const GSVector2i target_size = GetTargetSize(DBP, DBW, DPSM, Common::AlignUpPow2(w, 64), h); dst = LookupTarget(new_TEX0, target_size, src->m_scale, src->m_type); if (!dst) - dst = CreateTarget(new_TEX0, target_size, src->m_scale, src->m_type); + dst = CreateTarget(new_TEX0, target_size, target_size, src->m_scale, src->m_type); if (!dst) return false; diff --git a/pcsx2/GS/Renderers/HW/GSTextureCache.h b/pcsx2/GS/Renderers/HW/GSTextureCache.h index 53b8fde57d..b78a52c210 100644 --- a/pcsx2/GS/Renderers/HW/GSTextureCache.h +++ b/pcsx2/GS/Renderers/HW/GSTextureCache.h @@ -469,7 +469,7 @@ public: Target* LookupTarget(GIFRegTEX0 TEX0, const GSVector2i& size, float scale, int type, bool used = true, u32 fbmask = 0, bool is_frame = false, bool preload = GSConfig.PreloadFrameWithGSData, bool preserve_target = true, const GSVector4i draw_rc = GSVector4i::zero()); - Target* CreateTarget(GIFRegTEX0 TEX0, const GSVector2i& size, float scale, int type, bool used = true, u32 fbmask = 0, + Target* CreateTarget(GIFRegTEX0 TEX0, const GSVector2i& size, const GSVector2i& valid_size,float scale, int type, bool used = true, u32 fbmask = 0, bool is_frame = false, bool preload = GSConfig.PreloadFrameWithGSData, bool preserve_target = true, const GSVector4i draw_rc = GSVector4i::zero()); Target* LookupDisplayTarget(GIFRegTEX0 TEX0, const GSVector2i& size, float scale);