From a8c1104f57ec3b09a46bb44aca5a36e5d9783043 Mon Sep 17 00:00:00 2001 From: Aleksandar Andrejevic Date: Thu, 12 Sep 2013 00:05:23 +0000 Subject: [PATCH] [SOFT386] Implement ARPL. svn path=/branches/ntvdm/; revision=60050 --- lib/soft386/opcodes.c | 42 +++++++++++++++++++++++++++++++++++++++--- 1 file changed, 39 insertions(+), 3 deletions(-) diff --git a/lib/soft386/opcodes.c b/lib/soft386/opcodes.c index fb22ee0d280..bd4508a32d9 100644 --- a/lib/soft386/opcodes.c +++ b/lib/soft386/opcodes.c @@ -3583,10 +3583,46 @@ SOFT386_OPCODE_HANDLER(Soft386OpcodeBound) SOFT386_OPCODE_HANDLER(Soft386OpcodeArpl) { - // TODO: NOT IMPLEMENTED - UNIMPLEMENTED; + USHORT FirstValue, SecondValue; + SOFT386_MOD_REG_RM ModRegRm; - return FALSE; + if (!(State->ControlRegisters[SOFT386_REG_CR0] & SOFT386_CR0_PE) + || State->PrefixFlags) + { + /* No prefixes allowed, protected mode only */ + Soft386Exception(State, SOFT386_EXCEPTION_UD); + return FALSE; + } + + /* Get the operands */ + if (!Soft386ReadModrmWordOperands(State, + &ModRegRm, + &FirstValue, + &SecondValue)) + { + /* Exception occurred */ + return FALSE; + } + + /* Check if the RPL needs adjusting */ + if ((SecondValue & 3) < (FirstValue & 3)) + { + /* Adjust the RPL */ + SecondValue &= ~3; + SecondValue |= FirstValue & 3; + + /* Set ZF */ + State->Flags.Zf = TRUE; + + /* Write back the result */ + return Soft386WriteModrmWordOperands(State, &ModRegRm, FALSE, SecondValue); + } + else + { + /* Clear ZF */ + State->Flags.Zf = FALSE; + return TRUE; + } } SOFT386_OPCODE_HANDLER(Soft386OpcodePushImm)