diff options
| author | ptitSeb <sebastien.chev@gmail.com> | 2021-04-08 19:11:42 +0200 |
|---|---|---|
| committer | ptitSeb <sebastien.chev@gmail.com> | 2021-04-08 19:11:42 +0200 |
| commit | d809b59daa15183e83f48d38e7a4440363242728 (patch) | |
| tree | 96d16e9fb47df43a7db16b4038b3840d93d6bb72 /src | |
| parent | e14d4042d932d6a9098f2a5082f28387265270ab (diff) | |
| download | box64-d809b59daa15183e83f48d38e7a4440363242728.tar.gz box64-d809b59daa15183e83f48d38e7a4440363242728.zip | |
Added 67 66 0F 6F/7A opcodes
Diffstat (limited to 'src')
| -rw-r--r-- | src/emu/modrm.h | 2 | ||||
| -rwxr-xr-x | src/emu/x64run.c | 2 | ||||
| -rw-r--r-- | src/emu/x64run67.c | 12 | ||||
| -rw-r--r-- | src/emu/x64run6766.c | 66 | ||||
| -rw-r--r-- | src/emu/x64run67660f.c | 64 | ||||
| -rwxr-xr-x | src/emu/x64run_private.c | 8 | ||||
| -rwxr-xr-x | src/emu/x64run_private.h | 6 |
7 files changed, 157 insertions, 3 deletions
diff --git a/src/emu/modrm.h b/src/emu/modrm.h index f2a5029e..7f5c77ce 100644 --- a/src/emu/modrm.h +++ b/src/emu/modrm.h @@ -22,9 +22,11 @@ #define GETEB_OFFS(D, O) oped=GetEbO(emu, rex, nextop, D, O) #define GETGB opgd=GetGb(emu, rex, nextop) #define GETEW(D) oped=GetEw(emu, rex, nextop, D) +#define GETEW32(D) oped=GetEw32O(emu, rex, nextop, D, 0) #define GETEW_OFFS(D, O) oped=GetEdO(emu, rex, nextop, D, O) #define GETGW opgd=GetGw(emu, rex, nextop) #define GETEX(D) opex=GetEx(emu, rex, nextop, D) +#define GETEX32(D) opex=GetEx32O(emu, rex, nextop, D, 0) #define GETEX_OFFS(D, O) opex=GetExO(emu, rex, nextop, D, O) #define GETGX opgx=GetGx(emu, rex, nextop) #define GETEM(D) opem=GetEm(emu, rex, nextop, D) diff --git a/src/emu/x64run.c b/src/emu/x64run.c index 34db888e..3c83e6b0 100755 --- a/src/emu/x64run.c +++ b/src/emu/x64run.c @@ -256,7 +256,7 @@ x64emurun: goto fini; break; case 0x67: /* reduce EASize prefix */ - if(Run67(emu, rex)) { + if(Run67(emu, rex, rep)) { unimp = 1; goto fini; } diff --git a/src/emu/x64run67.c b/src/emu/x64run67.c index e074be4b..75f64125 100644 --- a/src/emu/x64run67.c +++ b/src/emu/x64run67.c @@ -22,7 +22,7 @@ #include "modrm.h" -int Run67(x64emu_t *emu, rex_t rex) +int Run67(x64emu_t *emu, rex_t rex, int rep) { uint8_t opcode; uint8_t nextop; @@ -34,12 +34,19 @@ int Run67(x64emu_t *emu, rex_t rex) opcode = F8; + while(opcode==0x67) + opcode = F8; + // REX prefix before the 67 are ignored rex.rex = 0; while(opcode>=0x40 && opcode<=0x4f) { rex.rex = opcode; opcode = F8; } + while((opcode==0xF2) || (opcode==0xF3)) { + rep = opcode-0xF1; + opcode = F8; + } switch(opcode) { #define GO(B, OP) \ @@ -96,6 +103,9 @@ int Run67(x64emu_t *emu, rex_t rex) GO(0x30, xor) /* XOR 0x30 -> 0x35 */ #undef GO + case 0x66: + return Run6766(emu, rex, rep); + case 0x80: /* GRP Eb,Ib */ nextop = F8; GETEB32(1); diff --git a/src/emu/x64run6766.c b/src/emu/x64run6766.c new file mode 100644 index 00000000..256a2671 --- /dev/null +++ b/src/emu/x64run6766.c @@ -0,0 +1,66 @@ +#define _GNU_SOURCE +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <math.h> +#include <string.h> +#include <signal.h> +#include <sys/types.h> +#include <unistd.h> + +#include "debug.h" +#include "box64stack.h" +#include "x64emu.h" +#include "x64run.h" +#include "x64emu_private.h" +#include "x64run_private.h" +#include "x64primop.h" +#include "x64trace.h" +#include "x87emu_private.h" +#include "box64context.h" +#include "bridge.h" +#ifdef DYNAREC +#include "../dynarec/arm64_lock.h" +#endif + +#include "modrm.h" + +int Run6766(x64emu_t *emu, rex_t rex, int rep) +{ + uint8_t opcode; + uint8_t nextop; + int8_t tmp8s; + uint8_t tmp8u, tmp8u2; + int16_t tmp16s; + uint16_t tmp16u, tmp16u2; + int32_t tmp32s; + int64_t tmp64s; + uint64_t tmp64u, tmp64u2, tmp64u3; + reg64_t *oped, *opgd; + + opcode = F8; + + while((opcode==0x2E) || (opcode==0x66)) // ignoring CS: or multiple 0x66 + opcode = F8; + + while((opcode==0xF2) || (opcode==0xF3)) { + rep = opcode-0xF1; + opcode = F8; + } + // REX prefix before the F0 are ignored + rex.rex = 0; + while(opcode>=0x40 && opcode<=0x4f) { + rex.rex = opcode; + opcode = F8; + } + + switch(opcode) { + + case 0x0F: /* more opcdes */ + return Run67660F(emu, rex); + + default: + return 1; + } + return 0; +} \ No newline at end of file diff --git a/src/emu/x64run67660f.c b/src/emu/x64run67660f.c new file mode 100644 index 00000000..e5a9d1f8 --- /dev/null +++ b/src/emu/x64run67660f.c @@ -0,0 +1,64 @@ +#define _GNU_SOURCE +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <math.h> +#include <string.h> +#include <signal.h> +#include <sys/types.h> +#include <unistd.h> + +#include "debug.h" +#include "box64stack.h" +#include "x64emu.h" +#include "x64run.h" +#include "x64emu_private.h" +#include "x64run_private.h" +#include "x64primop.h" +#include "x64trace.h" +#include "x87emu_private.h" +#include "box64context.h" +#include "bridge.h" + +#include "modrm.h" + +int Run67660F(x64emu_t *emu, rex_t rex) +{ + uint8_t opcode; + uint8_t nextop; + uint8_t tmp8u; + int8_t tmp8s; + int16_t tmp16s; + uint16_t tmp16u; + int32_t tmp32s; + uint32_t tmp32u; + uint64_t tmp64u; + reg64_t *oped, *opgd; + sse_regs_t *opex, *opgx, eax1, *opex2; + mmx87_regs_t *opem, *opgm; + + opcode = F8; + + switch(opcode) { + + case 0x6F: /* MOVDQA Gx,Ex */ + nextop = F8; + GETEX32(0); + GETGX; + GX->q[0] = EX->q[0]; + GX->q[1] = EX->q[1]; + break; + + case 0x76: /* PCMPEQD Gx,Ex */ + nextop = F8; + GETEX32(0); + GETGX; + for (int i=0; i<4; ++i) + GX->ud[i] = (GX->ud[i]==EX->ud[i])?0xffffffff:0; + break; + + default: + return 1; + } + return 0; +} \ No newline at end of file diff --git a/src/emu/x64run_private.c b/src/emu/x64run_private.c index 738dd603..8b7add60 100755 --- a/src/emu/x64run_private.c +++ b/src/emu/x64run_private.c @@ -1256,6 +1256,14 @@ sse_regs_t* GetExO(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t } else return (sse_regs_t*)GetECommonO(emu, rex, m, delta, offset); } +sse_regs_t* GetEx32O(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset) +{ + uint8_t m = v&0xC7; // filter Ed + if(m>=0xC0) { + return &emu->xmm[(m&0x07)+(rex.b<<3)]; + } else return (sse_regs_t*)GetECommon32O(emu, rex, m, delta, offset); +} + reg64_t* GetGd(x64emu_t *emu, rex_t rex, uint8_t v) { diff --git a/src/emu/x64run_private.h b/src/emu/x64run_private.h index 358a972e..e465c6b0 100755 --- a/src/emu/x64run_private.h +++ b/src/emu/x64run_private.h @@ -83,11 +83,13 @@ reg64_t* GetEdO(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t of reg64_t* GetEd32O(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset); reg64_t* GetEb32O(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset); #define GetEw GetEd +#define GetEw32O GetEd32O reg64_t* GetEw16(x64emu_t *emu, rex_t rex, uint8_t v); reg64_t* GetEw16off(x64emu_t *emu, rex_t rex, uint8_t v, uintptr_t offset); mmx87_regs_t* GetEm(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta); sse_regs_t* GetEx(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta); sse_regs_t* GetExO(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset); +sse_regs_t* GetEx32O(x64emu_t *emu, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset); reg64_t* GetGd(x64emu_t *emu, rex_t rex, uint8_t v); #define GetGw GetGd reg64_t* GetGb(x64emu_t *emu, rex_t rex, uint8_t v); @@ -106,7 +108,9 @@ int Run660F(x64emu_t *emu, rex_t rex); int Run6664(x64emu_t *emu, rex_t rex); int Run66D9(x64emu_t *emu, rex_t rex); int Run66DD(x64emu_t *emu, rex_t rex); -int Run67(x64emu_t *emu, rex_t rex); +int Run67(x64emu_t *emu, rex_t rex, int rep); +int Run6766(x64emu_t *emu, rex_t rex, int rep); +int Run67660F(x64emu_t *emu, rex_t rex); int RunD8(x64emu_t *emu, rex_t rex); int RunD9(x64emu_t *emu, rex_t rex); int RunDA(x64emu_t *emu, rex_t rex); |