Fix jmp/call near offsets in long mode

In long mode relative offsets are always 32 bits sign-extended to 64
bits and absolute near addresses are always 64 bits, regardless of the
operand size.

Signed-off-by: Ben Rudiak-Gould <benrudiak@gmail.com>
Signed-off-by: Cyrill Gorcunov <gorcunov@gmail.com>
This commit is contained in:
Ben Rudiak-Gould 2013-02-20 23:25:59 +04:00 committed by Cyrill Gorcunov
parent d7ab1f9638
commit bf0f42390d
2 changed files with 51 additions and 51 deletions

View File

@ -532,22 +532,21 @@ static int matches(const struct itemplate *t, uint8_t *data,
opx->segment &= ~SEG_32BIT;
break;
case4(064):
case4(064): /* rel */
opx->segment |= SEG_RELATIVE;
if (osize == 16) {
opx->offset = gets16(data);
data += 2;
opx->segment &= ~(SEG_32BIT|SEG_64BIT);
} else if (osize == 32) {
opx->offset = gets32(data);
data += 4;
opx->segment &= ~SEG_64BIT;
opx->segment |= SEG_32BIT;
}
if (segsize != osize) {
opx->type =
(opx->type & ~SIZE_MASK)
| ((osize == 16) ? BITS16 : BITS32);
/* In long mode rel is always 32 bits, sign extended. */
if (segsize == 64 || osize == 32) {
opx->offset = gets32(data);
data += 4;
if (segsize != 64)
opx->segment |= SEG_32BIT;
opx->type = (opx->type & ~SIZE_MASK)
| (segsize == 64 ? BITS64 : BITS32);
} else {
opx->offset = gets16(data);
data += 2;
opx->segment &= ~SEG_32BIT;
opx->type = (opx->type & ~SIZE_MASK) | BITS16;
}
break;

View File

@ -229,14 +229,17 @@ BTS rm16,imm [mi: hle o16 0f ba /5 ib,u] 386,SB,LOCK
BTS rm32,imm [mi: hle o32 0f ba /5 ib,u] 386,SB,LOCK
BTS rm64,imm [mi: hle o64 0f ba /5 ib,u] X64,SB,LOCK
CALL imm [i: odf e8 rel] 8086
CALL imm|near [i: odf e8 rel] 8086
CALL imm|near [i: odf e8 rel] 8086,ND
CALL imm|far [i: odf 9a iwd seg] 8086,ND,NOLONG
CALL imm16 [i: o16 e8 rel] 8086
CALL imm16|near [i: o16 e8 rel] 8086
; Call/jmp near imm/reg/mem is always 64-bit in long mode.
CALL imm16 [i: o16 e8 rel] 8086,NOLONG
CALL imm16|near [i: o16 e8 rel] 8086,ND,NOLONG
CALL imm16|far [i: o16 9a iwd seg] 8086,ND,NOLONG
CALL imm32 [i: o32 e8 rel] 386
CALL imm32|near [i: o32 e8 rel] 386
CALL imm32 [i: o32 e8 rel] 386,NOLONG
CALL imm32|near [i: o32 e8 rel] 386,ND,NOLONG
CALL imm32|far [i: o32 9a iwd seg] 386,ND,NOLONG
CALL imm64 [i: o64nw e8 rel] X64
CALL imm64|near [i: o64nw e8 rel] X64,ND
CALL imm:imm [ji: odf 9a iwd iw] 8086,NOLONG
CALL imm16:imm [ji: o16 9a iw iw] 8086,NOLONG
CALL imm:imm16 [ji: o16 9a iw iw] 8086,NOLONG
@ -248,17 +251,13 @@ CALL mem16|far [m: o16 ff /3] 8086
CALL mem32|far [m: o32 ff /3] 386
CALL mem64|far [m: o64 ff /3] X64
CALL mem|near [m: odf ff /2] 8086,ND
CALL mem16|near [m: o16 ff /2] 8086,ND
CALL mem32|near [m: o32 ff /2] 386,NOLONG,ND
CALL mem64|near [m: o64nw ff /2] X64,ND
CALL reg16 [m: o16 ff /2] 8086
CALL reg32 [m: o32 ff /2] 386,NOLONG
CALL reg64 [m: o64nw ff /2] X64
CALL rm16|near [m: o16 ff /2] 8086,NOLONG,ND
CALL rm32|near [m: o32 ff /2] 386,NOLONG,ND
CALL rm64|near [m: o64nw ff /2] X64,ND
CALL mem [m: odf ff /2] 8086
CALL mem16 [m: o16 ff /2] 8086
CALL mem32 [m: o32 ff /2] 386,NOLONG
CALL mem [m: o64nw ff /2] X64
CALL mem64 [m: o64nw ff /2] X64
CALL rm16 [m: o16 ff /2] 8086,NOLONG
CALL rm32 [m: o32 ff /2] 386,NOLONG
CALL rm64 [m: o64nw ff /2] X64
CBW void [ o16 98] 8086
CDQ void [ o32 99] 386
CDQE void [ o64 98] X64
@ -661,12 +660,15 @@ JMP imm [i: jmp8 eb rel8] 8086,ND
JMP imm [i: odf e9 rel] 8086
JMP imm|near [i: odf e9 rel] 8086,ND
JMP imm|far [i: odf ea iwd seg] 8086,ND,NOLONG
JMP imm16 [i: o16 e9 rel] 8086
JMP imm16|near [i: o16 e9 rel] 8086,ND
; Call/jmp near imm/reg/mem is always 64-bit in long mode.
JMP imm16 [i: o16 e9 rel] 8086,NOLONG
JMP imm16|near [i: o16 e9 rel] 8086,ND,NOLONG
JMP imm16|far [i: o16 ea iwd seg] 8086,ND,NOLONG
JMP imm32 [i: o32 e9 rel] 386
JMP imm32|near [i: o32 e9 rel] 386,ND
JMP imm32 [i: o32 e9 rel] 386,NOLONG
JMP imm32|near [i: o32 e9 rel] 386,ND,NOLONG
JMP imm32|far [i: o32 ea iwd seg] 386,ND,NOLONG
JMP imm64 [i: o64nw e9 rel] X64
JMP imm64|near [i: o64nw e9 rel] X64,ND
JMP imm:imm [ji: odf ea iwd iw] 8086,NOLONG
JMP imm16:imm [ji: o16 ea iw iw] 8086,NOLONG
JMP imm:imm16 [ji: o16 ea iw iw] 8086,NOLONG
@ -678,17 +680,13 @@ JMP mem16|far [m: o16 ff /5] 8086
JMP mem32|far [m: o32 ff /5] 386
JMP mem64|far [m: o64 ff /5] X64
JMP mem|near [m: odf ff /4] 8086,ND
JMP mem16|near [m: o16 ff /4] 8086,ND
JMP mem32|near [m: o32 ff /4] 386,NOLONG,ND
JMP mem64|near [m: o64nw ff /4] X64,ND
JMP reg16 [m: o16 ff /4] 8086
JMP reg32 [m: o32 ff /4] 386,NOLONG
JMP reg64 [m: o64nw ff /4] X64
JMP rm16|near [m: o16 ff /4] 8086,NOLONG,ND
JMP rm32|near [m: o32 ff /4] 386,NOLONG,ND
JMP rm64|near [m: o64nw ff /4] X64,ND
JMP mem [m: odf ff /4] 8086
JMP mem16 [m: o16 ff /4] 8086
JMP mem32 [m: o32 ff /4] 386,NOLONG
JMP mem [m: o64nw ff /4] X64
JMP mem64 [m: o64nw ff /4] X64
JMP rm16 [m: o16 ff /4] 8086,NOLONG
JMP rm32 [m: o32 ff /4] 386,NOLONG
JMP rm64 [m: o64nw ff /4] X64
JMPE imm [i: odf 0f b8 rel] IA64
JMPE imm16 [i: o16 0f b8 rel] IA64
JMPE imm32 [i: o32 0f b8 rel] IA64
@ -1428,8 +1426,9 @@ CMOVcc reg32,reg32 [rm: o32 0f 40+c /r] P6
CMOVcc reg64,mem [rm: o64 0f 40+c /r] X64,SM
CMOVcc reg64,reg64 [rm: o64 0f 40+c /r] X64
Jcc imm|near [i: odf 0f 80+c rel] 386
Jcc imm16|near [i: o16 0f 80+c rel] 386
Jcc imm32|near [i: o32 0f 80+c rel] 386
Jcc imm16|near [i: o16 0f 80+c rel] 386,NOLONG
Jcc imm32|near [i: o32 0f 80+c rel] 386,NOLONG
Jcc imm64|near [i: o64nw 0f 80+c rel] X64
Jcc imm|short [i: 70+c rel8] 8086,ND
Jcc imm [i: jcc8 70+c rel8] 8086,ND
Jcc imm [i: 0f 80+c rel] 386,ND
@ -3344,11 +3343,13 @@ VPGATHERQQ ymmreg,mem64,ymmreg [rmv: vm64y vex.dds.256.66.0f38.w1 91 /r] FUTURE
XABORT imm [i: c6 f8 ib] FUTURE,RTM
XABORT imm8 [i: c6 f8 ib] FUTURE,RTM
XBEGIN imm [i: odf c7 f8 rel] FUTURE,RTM
XBEGIN imm|near [i: odf c7 f8 rel] FUTURE,RTM
XBEGIN imm16 [i: o16 c7 f8 rel] FUTURE,RTM
XBEGIN imm16|near [i: o16 c7 f8 rel] FUTURE,RTM
XBEGIN imm32 [i: o32 c7 f8 rel] FUTURE,RTM
XBEGIN imm32|near [i: o32 c7 f8 rel] FUTURE,RTM
XBEGIN imm|near [i: odf c7 f8 rel] FUTURE,RTM,ND
XBEGIN imm16 [i: o16 c7 f8 rel] FUTURE,RTM,NOLONG
XBEGIN imm16|near [i: o16 c7 f8 rel] FUTURE,RTM,NOLONG,ND
XBEGIN imm32 [i: o32 c7 f8 rel] FUTURE,RTM,NOLONG
XBEGIN imm32|near [i: o32 c7 f8 rel] FUTURE,RTM,NOLONG,ND
XBEGIN imm64 [i: o64nw c7 f8 rel] FUTURE,RTM,LONG
XBEGIN imm64|near [i: o64nw c7 f8 rel] FUTURE,RTM,LONG,ND
XEND void [ 0f 01 d5] FUTURE,RTM
XTEST void [ 0f 01 d6] FUTURE,HLE,RTM