diff options
| author | 2015-08-24 01:46:58 -0300 | |
|---|---|---|
| committer | 2015-08-24 01:46:58 -0300 | |
| commit | 082b74fa241ba71f27b2e3fdf756824a0467f7f4 (patch) | |
| tree | 4bc4da888d196924e300d4f853855ac6d55fafa9 /src | |
| parent | Shader JIT: Add name to second scratch register (XMM4) (diff) | |
| download | yuzu-082b74fa241ba71f27b2e3fdf756824a0467f7f4.tar.gz yuzu-082b74fa241ba71f27b2e3fdf756824a0467f7f4.tar.xz yuzu-082b74fa241ba71f27b2e3fdf756824a0467f7f4.zip | |
Shaders: Explicitly conform to PICA semantics in MAX/MIN
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/shader/shader_interpreter.cpp | 10 | ||||
| -rw-r--r-- | src/video_core/shader/shader_jit_x64.cpp | 2 |
2 files changed, 10 insertions, 2 deletions
diff --git a/src/video_core/shader/shader_interpreter.cpp b/src/video_core/shader/shader_interpreter.cpp index ae5a30441..69e4efa68 100644 --- a/src/video_core/shader/shader_interpreter.cpp +++ b/src/video_core/shader/shader_interpreter.cpp | |||
| @@ -177,7 +177,10 @@ void RunInterpreter(UnitState<Debug>& state) { | |||
| 177 | if (!swizzle.DestComponentEnabled(i)) | 177 | if (!swizzle.DestComponentEnabled(i)) |
| 178 | continue; | 178 | continue; |
| 179 | 179 | ||
| 180 | dest[i] = std::max(src1[i], src2[i]); | 180 | // NOTE: Exact form required to match NaN semantics to hardware: |
| 181 | // max(0, NaN) -> NaN | ||
| 182 | // max(NaN, 0) -> 0 | ||
| 183 | dest[i] = (src1[i] > src2[i]) ? src1[i] : src2[i]; | ||
| 181 | } | 184 | } |
| 182 | Record<DebugDataRecord::DEST_OUT>(state.debug, iteration, dest); | 185 | Record<DebugDataRecord::DEST_OUT>(state.debug, iteration, dest); |
| 183 | break; | 186 | break; |
| @@ -190,7 +193,10 @@ void RunInterpreter(UnitState<Debug>& state) { | |||
| 190 | if (!swizzle.DestComponentEnabled(i)) | 193 | if (!swizzle.DestComponentEnabled(i)) |
| 191 | continue; | 194 | continue; |
| 192 | 195 | ||
| 193 | dest[i] = std::min(src1[i], src2[i]); | 196 | // NOTE: Exact form required to match NaN semantics to hardware: |
| 197 | // min(0, NaN) -> NaN | ||
| 198 | // min(NaN, 0) -> 0 | ||
| 199 | dest[i] = (src1[i] < src2[i]) ? src1[i] : src2[i]; | ||
| 194 | } | 200 | } |
| 195 | Record<DebugDataRecord::DEST_OUT>(state.debug, iteration, dest); | 201 | Record<DebugDataRecord::DEST_OUT>(state.debug, iteration, dest); |
| 196 | break; | 202 | break; |
diff --git a/src/video_core/shader/shader_jit_x64.cpp b/src/video_core/shader/shader_jit_x64.cpp index e56bff2b8..456c8567d 100644 --- a/src/video_core/shader/shader_jit_x64.cpp +++ b/src/video_core/shader/shader_jit_x64.cpp | |||
| @@ -467,6 +467,7 @@ void JitCompiler::Compile_FLR(Instruction instr) { | |||
| 467 | void JitCompiler::Compile_MAX(Instruction instr) { | 467 | void JitCompiler::Compile_MAX(Instruction instr) { |
| 468 | Compile_SwizzleSrc(instr, 1, instr.common.src1, SRC1); | 468 | Compile_SwizzleSrc(instr, 1, instr.common.src1, SRC1); |
| 469 | Compile_SwizzleSrc(instr, 2, instr.common.src2, SRC2); | 469 | Compile_SwizzleSrc(instr, 2, instr.common.src2, SRC2); |
| 470 | // SSE semantics match PICA200 ones: In case of NaN, SRC2 is returned. | ||
| 470 | MAXPS(SRC1, R(SRC2)); | 471 | MAXPS(SRC1, R(SRC2)); |
| 471 | Compile_DestEnable(instr, SRC1); | 472 | Compile_DestEnable(instr, SRC1); |
| 472 | } | 473 | } |
| @@ -474,6 +475,7 @@ void JitCompiler::Compile_MAX(Instruction instr) { | |||
| 474 | void JitCompiler::Compile_MIN(Instruction instr) { | 475 | void JitCompiler::Compile_MIN(Instruction instr) { |
| 475 | Compile_SwizzleSrc(instr, 1, instr.common.src1, SRC1); | 476 | Compile_SwizzleSrc(instr, 1, instr.common.src1, SRC1); |
| 476 | Compile_SwizzleSrc(instr, 2, instr.common.src2, SRC2); | 477 | Compile_SwizzleSrc(instr, 2, instr.common.src2, SRC2); |
| 478 | // SSE semantics match PICA200 ones: In case of NaN, SRC2 is returned. | ||
| 477 | MINPS(SRC1, R(SRC2)); | 479 | MINPS(SRC1, R(SRC2)); |
| 478 | Compile_DestEnable(instr, SRC1); | 480 | Compile_DestEnable(instr, SRC1); |
| 479 | } | 481 | } |