mirror of
https://github.com/reactos/reactos.git
synced 2024-08-21 02:43:48 +00:00
[SOFT386]
- Fix calculation of the AF flag in opcode groups 0xFE and 0xFF (INC/DEC). - Fix a bug in the REP prefix by simulating the wrap-around of DI which can occur when the current address size is 16-bit. - Exception error codes are only pushed on the stack in protected mode. svn path=/branches/ntvdm/; revision=60625
This commit is contained in:
parent
8dff09c37a
commit
a2e0e03ee6
|
@ -494,7 +494,8 @@ Soft386ExceptionWithErrorCode(PSOFT386_STATE State,
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (EXCEPTION_HAS_ERROR_CODE(ExceptionCode))
|
if (EXCEPTION_HAS_ERROR_CODE(ExceptionCode)
|
||||||
|
&& (State->ControlRegisters[SOFT386_REG_CR0] & SOFT386_CR0_PE))
|
||||||
{
|
{
|
||||||
/* Push the error code */
|
/* Push the error code */
|
||||||
Soft386StackPush(State, ErrorCode);
|
Soft386StackPush(State, ErrorCode);
|
||||||
|
|
|
@ -6168,6 +6168,15 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeStos)
|
||||||
{
|
{
|
||||||
ULONG Processed = min(Count, STRING_BLOCK_SIZE / DataSize);
|
ULONG Processed = min(Count, STRING_BLOCK_SIZE / DataSize);
|
||||||
|
|
||||||
|
/* Simulate the 16-bit wrap-around of DI in 16-bit address mode */
|
||||||
|
if (!AddressSize)
|
||||||
|
{
|
||||||
|
ULONG MaxBytes = 0x10000 - (ULONG)State->GeneralRegs[SOFT386_REG_EDI].LowWord;
|
||||||
|
|
||||||
|
Processed = min(Processed, MaxBytes / DataSize);
|
||||||
|
if (Processed == 0) Processed = 1;
|
||||||
|
}
|
||||||
|
|
||||||
if (State->Flags.Df)
|
if (State->Flags.Df)
|
||||||
{
|
{
|
||||||
/* Reduce EDI by the number of bytes to transfer */
|
/* Reduce EDI by the number of bytes to transfer */
|
||||||
|
@ -6437,6 +6446,15 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeIns)
|
||||||
{
|
{
|
||||||
ULONG Processed = min(Count, STRING_BLOCK_SIZE / DataSize);
|
ULONG Processed = min(Count, STRING_BLOCK_SIZE / DataSize);
|
||||||
|
|
||||||
|
/* Simulate the 16-bit wrap-around of DI in 16-bit address mode */
|
||||||
|
if (!AddressSize)
|
||||||
|
{
|
||||||
|
ULONG MaxBytes = 0x10000 - (ULONG)State->GeneralRegs[SOFT386_REG_EDI].LowWord;
|
||||||
|
|
||||||
|
Processed = min(Processed, MaxBytes / DataSize);
|
||||||
|
if (Processed == 0) Processed = 1;
|
||||||
|
}
|
||||||
|
|
||||||
/* Read from the I/O port */
|
/* Read from the I/O port */
|
||||||
State->IoReadCallback(State,
|
State->IoReadCallback(State,
|
||||||
State->GeneralRegs[SOFT386_REG_EDX].LowWord,
|
State->GeneralRegs[SOFT386_REG_EDX].LowWord,
|
||||||
|
@ -6574,6 +6592,15 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeOuts)
|
||||||
{
|
{
|
||||||
ULONG Processed = min(Count, STRING_BLOCK_SIZE / DataSize);
|
ULONG Processed = min(Count, STRING_BLOCK_SIZE / DataSize);
|
||||||
|
|
||||||
|
/* Simulate the 16-bit wrap-around of DI in 16-bit address mode */
|
||||||
|
if (!AddressSize)
|
||||||
|
{
|
||||||
|
ULONG MaxBytes = 0x10000 - (ULONG)State->GeneralRegs[SOFT386_REG_EDI].LowWord;
|
||||||
|
|
||||||
|
Processed = min(Processed, MaxBytes / DataSize);
|
||||||
|
if (Processed == 0) Processed = 1;
|
||||||
|
}
|
||||||
|
|
||||||
/* Read from memory */
|
/* Read from memory */
|
||||||
if (!Soft386ReadMemory(State,
|
if (!Soft386ReadMemory(State,
|
||||||
SOFT386_REG_ES,
|
SOFT386_REG_ES,
|
||||||
|
|
|
@ -1414,21 +1414,22 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeGroupFE)
|
||||||
|
|
||||||
if (ModRegRm.Register == 0)
|
if (ModRegRm.Register == 0)
|
||||||
{
|
{
|
||||||
/* Increment and update OF */
|
/* Increment and update OF and AF */
|
||||||
Value++;
|
Value++;
|
||||||
State->Flags.Of = (Value == SIGN_FLAG_BYTE) ? TRUE : FALSE;
|
State->Flags.Of = (Value == SIGN_FLAG_BYTE) ? TRUE : FALSE;
|
||||||
|
State->Flags.Af = ((Value & 0x0F) == 0);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
/* Decrement and update OF */
|
/* Decrement and update OF and AF */
|
||||||
State->Flags.Of = (Value == SIGN_FLAG_BYTE) ? TRUE : FALSE;
|
State->Flags.Of = (Value == SIGN_FLAG_BYTE) ? TRUE : FALSE;
|
||||||
Value--;
|
Value--;
|
||||||
|
State->Flags.Af = ((Value & 0x0F) == 0x0F);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Update flags */
|
/* Update flags */
|
||||||
State->Flags.Sf = (Value & SIGN_FLAG_BYTE) ? TRUE : FALSE;
|
State->Flags.Sf = (Value & SIGN_FLAG_BYTE) ? TRUE : FALSE;
|
||||||
State->Flags.Zf = (Value == 0) ? TRUE : FALSE;
|
State->Flags.Zf = (Value == 0) ? TRUE : FALSE;
|
||||||
State->Flags.Af = ((Value & 0x0F) == 0) ? TRUE : FALSE;
|
|
||||||
State->Flags.Pf = Soft386CalculateParity(Value);
|
State->Flags.Pf = Soft386CalculateParity(Value);
|
||||||
|
|
||||||
/* Write back the result */
|
/* Write back the result */
|
||||||
|
@ -1483,15 +1484,17 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeGroupFF)
|
||||||
|
|
||||||
if (ModRegRm.Register == 0)
|
if (ModRegRm.Register == 0)
|
||||||
{
|
{
|
||||||
/* Increment and update OF */
|
/* Increment and update OF and AF */
|
||||||
Value++;
|
Value++;
|
||||||
State->Flags.Of = (Value == SIGN_FLAG_LONG) ? TRUE : FALSE;
|
State->Flags.Of = (Value == SIGN_FLAG_LONG) ? TRUE : FALSE;
|
||||||
|
State->Flags.Af = ((Value & 0x0F) == 0);
|
||||||
}
|
}
|
||||||
else if (ModRegRm.Register == 1)
|
else if (ModRegRm.Register == 1)
|
||||||
{
|
{
|
||||||
/* Decrement and update OF */
|
/* Decrement and update OF and AF */
|
||||||
State->Flags.Of = (Value == SIGN_FLAG_LONG) ? TRUE : FALSE;
|
State->Flags.Of = (Value == SIGN_FLAG_LONG) ? TRUE : FALSE;
|
||||||
Value--;
|
Value--;
|
||||||
|
State->Flags.Af = ((Value & 0x0F) == 0x0F);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ModRegRm.Register <= 1)
|
if (ModRegRm.Register <= 1)
|
||||||
|
@ -1499,7 +1502,6 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeGroupFF)
|
||||||
/* Update flags */
|
/* Update flags */
|
||||||
State->Flags.Sf = (Value & SIGN_FLAG_LONG) ? TRUE : FALSE;
|
State->Flags.Sf = (Value & SIGN_FLAG_LONG) ? TRUE : FALSE;
|
||||||
State->Flags.Zf = (Value == 0) ? TRUE : FALSE;
|
State->Flags.Zf = (Value == 0) ? TRUE : FALSE;
|
||||||
State->Flags.Af = ((Value & 0x0F) == 0) ? TRUE : FALSE;
|
|
||||||
State->Flags.Pf = Soft386CalculateParity(Value);
|
State->Flags.Pf = Soft386CalculateParity(Value);
|
||||||
|
|
||||||
/* Write back the result */
|
/* Write back the result */
|
||||||
|
@ -1524,12 +1526,14 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeGroupFF)
|
||||||
/* Increment and update OF */
|
/* Increment and update OF */
|
||||||
Value++;
|
Value++;
|
||||||
State->Flags.Of = (Value == SIGN_FLAG_WORD) ? TRUE : FALSE;
|
State->Flags.Of = (Value == SIGN_FLAG_WORD) ? TRUE : FALSE;
|
||||||
|
State->Flags.Af = ((Value & 0x0F) == 0);
|
||||||
}
|
}
|
||||||
else if (ModRegRm.Register == 1)
|
else if (ModRegRm.Register == 1)
|
||||||
{
|
{
|
||||||
/* Decrement and update OF */
|
/* Decrement and update OF */
|
||||||
State->Flags.Of = (Value == SIGN_FLAG_WORD) ? TRUE : FALSE;
|
State->Flags.Of = (Value == SIGN_FLAG_WORD) ? TRUE : FALSE;
|
||||||
Value--;
|
Value--;
|
||||||
|
State->Flags.Af = ((Value & 0x0F) == 0x0F);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ModRegRm.Register <= 1)
|
if (ModRegRm.Register <= 1)
|
||||||
|
@ -1537,7 +1541,6 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeGroupFF)
|
||||||
/* Update flags */
|
/* Update flags */
|
||||||
State->Flags.Sf = (Value & SIGN_FLAG_WORD) ? TRUE : FALSE;
|
State->Flags.Sf = (Value & SIGN_FLAG_WORD) ? TRUE : FALSE;
|
||||||
State->Flags.Zf = (Value == 0) ? TRUE : FALSE;
|
State->Flags.Zf = (Value == 0) ? TRUE : FALSE;
|
||||||
State->Flags.Af = ((Value & 0x0F) == 0) ? TRUE : FALSE;
|
|
||||||
State->Flags.Pf = Soft386CalculateParity(Value);
|
State->Flags.Pf = Soft386CalculateParity(Value);
|
||||||
|
|
||||||
/* Write back the result */
|
/* Write back the result */
|
||||||
|
|
Loading…
Reference in a new issue