summaryrefslogtreecommitdiff
path: root/Source/Core
diff options
context:
space:
mode:
authorFiora <fioraaeterna@gmail.com>2015-02-22 07:53:52 -0800
committerFiora <fioraaeterna@gmail.com>2015-02-22 07:53:52 -0800
commit8cd32e171a3a100b0f08b2b49f8864c348a4266f (patch)
treefbf4d5c6ad171593b160e2b0e8147eb60f190fd0 /Source/Core
parent860c889454635c0f4f7cf601f8ec77c7b81c19cd (diff)
parentbfa5dcc8913def1e1decf8e834cb64694ed0aa5d (diff)
Merge pull request #2095 from lioncash/correctness
Interpreter: Set the FPCC bits correctly for ordered/unordered compares.
Diffstat (limited to 'Source/Core')
-rw-r--r--Source/Core/Core/PowerPC/Interpreter/Interpreter_FloatingPoint.cpp57
1 files changed, 31 insertions, 26 deletions
diff --git a/Source/Core/Core/PowerPC/Interpreter/Interpreter_FloatingPoint.cpp b/Source/Core/Core/PowerPC/Interpreter/Interpreter_FloatingPoint.cpp
index 31850a1c25..26cb1edf7d 100644
--- a/Source/Core/Core/PowerPC/Interpreter/Interpreter_FloatingPoint.cpp
+++ b/Source/Core/Core/PowerPC/Interpreter/Interpreter_FloatingPoint.cpp
@@ -22,19 +22,7 @@ void Interpreter::Helper_FloatCompareOrdered(UGeckoInstruction _inst, double fa,
{
int compareResult;
- if (fa < fb)
- {
- compareResult = FPCC::FL;
- }
- else if (fa > fb)
- {
- compareResult = FPCC::FG;
- }
- else if (fa == fb)
- {
- compareResult = FPCC::FE;
- }
- else // NaN
+ if (IsNAN(fa) || IsNAN(fb))
{
FPSCR.FX = 1;
compareResult = FPCC::FU;
@@ -51,16 +39,7 @@ void Interpreter::Helper_FloatCompareOrdered(UGeckoInstruction _inst, double fa,
SetFPException(FPSCR_VXVC);
}
}
-
- FPSCR.FPRF = compareResult;
- SetCRField(_inst.CRFD, compareResult);
-}
-
-void Interpreter::Helper_FloatCompareUnordered(UGeckoInstruction _inst, double fa, double fb)
-{
- int compareResult;
-
- if (fa < fb)
+ else if (fa < fb)
{
compareResult = FPCC::FL;
}
@@ -68,21 +47,47 @@ void Interpreter::Helper_FloatCompareUnordered(UGeckoInstruction _inst, double f
{
compareResult = FPCC::FG;
}
- else if (fa == fb)
+ else // Equals
{
compareResult = FPCC::FE;
}
- else
+
+ // Clear and set the FPCC bits accordingly.
+ FPSCR.FPRF = (FPSCR.FPRF & ~0xF) | compareResult;
+
+ SetCRField(_inst.CRFD, compareResult);
+}
+
+void Interpreter::Helper_FloatCompareUnordered(UGeckoInstruction _inst, double fa, double fb)
+{
+ int compareResult;
+
+ if (IsNAN(fa) || IsNAN(fb))
{
compareResult = FPCC::FU;
+
if (IsSNAN(fa) || IsSNAN(fb))
{
FPSCR.FX = 1;
SetFPException(FPSCR_VXSNAN);
}
}
+ else if (fa < fb)
+ {
+ compareResult = FPCC::FL;
+ }
+ else if (fa > fb)
+ {
+ compareResult = FPCC::FG;
+ }
+ else // Equals
+ {
+ compareResult = FPCC::FE;
+ }
+
+ // Clear and set the FPCC bits accordingly.
+ FPSCR.FPRF = (FPSCR.FPRF & ~0xF) | compareResult;
- FPSCR.FPRF = compareResult;
SetCRField(_inst.CRFD, compareResult);
}