mirror of
https://github.com/FEX-Emu/FEX.git
synced 2026-10-14 10:00:42 +02:00
Merge pull request #1555 from Sonicadvance1/weirdo_edge_case
OpcodeDispatcher: Fixes weirdo edge case in segment moving
This commit is contained in:
4 files changed
+62
-4
No files matched your search
+13
-1
@@ -1573,19 +1573,24 @@ void OpDispatchBuilder::MOVSegOp(OpcodeArgs) {
|
||||
|
||||
switch (Op->Dest.Data.GPR.GPR) {
|
||||
case 0: // ES
|
||||
case FEXCore::X86State::REG_R8: // ES
|
||||
_StoreContext(GPRClass, 2, offsetof(FEXCore::Core::CPUState, es), Src);
|
||||
break;
|
||||
case 1: // DS
|
||||
case FEXCore::X86State::REG_R11: // DS
|
||||
_StoreContext(GPRClass, 2, offsetof(FEXCore::Core::CPUState, ds), Src);
|
||||
break;
|
||||
case 2: // CS
|
||||
case FEXCore::X86State::REG_R9: // CS
|
||||
// CPL3 can't write to this
|
||||
_Break(FEXCore::IR::Break_InvalidInstruction, 0);
|
||||
break;
|
||||
case 3: // SS
|
||||
case FEXCore::X86State::REG_R10: // SS
|
||||
_StoreContext(GPRClass, 2, offsetof(FEXCore::Core::CPUState, ss), Src);
|
||||
break;
|
||||
case 6: // GS
|
||||
case FEXCore::X86State::REG_R13: // GS
|
||||
if (!CTX->Config.Is64BitMode) {
|
||||
_StoreContext(GPRClass, 2, offsetof(FEXCore::Core::CPUState, gs), Src);
|
||||
} else {
|
||||
@@ -1594,6 +1599,7 @@ void OpDispatchBuilder::MOVSegOp(OpcodeArgs) {
|
||||
}
|
||||
break;
|
||||
case 7: // FS
|
||||
case FEXCore::X86State::REG_R12: // FS
|
||||
if (!CTX->Config.Is64BitMode) {
|
||||
_StoreContext(GPRClass, 2, offsetof(FEXCore::Core::CPUState, fs), Src);
|
||||
} else {
|
||||
@@ -1602,7 +1608,7 @@ void OpDispatchBuilder::MOVSegOp(OpcodeArgs) {
|
||||
}
|
||||
break;
|
||||
default:
|
||||
LogMan::Msg::EFmt("Unknown segment register: %d", Op->Dest.Data.GPR.GPR);
|
||||
LogMan::Msg::EFmt("Unknown segment register: {}", Op->Dest.Data.GPR.GPR);
|
||||
DecodeFailure = true;
|
||||
break;
|
||||
}
|
||||
@@ -1612,18 +1618,23 @@ void OpDispatchBuilder::MOVSegOp(OpcodeArgs) {
|
||||
|
||||
switch (Op->Src[0].Data.GPR.GPR) {
|
||||
case 0: // ES
|
||||
case FEXCore::X86State::REG_R8: // ES
|
||||
Segment = _LoadContext(2, offsetof(FEXCore::Core::CPUState, es), GPRClass);
|
||||
break;
|
||||
case 1: // DS
|
||||
case FEXCore::X86State::REG_R11: // DS
|
||||
Segment = _LoadContext(2, offsetof(FEXCore::Core::CPUState, ds), GPRClass);
|
||||
break;
|
||||
case 2: // CS
|
||||
case FEXCore::X86State::REG_R9: // CS
|
||||
Segment = _LoadContext(2, offsetof(FEXCore::Core::CPUState, cs), GPRClass);
|
||||
break;
|
||||
case 3: // SS
|
||||
case FEXCore::X86State::REG_R10: // SS
|
||||
Segment = _LoadContext(2, offsetof(FEXCore::Core::CPUState, ss), GPRClass);
|
||||
break;
|
||||
case 6: // GS
|
||||
case FEXCore::X86State::REG_R13: // GS
|
||||
if (CTX->Config.Is64BitMode) {
|
||||
Segment = _Constant(0);
|
||||
}
|
||||
@@ -1632,6 +1643,7 @@ void OpDispatchBuilder::MOVSegOp(OpcodeArgs) {
|
||||
}
|
||||
break;
|
||||
case 7: // FS
|
||||
case FEXCore::X86State::REG_R12: // FS
|
||||
if (CTX->Config.Is64BitMode) {
|
||||
Segment = _Constant(0);
|
||||
}
|
||||
|
||||
@@ -1,6 +1,3 @@
|
||||
# Not guaranteed to work in 64bit mode
|
||||
Test_Primary/Primary_8C.asm
|
||||
|
||||
# Needs Precision checking
|
||||
Test_REP/F3_52.asm
|
||||
Test_REP/F3_53.asm
|
||||
|
||||
@@ -11,3 +11,7 @@ Test_TwoByte/0F_0E.asm
|
||||
# Intel doesn't support CLZero, which the CI uses
|
||||
Test_SecondaryModRM/Reg_7_4.asm
|
||||
Test_SecondaryModRM/Reg_7_4_2.asm
|
||||
|
||||
# Not guaranteed to work in 64bit mode
|
||||
Test_Primary/Primary_8C.asm
|
||||
Test_Primary/Primary_8C_2.asm
|
||||
@@ -0,0 +1,45 @@
|
||||
%ifdef CONFIG
|
||||
{
|
||||
"RegData": {
|
||||
"RAX": "0x4142",
|
||||
"RBX": "0x4143",
|
||||
"RCX": "0x4144"
|
||||
}
|
||||
}
|
||||
%endif
|
||||
; This relies on some behaviour that isn't guaranteed in 64bit mode
|
||||
|
||||
; Technically this can result in an invalid selector which can cause faults
|
||||
; We currently don't do any selector validation to enforce this
|
||||
mov rax, 0x4142
|
||||
|
||||
db 0x44 ; REX.R
|
||||
mov es, ax
|
||||
|
||||
inc rax
|
||||
|
||||
db 0x44 ; REX.R
|
||||
mov ss, ax
|
||||
|
||||
inc rax
|
||||
|
||||
db 0x44 ; REX.R
|
||||
mov ds, ax
|
||||
|
||||
; Can't test FS/GS here
|
||||
; Behaviour is ill-defined and needs to be worked through
|
||||
|
||||
mov rax, 0
|
||||
mov rbx, 0
|
||||
mov rcx, 0
|
||||
|
||||
db 0x44 ; REX.R
|
||||
mov ax, es
|
||||
|
||||
db 0x44 ; REX.R
|
||||
mov bx, ss
|
||||
|
||||
db 0x44 ; REX.R
|
||||
mov cx, ds
|
||||
|
||||
hlt
|
||||
Reference in new issue
Block a user