Fixed compilation error for 486 CPU

small fixes for IRET instructionm
This commit is contained in:
Stanislav Shwartsman 2005-03-12 16:40:14 +00:00
parent 75bf07a22a
commit 2a5a5c2de5
4 changed files with 53 additions and 89 deletions

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: cpu.h,v 1.202 2005-03-09 22:01:12 sshwarts Exp $
// $Id: cpu.h,v 1.203 2005-03-12 16:40:12 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -2662,9 +2662,6 @@ public: // for now...
BX_SMF void call_protected(bxInstruction_c *, Bit16u cs, bx_address disp) BX_CPP_AttrRegparmN(3);
BX_SMF void return_protected(bxInstruction_c *, Bit16u pop_bytes) BX_CPP_AttrRegparmN(2);
BX_SMF void iret_protected(bxInstruction_c *) BX_CPP_AttrRegparmN(1);
#if BX_CPU_LEVEL >= 5
BX_SMF bx_bool iret32_real(bxInstruction_c *) BX_CPP_AttrRegparmN(1);
#endif
BX_SMF void validate_seg_regs(void);
BX_SMF void stack_return_to_v86(Bit32u new_eip, Bit32u raw_cs_selector,
Bit32u flags32);

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: ctrl_xfer16.cc,v 1.27 2005-02-16 21:26:50 sshwarts Exp $
// $Id: ctrl_xfer16.cc,v 1.28 2005-03-12 16:40:14 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -83,7 +83,6 @@ void BX_CPU_C::RETnear16(bxInstruction_c *i)
void BX_CPU_C::RETfar16_Iw(bxInstruction_c *i)
{
BailBigRSP("RETfar16_Iw");
Bit16s imm16;
Bit16u ip, cs_raw;
@ -189,7 +188,7 @@ void BX_CPU_C::CALL16_Ap(bxInstruction_c *i)
if (protected_mode()) {
BX_CPU_THIS_PTR call_protected(i, cs_raw, disp16);
goto done;
}
}
#endif
push_16(BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.value);
@ -212,10 +211,10 @@ void BX_CPU_C::CALL_Ew(bxInstruction_c *i)
if (i->modC0()) {
op1_16 = BX_READ_16BIT_REG(i->rm());
}
}
else {
read_virtual_word(i->seg(), RMAddr(i), &op1_16);
}
}
#if BX_CPU_LEVEL >= 2
if (op1_16 > BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].cache.u.segment.limit_scaled)
@ -245,7 +244,7 @@ void BX_CPU_C::CALL16_Ep(bxInstruction_c *i)
if (i->modC0()) {
BX_INFO(("CALL_Ep: op1 is a register"));
exception(BX_UD_EXCEPTION, 0, 0);
}
}
read_virtual_word(i->seg(), RMAddr(i), &op1_16);
read_virtual_word(i->seg(), RMAddr(i)+2, &cs_raw);
@ -253,7 +252,7 @@ void BX_CPU_C::CALL16_Ep(bxInstruction_c *i)
if ( protected_mode() ) {
BX_CPU_THIS_PTR call_protected(i, cs_raw, op1_16);
goto done;
}
}
push_16(BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS].selector.value);
push_16(IP);
@ -301,7 +300,7 @@ void BX_CPU_C::JCC_Jw(bxInstruction_c *i)
default:
condition = 0; // For compiler...all targets should set condition.
break;
}
}
if (condition) {
Bit32u new_EIP = EIP + (Bit32s) i->Id();
@ -312,7 +311,7 @@ void BX_CPU_C::JCC_Jw(bxInstruction_c *i)
#if BX_INSTRUMENTATION
else {
BX_INSTR_CNEAR_BRANCH_NOT_TAKEN(BX_CPU_ID);
}
}
#endif
}
@ -327,7 +326,7 @@ void BX_CPU_C::JZ_Jw(bxInstruction_c *i)
#if BX_INSTRUMENTATION
else {
BX_INSTR_CNEAR_BRANCH_NOT_TAKEN(BX_CPU_ID);
}
}
#endif
}
@ -342,7 +341,7 @@ void BX_CPU_C::JNZ_Jw(bxInstruction_c *i)
#if BX_INSTRUMENTATION
else {
BX_INSTR_CNEAR_BRANCH_NOT_TAKEN(BX_CPU_ID);
}
}
#endif
}
@ -352,10 +351,10 @@ void BX_CPU_C::JMP_Ew(bxInstruction_c *i)
if (i->modC0()) {
op1_16 = BX_READ_16BIT_REG(i->rm());
}
}
else {
read_virtual_word(i->seg(), RMAddr(i), &op1_16);
}
}
Bit32u new_EIP = op1_16;
branch_near32(new_EIP);
@ -366,7 +365,6 @@ void BX_CPU_C::JMP_Ew(bxInstruction_c *i)
void BX_CPU_C::JMP16_Ep(bxInstruction_c *i)
{
BailBigRSP("JMP16_Ep");
Bit16u cs_raw;
Bit16u op1_16;
@ -376,7 +374,7 @@ BailBigRSP("JMP16_Ep");
/* far indirect must specify a memory address */
BX_INFO(("JMP_Ep(): op1 is a register"));
exception(BX_UD_EXCEPTION, 0, 0);
}
}
read_virtual_word(i->seg(), RMAddr(i), &op1_16);
read_virtual_word(i->seg(), RMAddr(i)+2, &cs_raw);
@ -385,7 +383,7 @@ BailBigRSP("JMP16_Ep");
if ( protected_mode() ) {
BX_CPU_THIS_PTR jump_protected(i, cs_raw, op1_16);
goto done;
}
}
#endif
EIP = op1_16;
@ -398,7 +396,6 @@ done:
void BX_CPU_C::IRET16(bxInstruction_c *i)
{
BailBigRSP("IRET16");
Bit16u ip, cs_raw, flags;
invalidate_prefetch_q();
@ -412,15 +409,20 @@ BailBigRSP("IRET16");
// IOPL check in stack_return_from_v86()
stack_return_from_v86(i);
goto done;
}
}
#if BX_CPU_LEVEL >= 2
if (BX_CPU_THIS_PTR cr0.pe) {
iret_protected(i);
goto done;
}
}
#endif
if (! can_pop(6)) {
BX_PANIC(("IRET: top 6 bytes of stack not within stack limits"));
exception(BX_SS_EXCEPTION, 0, 0);
}
pop_16(&ip);
pop_16(&cs_raw);
pop_16(&flags);

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: ctrl_xfer32.cc,v 1.38 2005-02-16 21:26:50 sshwarts Exp $
// $Id: ctrl_xfer32.cc,v 1.39 2005-03-12 16:40:14 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -67,7 +67,6 @@ void BX_CPU_C::RETnear32(bxInstruction_c *i)
void BX_CPU_C::RETfar32_Iw(bxInstruction_c *i)
{
BailBigRSP("RETfar32_Iw");
Bit32u eip, ecs_raw;
Bit16s imm16;
@ -101,7 +100,6 @@ done:
void BX_CPU_C::RETfar32(bxInstruction_c *i)
{
BailBigRSP("RETfar32");
Bit32u eip, ecs_raw;
invalidate_prefetch_q();
@ -149,7 +147,6 @@ BailBigRSP("CALL_Ad");
void BX_CPU_C::CALL32_Ap(bxInstruction_c *i)
{
BailBigRSP("CALL32_Ap");
Bit16u cs_raw;
Bit32u disp32;
@ -206,7 +203,6 @@ void BX_CPU_C::CALL_Ed(bxInstruction_c *i)
void BX_CPU_C::CALL32_Ep(bxInstruction_c *i)
{
BailBigRSP("CALL32_Ep");
Bit16u cs_raw;
Bit32u op1_32;
@ -286,7 +282,7 @@ void BX_CPU_C::JCC_Jd(bxInstruction_c *i)
#if BX_INSTRUMENTATION
else {
BX_INSTR_CNEAR_BRANCH_NOT_TAKEN(BX_CPU_ID);
}
}
#endif
}
@ -320,7 +316,6 @@ void BX_CPU_C::JNZ_Jd(bxInstruction_c *i)
void BX_CPU_C::JMP_Ap(bxInstruction_c *i)
{
BailBigRSP("JMP_Ap");
Bit32u disp32;
Bit16u cs_raw;
@ -369,7 +364,6 @@ void BX_CPU_C::JMP_Ed(bxInstruction_c *i)
void BX_CPU_C::JMP32_Ep(bxInstruction_c *i)
{
BailBigRSP("JMP32_Ep");
Bit16u cs_raw;
Bit32u op1_32;
@ -401,8 +395,6 @@ done:
void BX_CPU_C::IRET32(bxInstruction_c *i)
{
BailBigRSP("IRET32");
invalidate_prefetch_q();
#if BX_DEBUGGER
@ -421,8 +413,31 @@ BailBigRSP("IRET32");
goto done;
}
if (iret32_real(i))
goto done;
Bit32u eip, ecs, eflags;
if (! can_pop(12)) {
BX_PANIC(("IRETD: to 12 bytes of stack not within stack limits"));
exception(BX_SS_EXCEPTION, 0, 0);
}
access_linear(BX_CPU_THIS_PTR get_segment_base(BX_SEG_REG_SS) + ESP,
4, CPL == 3, BX_READ, &eip);
// still need to be validated !
if (eip > 0xffff) {
BX_PANIC(("IRETD: instruction pointer not within code segment limits"));
exception(BX_GP_EXCEPTION, 0, 0);
}
pop_32(&eip);
pop_32(&ecs);
pop_32(&eflags);
ecs &= 0xffff;
eflags = (eflags & 0x257fd5) | (read_eflags() & 0x1a0000);
load_seg_reg(&BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS], (Bit16u)ecs);
EIP = eip;
writeEFlags(eflags, 0xffffffff);
done:
BX_INSTR_FAR_BRANCH(BX_CPU_ID, BX_INSTR_IS_IRET,

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////
// $Id: ctrl_xfer_pro.cc,v 1.33 2005-03-04 21:03:22 sshwarts Exp $
// $Id: ctrl_xfer_pro.cc,v 1.34 2005-03-12 16:40:14 sshwarts Exp $
/////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2001 MandrakeSoft S.A.
@ -36,7 +36,6 @@
#endif
#if BX_CPU_LEVEL >= 2
void BX_CPP_AttrRegparmN(3)
BX_CPU_C::jump_protected(bxInstruction_c *i, Bit16u cs_raw, bx_address dispBig)
{
@ -423,10 +422,7 @@ BX_CPU_C::jump_protected(bxInstruction_c *i, Bit16u cs_raw, bx_address dispBig)
}
}
}
#endif /* if BX_CPU_LEVEL >= 2 */
#if BX_CPU_LEVEL >= 2
void BX_CPP_AttrRegparmN(3)
BX_CPU_C::call_protected(bxInstruction_c *i, Bit16u cs_raw, bx_address dispBig)
{
@ -1002,10 +998,7 @@ BX_CPU_C::call_protected(bxInstruction_c *i, Bit16u cs_raw, bx_address dispBig)
BX_PANIC(("call_protected: shouldn't get here!"));
}
#endif /* 286+ */
#if BX_CPU_LEVEL >= 2
void BX_CPP_AttrRegparmN(2)
BX_CPU_C::return_protected(bxInstruction_c *i, Bit16u pop_bytes)
{
@ -1027,7 +1020,6 @@ BX_CPU_C::return_protected(bxInstruction_c *i, Bit16u pop_bytes)
/* + 2: CS | + 4: CS */
/* + 0: IP | + 0: EIP */
#if BX_CPU_LEVEL >= 3
if ( i->os32L() ) {
/* operand size=32: third word on stack must be within stack limits,
* else #SS(0); */
@ -1039,9 +1031,7 @@ BX_CPU_C::return_protected(bxInstruction_c *i, Bit16u pop_bytes)
stack_cs_offset = 4;
stack_param_offset = 8;
}
else
#endif
{
else {
/* operand size=16: second word on stack must be within stack limits,
* else #SS(0); */
if ( !can_pop(4) ) {
@ -1130,14 +1120,11 @@ BX_CPU_C::return_protected(bxInstruction_c *i, Bit16u pop_bytes)
return;
}
#if BX_CPU_LEVEL >= 3
if (i->os32L()) {
access_linear(BX_CPU_THIS_PTR get_segment_base(BX_SEG_REG_SS) + temp_ESP + 0,
4, CPL==3, BX_READ, &return_EIP);
}
else
#endif
{
}
else {
access_linear(BX_CPU_THIS_PTR get_segment_base(BX_SEG_REG_SS) + temp_ESP + 0,
2, CPL==3, BX_READ, &return_IP);
return_EIP = return_IP;
@ -1340,41 +1327,7 @@ BX_CPU_C::return_protected(bxInstruction_c *i, Bit16u pop_bytes)
validate_seg_regs();
}
}
#endif
#if BX_CPU_LEVEL >= 5
bx_bool BX_CPP_AttrRegparmN(1)
BX_CPU_C::iret32_real(bxInstruction_c *i)
{ Bit32u eip, ecs, efl;
if (ESP + 12 > 0xffff)
{
BX_PANIC(("iretd: to 12 bytes of stack not within stack limits"));
exception(BX_SS_EXCEPTION, 0, 0);
return 0;
}
access_linear(BX_CPU_THIS_PTR get_segment_base(BX_SEG_REG_SS) + ESP,
4, CPL == 3, BX_READ, &eip);
if (eip > 0xffff)
{
BX_PANIC(("iretd: instruction pointer not within code segment limits"));
exception(BX_GP_EXCEPTION, 0, 0);
return 0;
}
pop_32(&eip);
pop_32(&ecs);
pop_32(&efl);
ecs &= 0xffff;
efl = (efl & 0x257fd5) | ( read_eflags() & 0x1a0000);
load_seg_reg(&BX_CPU_THIS_PTR sregs[BX_SEG_REG_CS], (Bit16u)ecs);
EIP = eip;
writeEFlags(efl, 0xffffffff);
return 1;
}
#endif
#if BX_CPU_LEVEL >= 2
void BX_CPP_AttrRegparmN(1)
BX_CPU_C::iret_protected(bxInstruction_c *i)
{
@ -1988,9 +1941,7 @@ BX_CPU_C::iret_protected(bxInstruction_c *i)
BX_PANIC(("IRET: shouldn't get here!"));
}
#endif
#if BX_CPU_LEVEL >= 2
void BX_CPP_AttrRegparmN(1) BX_CPU_C::branch_near32(Bit32u new_EIP)
{
// check always, not only in protected mode
@ -2028,4 +1979,3 @@ void BX_CPU_C::validate_seg_regs(void)
BX_CPU_THIS_PTR sregs[BX_SEG_REG_GS].selector.value = 0;
}
}
#endif