Fix the handling of \324 for computing the length

\324 means REX.W is mandatory, but that doesn't mean add a byte to the
output!  Instead, force REX.W set, and let the REX logic deal with the
length.
This commit is contained in:
H. Peter Anvin 2007-04-18 02:27:18 +00:00
parent 7295e9856d
commit 8d7316a3ff

View File

@ -695,9 +695,9 @@ static int32_t calcsize(int32_t segment, int32_t offset, int bits,
int32_t length = 0; int32_t length = 0;
uint8_t c; uint8_t c;
int t; int t;
ins->rex = 0; /* Ensure REX is reset */
int rex_mask = 0xFF; int rex_mask = 0xFF;
int lock_is_rex_r = 0; int lock_is_rex_r = 0;
ins->rex = 0; /* Ensure REX is reset */
(void)segment; /* Don't warn that this parameter is unused */ (void)segment; /* Don't warn that this parameter is unused */
(void)offset; /* Don't warn that this parameter is unused */ (void)offset; /* Don't warn that this parameter is unused */
@ -860,8 +860,8 @@ static int32_t calcsize(int32_t segment, int32_t offset, int bits,
rex_mask = 0x07; rex_mask = 0x07;
break; break;
case 0324: case 0324:
length++; ins->rex |= 0xF8;
break; break;
case 0330: case 0330:
codes++, length++; codes++, length++;
break; break;
@ -919,10 +919,12 @@ static int32_t calcsize(int32_t segment, int32_t offset, int bits,
ins->rex &= rex_mask; ins->rex &= rex_mask;
if (ins->rex) { if (ins->rex) {
if (bits == 64 || if (bits == 64 ||
(lock_is_rex_r && ins->rex == 0xf4 && cpu >= IF_X86_64)) (lock_is_rex_r && ins->rex == 0xf4 && cpu >= IF_X86_64)) {
length++; length++;
else } else {
errfunc(ERR_NONFATAL, "invalid operands in non-64-bit mode"); errfunc(ERR_NONFATAL, "invalid operands in non-64-bit mode");
return -1;
}
} }
return length; return length;