From d2224064f1a70969a77a8a82b117489793d6653e Mon Sep 17 00:00:00 2001 From: Jan Beulich Date: Thu, 8 Mar 2018 08:52:27 +0100 Subject: [PATCH] x86: drop {X,Y,Z}MMWORD_MNEM_SUFFIX They aren't really useful (anymore?): The conflicting operand size check isn't applicable to any insn validly using respective memory operand sizes (and if they're used wrongly, another error would result), and the logic in process_suffix() can be easily changed to work without them. While re-structuring conditionals in process_suffix() also drop the CMPXCHG8B special case in favor of a NoRex64 attribute in the opcode table. --- gas/ChangeLog | 8 +++++ gas/config/tc-i386-intel.c | 3 -- gas/config/tc-i386.c | 64 ++++++++++++++------------------------ opcodes/ChangeLog | 5 +++ opcodes/i386-opc.tbl | 2 +- opcodes/i386-tbl.h | 2 +- 6 files changed, 39 insertions(+), 45 deletions(-) diff --git a/gas/ChangeLog b/gas/ChangeLog index c36e14a442..d668f42206 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,11 @@ +2018-03-08 Jan Beulich + + * config/tc-i386.c (XMMWORD_MNEM_SUFFIX, YMMWORD_MNEM_SUFFIX, + ZMMWORD_MNEM_SUFFIX): Delete. + (process_suffix): Drop their uses. Re-arrange final part of + logic into a switch() statement. Drop special casing of + cmpxchg8b. + 2018-03-08 Jan Beulich * config/tc-i386.c (match_template): Also match register diff --git a/gas/config/tc-i386-intel.c b/gas/config/tc-i386-intel.c index 6030b9f5c6..26fc3efe66 100644 --- a/gas/config/tc-i386-intel.c +++ b/gas/config/tc-i386-intel.c @@ -698,17 +698,14 @@ i386_intel_operand (char *operand_string, int got_a_float) case O_oword_ptr: case O_xmmword_ptr: i.types[this_operand].bitfield.xmmword = 1; - suffix = XMMWORD_MNEM_SUFFIX; break; case O_ymmword_ptr: i.types[this_operand].bitfield.ymmword = 1; - suffix = YMMWORD_MNEM_SUFFIX; break; case O_zmmword_ptr: i.types[this_operand].bitfield.zmmword = 1; - suffix = ZMMWORD_MNEM_SUFFIX; break; case O_far_ptr: diff --git a/gas/config/tc-i386.c b/gas/config/tc-i386.c index 1da1fbd545..8c37bff344 100644 --- a/gas/config/tc-i386.c +++ b/gas/config/tc-i386.c @@ -81,9 +81,6 @@ #define SHORT_MNEM_SUFFIX 's' #define LONG_MNEM_SUFFIX 'l' #define QWORD_MNEM_SUFFIX 'q' -#define XMMWORD_MNEM_SUFFIX 'x' -#define YMMWORD_MNEM_SUFFIX 'y' -#define ZMMWORD_MNEM_SUFFIX 'z' /* Intel Syntax. Use a non-ascii letter since since it never appears in instructions. */ #define LONG_DOUBLE_MNEM_SUFFIX '\1' @@ -5790,13 +5787,6 @@ process_suffix (void) else if (!check_word_reg ()) return 0; } - else if (i.suffix == XMMWORD_MNEM_SUFFIX - || i.suffix == YMMWORD_MNEM_SUFFIX - || i.suffix == ZMMWORD_MNEM_SUFFIX) - { - /* Skip if the instruction has x/y/z suffix. match_template - should check if it is a valid suffix. */ - } else if (intel_syntax && i.tm.opcode_modifier.ignoresize) /* Do nothing if the instruction is going to ignore the prefix. */ ; @@ -5877,15 +5867,19 @@ process_suffix (void) } } - /* Change the opcode based on the operand size given by i.suffix; - We don't need to change things for byte insns. */ - - if (i.suffix - && i.suffix != BYTE_MNEM_SUFFIX - && i.suffix != XMMWORD_MNEM_SUFFIX - && i.suffix != YMMWORD_MNEM_SUFFIX - && i.suffix != ZMMWORD_MNEM_SUFFIX) + /* Change the opcode based on the operand size given by i.suffix. */ + switch (i.suffix) { + /* Size floating point instruction. */ + case LONG_MNEM_SUFFIX: + if (i.tm.opcode_modifier.floatmf) + { + i.tm.base_opcode ^= 4; + break; + } + /* fall through */ + case WORD_MNEM_SUFFIX: + case QWORD_MNEM_SUFFIX: /* It's not a byte, select word/dword operation. */ if (i.tm.opcode_modifier.w) { @@ -5894,7 +5888,8 @@ process_suffix (void) else i.tm.base_opcode |= 1; } - + /* fall through */ + case SHORT_MNEM_SUFFIX: /* Now select between word & dword operations via the operand size prefix, except for instructions that will ignore this prefix anyway. */ @@ -5910,7 +5905,6 @@ process_suffix (void) return 0; } else if (i.suffix != QWORD_MNEM_SUFFIX - && i.suffix != LONG_DOUBLE_MNEM_SUFFIX && !i.tm.opcode_modifier.ignoresize && !i.tm.opcode_modifier.floatmf && ((i.suffix == LONG_MNEM_SUFFIX) == (flag_code == CODE_16BIT) @@ -5929,27 +5923,17 @@ process_suffix (void) /* Set mode64 for an operand. */ if (i.suffix == QWORD_MNEM_SUFFIX && flag_code == CODE_64BIT - && !i.tm.opcode_modifier.norex64) - { + && !i.tm.opcode_modifier.norex64 /* Special case for xchg %rax,%rax. It is NOP and doesn't - need rex64. cmpxchg8b is also a special case. */ - if (! (i.operands == 2 - && i.tm.base_opcode == 0x90 - && i.tm.extension_opcode == None - && operand_type_equal (&i.types [0], &acc64) - && operand_type_equal (&i.types [1], &acc64)) - && ! (i.operands == 1 - && i.tm.base_opcode == 0xfc7 - && i.tm.extension_opcode == 1 - && !operand_type_check (i.types [0], reg) - && operand_type_check (i.types [0], anymem))) - i.rex |= REX_W; - } - - /* Size floating point instruction. */ - if (i.suffix == LONG_MNEM_SUFFIX) - if (i.tm.opcode_modifier.floatmf) - i.tm.base_opcode ^= 4; + need rex64. */ + && ! (i.operands == 2 + && i.tm.base_opcode == 0x90 + && i.tm.extension_opcode == None + && operand_type_equal (&i.types [0], &acc64) + && operand_type_equal (&i.types [1], &acc64))) + i.rex |= REX_W; + + break; } return 1; diff --git a/opcodes/ChangeLog b/opcodes/ChangeLog index a109e7deb2..3967b58382 100644 --- a/opcodes/ChangeLog +++ b/opcodes/ChangeLog @@ -1,3 +1,8 @@ +2018-03-08 Jan Beulich + + * i386-opc.tbl (cmpxchg8b): Add NoRex64. + * i386-tlb.h: Re-generate. + 2018-03-08 Jan Beulich * i386-opc.tbl (cmpxchg16b, fisttp, fisttpll, bndmov, mwaitx): diff --git a/opcodes/i386-opc.tbl b/opcodes/i386-opc.tbl index e5098eb287..793f4ded8f 100644 --- a/opcodes/i386-opc.tbl +++ b/opcodes/i386-opc.tbl @@ -848,7 +848,7 @@ cpuid, 0, 0xfa2, None, 2, Cpu486, No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_qSuf|No_ldS wrmsr, 0, 0xf30, None, 2, Cpu586, No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_qSuf|No_ldSuf, { 0 } rdtsc, 0, 0xf31, None, 2, Cpu586, No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_qSuf|No_ldSuf, { 0 } rdmsr, 0, 0xf32, None, 2, Cpu586, No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_qSuf|No_ldSuf, { 0 } -cmpxchg8b, 1, 0xfc7, 0x1, 2, Cpu586, Modrm|No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_ldSuf|IsLockable|HLEPrefixOk, { Qword|Unspecified|BaseIndex } +cmpxchg8b, 1, 0xfc7, 0x1, 2, Cpu586, Modrm|No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_ldSuf|IsLockable|NoRex64|HLEPrefixOk, { Qword|Unspecified|BaseIndex } // Pentium II/Pentium Pro extensions. sysenter, 0, 0xf34, None, 2, Cpu686, No_bSuf|No_wSuf|No_lSuf|No_sSuf|No_qSuf|No_ldSuf, { 0 } diff --git a/opcodes/i386-tbl.h b/opcodes/i386-tbl.h index 88381b63a0..6ffafc6a06 100644 --- a/opcodes/i386-tbl.h +++ b/opcodes/i386-tbl.h @@ -9475,7 +9475,7 @@ const insn_template i386_optab[] = 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } }, { 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, - 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, { { { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, -- 2.34.1