Author: aandrejevic
Date: Sat Jun 13 23:12:55 2015
New Revision: 68125
URL:
http://svn.reactos.org/svn/reactos?rev=68125&view=rev
Log:
[FAST486]
FPU exceptions are delayed until the next non-control FPU instruction.
Modified:
trunk/reactos/lib/fast486/common.inl
trunk/reactos/lib/fast486/fpu.c
trunk/reactos/lib/fast486/opcodes.c
Modified: trunk/reactos/lib/fast486/common.inl
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/lib/fast486/common.inl?rev…
==============================================================================
--- trunk/reactos/lib/fast486/common.inl [iso-8859-1] (original)
+++ trunk/reactos/lib/fast486/common.inl [iso-8859-1] Sat Jun 13 23:12:55 2015
@@ -1604,17 +1604,26 @@
FORCEINLINE
VOID
FASTCALL
-Fast486FpuException(PFAST486_STATE State)
-{
- if (State->ControlRegisters[FAST486_REG_CR0] & FAST486_CR0_NE)
- {
- /* Call the #MF handler */
- Fast486Exception(State, FAST486_EXCEPTION_MF);
- }
- else
- {
- /* Use the external interrupt */
- State->FpuCallback(State);
+Fast486FpuExceptionCheck(PFAST486_STATE State)
+{
+ /* Check if an unmasked exception occurred */
+ if ((State->FpuStatus.Ie && !State->FpuControl.Im)
+ || (State->FpuStatus.De && !State->FpuControl.Dm)
+ || (State->FpuStatus.Ze && !State->FpuControl.Zm)
+ || (State->FpuStatus.Oe && !State->FpuControl.Om)
+ || (State->FpuStatus.Ue && !State->FpuControl.Um)
+ || (State->FpuStatus.Pe && !State->FpuControl.Pm))
+ {
+ if (State->ControlRegisters[FAST486_REG_CR0] & FAST486_CR0_NE)
+ {
+ /* Call the #MF handler */
+ Fast486Exception(State, FAST486_EXCEPTION_MF);
+ }
+ else
+ {
+ /* Use the external interrupt */
+ State->FpuCallback(State);
+ }
}
}
@@ -1654,7 +1663,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1695,7 +1703,6 @@
/* Set the C1 condition code bit (stack overflow) */
State->FpuStatus.Code1 = TRUE;
- if (!State->FpuControl.Im) Fast486FpuException(State);
return FALSE;
}
}
@@ -1720,7 +1727,6 @@
/* Clear the C1 condition code bit (stack underflow) */
State->FpuStatus.Code1 = FALSE;
- if (!State->FpuControl.Im) Fast486FpuException(State);
return FALSE;
}
}
Modified: trunk/reactos/lib/fast486/fpu.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/lib/fast486/fpu.c?rev=6812…
==============================================================================
--- trunk/reactos/lib/fast486/fpu.c [iso-8859-1] (original)
+++ trunk/reactos/lib/fast486/fpu.c [iso-8859-1] Sat Jun 13 23:12:55 2015
@@ -490,7 +490,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -589,7 +588,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -608,7 +606,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -688,7 +685,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -707,7 +703,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -803,7 +798,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -897,7 +891,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1049,7 +1042,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1072,7 +1064,6 @@
if (!State->FpuControl.Um)
{
- Fast486FpuException(State);
return FALSE;
}
@@ -1090,7 +1081,6 @@
if (!State->FpuControl.Om)
{
- Fast486FpuException(State);
return FALSE;
}
@@ -1139,7 +1129,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1159,7 +1148,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1299,7 +1287,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1315,7 +1302,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
return FALSE;
}
@@ -1590,7 +1576,6 @@
}
else
{
- Fast486FpuException(State);
return FALSE;
}
}
@@ -1842,6 +1827,7 @@
#ifndef FAST486_NO_FPU
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
@@ -1858,7 +1844,6 @@
FPU_SET_TAG(0, FPU_TAG_SPECIAL);
}
- else Fast486FpuException(State);
return;
}
@@ -1895,7 +1880,6 @@
FPU_SET_TAG(0, FPU_TAG_SPECIAL);
}
- else Fast486FpuException(State);
return;
}
@@ -1940,6 +1924,7 @@
ULONG Value;
FAST486_FPU_DATA_REG MemoryData;
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
FPU_SAVE_LAST_OPERAND();
@@ -1962,6 +1947,7 @@
{
ULONG Value = FPU_REAL4_INDEFINITE;
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
FPU_SAVE_LAST_OPERAND();
@@ -1972,7 +1958,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -2050,6 +2035,9 @@
case 0x06:
case 0x07:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(ModRegRm.SecondRegister) == FPU_TAG_EMPTY)
{
/* Raise the invalid operation exception */
@@ -2057,7 +2045,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -2078,12 +2065,13 @@
{
FAST486_FPU_DATA_REG Temp;
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if ((FPU_GET_TAG(0) == FPU_TAG_EMPTY)
|| FPU_GET_TAG(ModRegRm.SecondRegister) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2115,6 +2103,9 @@
case 0x1E:
case 0x1F:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
FPU_ST(ModRegRm.SecondRegister) = FPU_ST(0);
FPU_UPDATE_TAG(ModRegRm.SecondRegister);
@@ -2125,11 +2116,12 @@
/* FCHS */
case 0x20:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2142,11 +2134,12 @@
/* FABS */
case 0x21:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2159,6 +2152,9 @@
/* FTST */
case 0x24:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
Fast486FpuCompare(State, &FPU_ST(0), &FpuZero);
break;
}
@@ -2166,6 +2162,9 @@
/* FXAM */
case 0x25:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
/* The sign bit goes in C1, even if the register's empty */
State->FpuStatus.Code1 = FPU_ST(0).Sign;
@@ -2241,6 +2240,9 @@
&FpuZero
};
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
Fast486FpuPush(State, Constants[ModRegRm.SecondRegister]);
break;
}
@@ -2248,13 +2250,12 @@
/* F2XM1 */
case 0x30:
{
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2264,7 +2265,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
break;
}
}
@@ -2280,11 +2280,12 @@
{
FAST486_FPU_DATA_REG Logarithm;
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY || FPU_GET_TAG(1) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2313,6 +2314,9 @@
FAST486_FPU_DATA_REG Sine;
FAST486_FPU_DATA_REG Cosine;
ULONGLONG Quadrant;
+
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
/* Compute the sine */
if (!Fast486FpuCalculateSine(State, &FPU_ST(0), &Sine)) break;
@@ -2351,6 +2355,9 @@
/* FPATAN */
case 0x33:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (!Fast486FpuCalculateArcTangent(State,
&FPU_ST(1),
&FPU_ST(0),
@@ -2370,12 +2377,13 @@
{
FAST486_FPU_DATA_REG Value = FPU_ST(0);
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if ((FPU_GET_TAG(0) == FPU_TAG_EMPTY) || FPU_IS_INDEFINITE(&Value))
{
State->FpuStatus.Ie = TRUE;
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY) State->FpuStatus.Sf = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2411,11 +2419,12 @@
/* FPREM1 */
case 0x35:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY || FPU_GET_TAG(1) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2442,11 +2451,12 @@
/* FPREM */
case 0x38:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY || FPU_GET_TAG(1) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2461,11 +2471,12 @@
{
FAST486_FPU_DATA_REG Value, Logarithm;
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY || FPU_GET_TAG(1) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2497,6 +2508,9 @@
/* FSQRT */
case 0x3A:
{
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
Fast486FpuCalculateSquareRoot(State, &FPU_ST(0), &FPU_ST(0));
FPU_UPDATE_TAG(0);
@@ -2507,13 +2521,13 @@
case 0x3B:
{
FAST486_FPU_DATA_REG Number = FPU_ST(0);
+
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2523,7 +2537,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
break;
}
}
@@ -2544,11 +2557,12 @@
{
LONGLONG Result = 0LL;
+ Fast486FpuExceptionCheck(State);
+ FPU_SAVE_LAST_INST();
+
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2558,7 +2572,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
break;
}
}
@@ -2571,8 +2584,6 @@
Fast486FpuFromInteger(State, Result, &FPU_ST(0));
State->FpuStatus.Pe = TRUE;
- if (!State->FpuControl.Pm) Fast486FpuException(State);
-
break;
}
@@ -2583,13 +2594,12 @@
LONGLONG UnbiasedExp = (LONGLONG)((SHORT)FPU_ST(0).Exponent) -
FPU_REAL10_BIAS;
INT OldRoundingMode = State->FpuControl.Rc;
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY || FPU_GET_TAG(1) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2599,7 +2609,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
break;
}
}
@@ -2629,10 +2638,6 @@
/* Make the result zero */
FPU_ST(0) = FpuZero;
FPU_UPDATE_TAG(0);
- }
- else
- {
- Fast486FpuException(State);
}
break;
@@ -2651,10 +2656,6 @@
FPU_ST(0).Exponent = FPU_MAX_EXPONENT + 1;
FPU_UPDATE_TAG(0);
}
- else
- {
- Fast486FpuException(State);
- }
break;
}
@@ -2668,13 +2669,12 @@
/* FSIN */
case 0x3E:
{
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2684,7 +2684,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
break;
}
}
@@ -2698,13 +2697,12 @@
/* FCOS */
case 0x3F:
{
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (FPU_GET_TAG(0) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -2714,7 +2712,6 @@
if (!State->FpuControl.Dm)
{
- Fast486FpuException(State);
break;
}
}
@@ -2759,6 +2756,7 @@
#ifndef FAST486_NO_FPU
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (!ModRegRm.Memory)
@@ -2774,8 +2772,6 @@
{
/* Raise the invalid operation exception*/
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
return;
}
@@ -2812,7 +2808,6 @@
FPU_SET_TAG(0, FPU_TAG_SPECIAL);
}
- else Fast486FpuException(State);
return;
}
@@ -2845,6 +2840,7 @@
if (ModRegRm.Memory)
{
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
FPU_SAVE_LAST_OPERAND();
@@ -2882,7 +2878,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -2904,7 +2899,6 @@
}
else
{
- Fast486FpuException(State);
return;
}
}
@@ -2973,7 +2967,6 @@
}
else
{
- Fast486FpuException(State);
return;
}
}
@@ -3081,6 +3074,7 @@
#ifndef FAST486_NO_FPU
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
if (ModRegRm.Memory)
@@ -3101,7 +3095,6 @@
FPU_SET_TAG(0, FPU_TAG_SPECIAL);
}
- else Fast486FpuException(State);
return;
}
@@ -3144,7 +3137,6 @@
FPU_SET_TAG(ModRegRm.SecondRegister, FPU_TAG_SPECIAL);
}
- else Fast486FpuException(State);
return;
}
@@ -3186,6 +3178,7 @@
ULONGLONG Value;
FAST486_FPU_DATA_REG MemoryData;
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
FPU_SAVE_LAST_OPERAND();
@@ -3214,6 +3207,7 @@
{
ULONGLONG Value = FPU_REAL8_INDEFINITE;
+ Fast486FpuExceptionCheck(State);
FPU_SAVE_LAST_INST();
FPU_SAVE_LAST_OPERAND();
@@ -3224,7 +3218,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -3352,8 +3345,6 @@
}
else
{
- FPU_SAVE_LAST_INST();
-
switch (ModRegRm.Register)
{
/* FFREE */
@@ -3368,12 +3359,13 @@
{
FAST486_FPU_DATA_REG Temp;
+ FPU_SAVE_LAST_INST();
+ Fast486FpuExceptionCheck(State);
+
if ((FPU_GET_TAG(0) == FPU_TAG_EMPTY)
|| FPU_GET_TAG(ModRegRm.SecondRegister) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
@@ -3393,6 +3385,9 @@
/* FSTP */
case 3:
{
+ FPU_SAVE_LAST_INST();
+ Fast486FpuExceptionCheck(State);
+
FPU_ST(ModRegRm.SecondRegister) = FPU_ST(0);
FPU_UPDATE_TAG(ModRegRm.SecondRegister);
@@ -3405,12 +3400,13 @@
/* FUCOMP */
case 5:
{
+ FPU_SAVE_LAST_INST();
+ Fast486FpuExceptionCheck(State);
+
if ((FPU_GET_TAG(0) == FPU_TAG_EMPTY)
|| (FPU_GET_TAG(ModRegRm.SecondRegister) == FPU_TAG_EMPTY))
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
return;
}
@@ -3454,6 +3450,7 @@
#ifndef FAST486_NO_FPU
FPU_SAVE_LAST_INST();
+ Fast486FpuExceptionCheck(State);
if (ModRegRm.Memory)
{
@@ -3473,7 +3470,6 @@
FPU_SET_TAG(0, FPU_TAG_SPECIAL);
}
- else Fast486FpuException(State);
return;
}
@@ -3508,8 +3504,6 @@
{
/* Raise the invalid operation exception, if unmasked */
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
return;
}
}
@@ -3540,6 +3534,7 @@
#ifndef FAST486_NO_FPU
FPU_SAVE_LAST_INST();
+ Fast486FpuExceptionCheck(State);
if (ModRegRm.Memory)
{
@@ -3579,7 +3574,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -3602,7 +3596,6 @@
}
else
{
- Fast486FpuException(State);
return;
}
}
@@ -3682,7 +3675,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -3719,7 +3711,6 @@
if (!State->FpuControl.Im)
{
- Fast486FpuException(State);
return;
}
}
@@ -3776,8 +3767,6 @@
|| FPU_GET_TAG(ModRegRm.SecondRegister) == FPU_TAG_EMPTY)
{
State->FpuStatus.Ie = TRUE;
-
- if (!State->FpuControl.Im) Fast486FpuException(State);
break;
}
Modified: trunk/reactos/lib/fast486/opcodes.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/lib/fast486/opcodes.c?rev=…
==============================================================================
--- trunk/reactos/lib/fast486/opcodes.c [iso-8859-1] (original)
+++ trunk/reactos/lib/fast486/opcodes.c [iso-8859-1] Sat Jun 13 23:12:55 2015
@@ -3974,17 +3974,7 @@
FAST486_OPCODE_HANDLER(Fast486OpcodeWait)
{
#ifndef FAST486_NO_FPU
-
- if ((!State->FpuControl.Pm && State->FpuStatus.Pe)
- || (!State->FpuControl.Um && State->FpuStatus.Ue)
- || (!State->FpuControl.Om && State->FpuStatus.Oe)
- || (!State->FpuControl.Zm && State->FpuStatus.Ze)
- || (!State->FpuControl.Dm && State->FpuStatus.De)
- || (!State->FpuControl.Im && State->FpuStatus.Ie))
- {
- Fast486FpuException(State);
- }
-
+ Fast486FpuExceptionCheck(State);
#endif
}