diff --git a/GPU/Common/DrawEngineCommon.cpp b/GPU/Common/DrawEngineCommon.cpp index ed58732a7d..0ea6f18a60 100644 --- a/GPU/Common/DrawEngineCommon.cpp +++ b/GPU/Common/DrawEngineCommon.cpp @@ -168,7 +168,8 @@ void DrawEngineCommon::DispatchSubmitImm(GEPrimitiveType prim, TransformedVertex uint32_t vertTypeID = GetVertTypeID(vtype, 0, applySkinInDecode_); bool clockwise = !gstate.isCullEnabled() || gstate.getCullMode() == cullMode; - SubmitPrim(&temp[0], nullptr, prim, vertexCount, vertTypeID, clockwise, &bytesRead); + VertexDecoder *dec = GetVertexDecoder(vertTypeID); + SubmitPrim(&temp[0], nullptr, prim, vertexCount, dec, vertTypeID, clockwise, &bytesRead); Flush(); if (!prevThrough) { @@ -826,7 +827,7 @@ void DrawEngineCommon::SkipPrim(GEPrimitiveType prim, int vertexCount, u32 vertT } // vertTypeID is the vertex type but with the UVGen mode smashed into the top bits. -bool DrawEngineCommon::SubmitPrim(const void *verts, const void *inds, GEPrimitiveType prim, int vertexCount, u32 vertTypeID, bool clockwise, int *bytesRead) { +bool DrawEngineCommon::SubmitPrim(const void *verts, const void *inds, GEPrimitiveType prim, int vertexCount, VertexDecoder *dec, u32 vertTypeID, bool clockwise, int *bytesRead) { if (!indexGen.PrimCompatible(prevPrim_, prim) || numDrawVerts_ >= MAX_DEFERRED_DRAW_VERTS || numDrawInds_ >= MAX_DEFERRED_DRAW_INDS || vertexCountInDrawCalls_ + vertexCount > VERTEX_BUFFER_MAX) { Flush(); } @@ -846,8 +847,11 @@ bool DrawEngineCommon::SubmitPrim(const void *verts, const void *inds, GEPrimiti // If vtype has changed, setup the vertex decoder. Don't need to nullcheck dec_ since we set lastVType_ to an invalid value whenever we null it. if (vertTypeID != lastVType_) { - dec_ = GetVertexDecoder(vertTypeID); + dec_ = dec; + _dbg_assert_(dec->VertexType() == vertTypeID); lastVType_ = vertTypeID; + } else { + _dbg_assert_(dec_->VertexType() == lastVType_); } *bytesRead = vertexCount * dec_->VertexSize(); diff --git a/GPU/Common/DrawEngineCommon.h b/GPU/Common/DrawEngineCommon.h index 38f41eca15..fd538c04ed 100644 --- a/GPU/Common/DrawEngineCommon.h +++ b/GPU/Common/DrawEngineCommon.h @@ -95,7 +95,8 @@ public: // is different. Should probably refactor that. // Note that vertTypeID should be computed using GetVertTypeID(). virtual void DispatchSubmitPrim(const void *verts, const void *inds, GEPrimitiveType prim, int vertexCount, u32 vertTypeID, bool clockwise, int *bytesRead) { - SubmitPrim(verts, inds, prim, vertexCount, vertTypeID, clockwise, bytesRead); + VertexDecoder *dec = GetVertexDecoder(vertTypeID); + SubmitPrim(verts, inds, prim, vertexCount, dec, vertTypeID, clockwise, bytesRead); } virtual void DispatchSubmitImm(GEPrimitiveType prim, TransformedVertex *buffer, int vertexCount, int cullMode, bool continuation); @@ -118,7 +119,7 @@ public: } int ExtendNonIndexedPrim(const uint32_t *cmd, const uint32_t *stall, u32 vertTypeID, bool clockwise, int *bytesRead, bool isTriangle); - bool SubmitPrim(const void *verts, const void *inds, GEPrimitiveType prim, int vertexCount, u32 vertTypeID, bool clockwise, int *bytesRead); + bool SubmitPrim(const void *verts, const void *inds, GEPrimitiveType prim, int vertexCount, VertexDecoder *dec, u32 vertTypeID, bool clockwise, int *bytesRead); void SkipPrim(GEPrimitiveType prim, int vertexCount, u32 vertTypeID, int *bytesRead); template @@ -145,14 +146,14 @@ public: return numDrawVerts_; } - VertexDecoder *GetVertexDecoder(u32 vtype) { + VertexDecoder *GetVertexDecoder(u32 vertTypeID) { VertexDecoder *dec; - if (decoderMap_.Get(vtype, &dec)) + if (decoderMap_.Get(vertTypeID, &dec)) return dec; dec = new VertexDecoder(); _assert_(dec); - dec->SetVertexType(vtype, decOptions_, decJitCache_); - decoderMap_.Insert(vtype, dec); + dec->SetVertexType(vertTypeID, decOptions_, decJitCache_); + decoderMap_.Insert(vertTypeID, dec); return dec; } diff --git a/GPU/GPUCommonHW.cpp b/GPU/GPUCommonHW.cpp index b4a8c97a7d..d4f11518b0 100644 --- a/GPU/GPUCommonHW.cpp +++ b/GPU/GPUCommonHW.cpp @@ -997,6 +997,7 @@ void GPUCommonHW::Execute_Prim(u32 op, u32 diff) { int cullMode = gstate.getCullMode(); uint32_t vertTypeID = GetVertTypeID(vertexType, gstate.getUVGenMode(), g_Config.bSoftwareSkinning); + VertexDecoder *decoder = drawEngineCommon_->GetVertexDecoder(vertTypeID); // Through mode early-out for simple float 2D draws, like in Fate Extra CCC (very beneficial there due to avoiding texture loads) if ((vertexType & (GE_VTYPE_THROUGH_MASK | GE_VTYPE_POS_MASK | GE_VTYPE_IDX_MASK)) == (GE_VTYPE_THROUGH_MASK | GE_VTYPE_POS_FLOAT | GE_VTYPE_IDX_NONE)) { @@ -1037,7 +1038,7 @@ void GPUCommonHW::Execute_Prim(u32 op, u32 diff) { // Cuts down on checking, while not losing that much efficiency. bool onePassed = false; if (passCulling) { - if (!drawEngineCommon_->SubmitPrim(verts, inds, prim, count, vertTypeID, true, &bytesRead)) { + if (!drawEngineCommon_->SubmitPrim(verts, inds, prim, count, decoder, vertTypeID, true, &bytesRead)) { canExtend = false; } onePassed = true; @@ -1115,7 +1116,7 @@ void GPUCommonHW::Execute_Prim(u32 op, u32 diff) { } } if (passCulling) { - if (!drawEngineCommon_->SubmitPrim(verts, inds, newPrim, count, vertTypeID, clockwise, &bytesRead)) { + if (!drawEngineCommon_->SubmitPrim(verts, inds, newPrim, count, decoder, vertTypeID, clockwise, &bytesRead)) { canExtend = false; } // As soon as one passes, assume we don't need to check the rest of this batch. @@ -1140,6 +1141,7 @@ void GPUCommonHW::Execute_Prim(u32 op, u32 diff) { canExtend = false; // TODO: Might support extending between some vertex types in the future. vertexType = data; vertTypeID = GetVertTypeID(vertexType, gstate.getUVGenMode(), g_Config.bSoftwareSkinning); + decoder = drawEngineCommon_->GetVertexDecoder(vertTypeID); } break; }