forked from suyu/suyu
Try to fix problems with stencil test in some games, relax translation to opengl enums to avoid crashing and only generate logs of the errors.
This commit is contained in:
parent
e9610ec0dd
commit
4a6eff3b7b
4 changed files with 61 additions and 37 deletions
|
@ -53,6 +53,19 @@ void Maxwell3D::InitializeRegisterDefaults() {
|
|||
regs.independent_blend[blend_index].factor_source_a = Regs::Blend::Factor::One;
|
||||
regs.independent_blend[blend_index].factor_dest_a = Regs::Blend::Factor::Zero;
|
||||
}
|
||||
regs.stencil_front_op_fail = Regs::StencilOp::Keep;
|
||||
regs.stencil_front_op_zfail = Regs::StencilOp::Keep;
|
||||
regs.stencil_front_op_zpass = Regs::StencilOp::Keep;
|
||||
regs.stencil_front_func_func = Regs::ComparisonOp::Always;
|
||||
regs.stencil_front_func_mask = 0xFFFFFFFF;
|
||||
regs.stencil_front_mask = 0xFFFFFFFF;
|
||||
regs.stencil_two_side_enable = 1;
|
||||
regs.stencil_back_op_fail = Regs::StencilOp::Keep;
|
||||
regs.stencil_back_op_zfail = Regs::StencilOp::Keep;
|
||||
regs.stencil_back_op_zpass = Regs::StencilOp::Keep;
|
||||
regs.stencil_back_func_func = Regs::ComparisonOp::Always;
|
||||
regs.stencil_back_func_mask = 0xFFFFFFFF;
|
||||
regs.stencil_back_mask = 0xFFFFFFFF;
|
||||
}
|
||||
|
||||
void Maxwell3D::CallMacroMethod(u32 method, std::vector<u32> parameters) {
|
||||
|
|
|
@ -345,6 +345,14 @@ public:
|
|||
Invert = 6,
|
||||
IncrWrap = 7,
|
||||
DecrWrap = 8,
|
||||
KeepOGL = 0x1E00,
|
||||
ZeroOGL = 0,
|
||||
ReplaceOGL = 0x1E01,
|
||||
IncrOGL = 0x1E02,
|
||||
DecrOGL = 0x1E03,
|
||||
InvertOGL = 0x150A,
|
||||
IncrWrapOGL = 0x8507,
|
||||
DecrWrapOGL = 0x8508,
|
||||
};
|
||||
|
||||
enum class MemoryLayout : u32 {
|
||||
|
|
|
@ -996,9 +996,6 @@ void RasterizerOpenGL::SyncStencilTestState() {
|
|||
return;
|
||||
}
|
||||
|
||||
// TODO(bunnei): Verify behavior when this is not set
|
||||
ASSERT(regs.stencil_two_side_enable);
|
||||
|
||||
state.stencil.front.test_func = MaxwellToGL::ComparisonOp(regs.stencil_front_func_func);
|
||||
state.stencil.front.test_ref = regs.stencil_front_func_ref;
|
||||
state.stencil.front.test_mask = regs.stencil_front_func_mask;
|
||||
|
@ -1006,7 +1003,7 @@ void RasterizerOpenGL::SyncStencilTestState() {
|
|||
state.stencil.front.action_depth_fail = MaxwellToGL::StencilOp(regs.stencil_front_op_zfail);
|
||||
state.stencil.front.action_depth_pass = MaxwellToGL::StencilOp(regs.stencil_front_op_zpass);
|
||||
state.stencil.front.write_mask = regs.stencil_front_mask;
|
||||
|
||||
if (regs.stencil_two_side_enable) {
|
||||
state.stencil.back.test_func = MaxwellToGL::ComparisonOp(regs.stencil_back_func_func);
|
||||
state.stencil.back.test_ref = regs.stencil_back_func_ref;
|
||||
state.stencil.back.test_mask = regs.stencil_back_func_mask;
|
||||
|
@ -1014,6 +1011,15 @@ void RasterizerOpenGL::SyncStencilTestState() {
|
|||
state.stencil.back.action_depth_fail = MaxwellToGL::StencilOp(regs.stencil_back_op_zfail);
|
||||
state.stencil.back.action_depth_pass = MaxwellToGL::StencilOp(regs.stencil_back_op_zpass);
|
||||
state.stencil.back.write_mask = regs.stencil_back_mask;
|
||||
} else {
|
||||
state.stencil.back.test_func = GL_ALWAYS;
|
||||
state.stencil.back.test_ref = 0;
|
||||
state.stencil.back.test_mask = 0xFFFFFFFF;
|
||||
state.stencil.back.write_mask = 0xFFFFFFFF;
|
||||
state.stencil.back.action_stencil_fail = GL_KEEP;
|
||||
state.stencil.back.action_depth_fail = GL_KEEP;
|
||||
state.stencil.back.action_depth_pass = GL_KEEP;
|
||||
}
|
||||
}
|
||||
|
||||
void RasterizerOpenGL::SyncColorMask() {
|
||||
|
|
|
@ -159,10 +159,9 @@ inline GLenum TextureFilterMode(Tegra::Texture::TextureFilter filter_mode,
|
|||
}
|
||||
}
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented texture filter mode={}",
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented texture filter mode={}",
|
||||
static_cast<u32>(filter_mode));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
return GL_LINEAR;
|
||||
}
|
||||
|
||||
inline GLenum WrapMode(Tegra::Texture::WrapMode wrap_mode) {
|
||||
|
@ -183,9 +182,8 @@ inline GLenum WrapMode(Tegra::Texture::WrapMode wrap_mode) {
|
|||
case Tegra::Texture::WrapMode::MirrorOnceClampToEdge:
|
||||
return GL_MIRROR_CLAMP_TO_EDGE;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented texture wrap mode={}", static_cast<u32>(wrap_mode));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented texture wrap mode={}", static_cast<u32>(wrap_mode));
|
||||
return GL_REPEAT;
|
||||
}
|
||||
|
||||
inline GLenum DepthCompareFunc(Tegra::Texture::DepthCompareFunc func) {
|
||||
|
@ -207,10 +205,9 @@ inline GLenum DepthCompareFunc(Tegra::Texture::DepthCompareFunc func) {
|
|||
case Tegra::Texture::DepthCompareFunc::Always:
|
||||
return GL_ALWAYS;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented texture depth compare function ={}",
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented texture depth compare function ={}",
|
||||
static_cast<u32>(func));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
return GL_GREATER;
|
||||
}
|
||||
|
||||
inline GLenum BlendEquation(Maxwell::Blend::Equation equation) {
|
||||
|
@ -226,9 +223,8 @@ inline GLenum BlendEquation(Maxwell::Blend::Equation equation) {
|
|||
case Maxwell::Blend::Equation::Max:
|
||||
return GL_MAX;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented blend equation={}", static_cast<u32>(equation));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented blend equation={}", static_cast<u32>(equation));
|
||||
return GL_FUNC_ADD;
|
||||
}
|
||||
|
||||
inline GLenum BlendFunc(Maxwell::Blend::Factor factor) {
|
||||
|
@ -291,9 +287,8 @@ inline GLenum BlendFunc(Maxwell::Blend::Factor factor) {
|
|||
case Maxwell::Blend::Factor::OneMinusConstantAlphaGL:
|
||||
return GL_ONE_MINUS_CONSTANT_ALPHA;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented blend factor={}", static_cast<u32>(factor));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented blend factor={}", static_cast<u32>(factor));
|
||||
return GL_ZERO;
|
||||
}
|
||||
|
||||
inline GLenum SwizzleSource(Tegra::Texture::SwizzleSource source) {
|
||||
|
@ -312,9 +307,8 @@ inline GLenum SwizzleSource(Tegra::Texture::SwizzleSource source) {
|
|||
case Tegra::Texture::SwizzleSource::OneFloat:
|
||||
return GL_ONE;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented swizzle source={}", static_cast<u32>(source));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented swizzle source={}", static_cast<u32>(source));
|
||||
return GL_ZERO;
|
||||
}
|
||||
|
||||
inline GLenum ComparisonOp(Maxwell::ComparisonOp comparison) {
|
||||
|
@ -344,33 +338,39 @@ inline GLenum ComparisonOp(Maxwell::ComparisonOp comparison) {
|
|||
case Maxwell::ComparisonOp::AlwaysOld:
|
||||
return GL_ALWAYS;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented comparison op={}", static_cast<u32>(comparison));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented comparison op={}", static_cast<u32>(comparison));
|
||||
return GL_ALWAYS;
|
||||
}
|
||||
|
||||
inline GLenum StencilOp(Maxwell::StencilOp stencil) {
|
||||
switch (stencil) {
|
||||
case Maxwell::StencilOp::Keep:
|
||||
case Maxwell::StencilOp::KeepOGL:
|
||||
return GL_KEEP;
|
||||
case Maxwell::StencilOp::Zero:
|
||||
case Maxwell::StencilOp::ZeroOGL:
|
||||
return GL_ZERO;
|
||||
case Maxwell::StencilOp::Replace:
|
||||
case Maxwell::StencilOp::ReplaceOGL:
|
||||
return GL_REPLACE;
|
||||
case Maxwell::StencilOp::Incr:
|
||||
case Maxwell::StencilOp::IncrOGL:
|
||||
return GL_INCR;
|
||||
case Maxwell::StencilOp::Decr:
|
||||
case Maxwell::StencilOp::DecrOGL:
|
||||
return GL_DECR;
|
||||
case Maxwell::StencilOp::Invert:
|
||||
case Maxwell::StencilOp::InvertOGL:
|
||||
return GL_INVERT;
|
||||
case Maxwell::StencilOp::IncrWrap:
|
||||
case Maxwell::StencilOp::IncrWrapOGL:
|
||||
return GL_INCR_WRAP;
|
||||
case Maxwell::StencilOp::DecrWrap:
|
||||
case Maxwell::StencilOp::DecrWrapOGL:
|
||||
return GL_DECR_WRAP;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented stencil op={}", static_cast<u32>(stencil));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented stencil op={}", static_cast<u32>(stencil));
|
||||
return GL_KEEP;
|
||||
}
|
||||
|
||||
inline GLenum FrontFace(Maxwell::Cull::FrontFace front_face) {
|
||||
|
@ -380,9 +380,8 @@ inline GLenum FrontFace(Maxwell::Cull::FrontFace front_face) {
|
|||
case Maxwell::Cull::FrontFace::CounterClockWise:
|
||||
return GL_CCW;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented front face cull={}", static_cast<u32>(front_face));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented front face cull={}", static_cast<u32>(front_face));
|
||||
return GL_CCW;
|
||||
}
|
||||
|
||||
inline GLenum CullFace(Maxwell::Cull::CullFace cull_face) {
|
||||
|
@ -394,9 +393,8 @@ inline GLenum CullFace(Maxwell::Cull::CullFace cull_face) {
|
|||
case Maxwell::Cull::CullFace::FrontAndBack:
|
||||
return GL_FRONT_AND_BACK;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented cull face={}", static_cast<u32>(cull_face));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented cull face={}", static_cast<u32>(cull_face));
|
||||
return GL_BACK;
|
||||
}
|
||||
|
||||
inline GLenum LogicOp(Maxwell::LogicOperation operation) {
|
||||
|
@ -434,9 +432,8 @@ inline GLenum LogicOp(Maxwell::LogicOperation operation) {
|
|||
case Maxwell::LogicOperation::Set:
|
||||
return GL_SET;
|
||||
}
|
||||
LOG_CRITICAL(Render_OpenGL, "Unimplemented logic operation={}", static_cast<u32>(operation));
|
||||
UNREACHABLE();
|
||||
return {};
|
||||
LOG_ERROR(Render_OpenGL, "Unimplemented logic operation={}", static_cast<u32>(operation));
|
||||
return GL_COPY;
|
||||
}
|
||||
|
||||
} // namespace MaxwellToGL
|
||||
|
|
Loading…
Reference in a new issue