This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |
Other format: | [Raw text] |
x86: derive DispN from BaseIndex BaseIndex implies - with the exception of string instructions the optional presence of a displacement. This is almost completely uniform for all instructions (the sole exception being MPX ones, which don't allow 16-bit addressing and hence Disp16), so there's no point in explicitly stating this in the main opcode table. Drop those explict specifications in favor of adding logic to i386-gen, shrinking the table size quite a bit and hence making it more readable. The opcodes/i386-tbl.h changes are due to a few cases where pointless Disp* still hadn't been removed from their insns. opcodes/ 2017-11-29 Jan Beulich <jbeulich@suse.com> * i386-gen.c (active_cpu_flags, active_isstring, enum stage): New. (output_cpu_flags): Update active_cpu_flags. (process_i386_opcode_modifier): Update active_isstring. (output_operand_type): Rename "macro" parameter to "stage", changing its type. (process_i386_operand_type): Likewise. Track presence of BaseIndex and emit DispN accordingly. (output_i386_opcode, process_i386_registers, process_i386_initializers): Adjust calls to process_i386_operand_type() for its changed parameter type. * i386-opc.tbl: Drop Disp8, Disp16, Disp32, and Disp32S from all insns operands having BaseIndex set. * i386-tbl.h: Re-generate. --- For readability and to meet size constraints I've removed not only the re-generated bits, but also the purely mechanical i386-opc.tbl changes from the inline patch. The compressed attachment contains them, though. --- a/opcodes/i386-gen.c +++ b/opcodes/i386-gen.c @@ -686,6 +686,8 @@ static bitfield operand_types[] = }; static const char *filename; +static i386_cpu_flags active_cpu_flags; +static int active_isstring; static int compare (const void *x, const void *y) @@ -876,6 +878,8 @@ output_cpu_flags (FILE *table, bitfield { unsigned int i; + memset (&active_cpu_flags, 0, sizeof(active_cpu_flags)); + fprintf (table, "%s{ { ", indent); for (i = 0; i < size - 1; i++) @@ -892,6 +896,8 @@ output_cpu_flags (FILE *table, bitfield else fprintf (table, "\n %s", indent); } + if (flags[i].value) + active_cpu_flags.array[i / 32] |= 1U << (i % 32); } fprintf (table, "%d } }%s\n", flags[i].value, comma); @@ -988,6 +994,8 @@ process_i386_opcode_modifier (FILE *tabl char *str, *next, *last; bitfield modifiers [ARRAY_SIZE (opcode_modifiers)]; + active_isstring = 0; + /* Copy the default opcode modifier. */ memcpy (modifiers, opcode_modifiers, sizeof (modifiers)); @@ -998,16 +1006,26 @@ process_i386_opcode_modifier (FILE *tabl { str = next_field (next, '|', &next, last); if (str) - set_bitfield (str, modifiers, 1, ARRAY_SIZE (modifiers), + { + set_bitfield (str, modifiers, 1, ARRAY_SIZE (modifiers), lineno); + if (strcasecmp(str, "IsString") == 0) + active_isstring = 1; + } } } output_opcode_modifier (table, modifiers, ARRAY_SIZE (modifiers)); } +enum stage { + stage_macros, + stage_opcodes, + stage_registers, +}; + static void output_operand_type (FILE *table, bitfield *types, unsigned int size, - int macro, const char *indent) + enum stage stage, const char *indent) { unsigned int i; @@ -1022,7 +1040,7 @@ output_operand_type (FILE *table, bitfie if (((i + 1) % 20) == 0) { /* We need \\ for macro. */ - if (macro) + if (stage == stage_macros) fprintf (table, " \\\n%s", indent); else fprintf (table, "\n%s", indent); @@ -1033,7 +1051,7 @@ output_operand_type (FILE *table, bitfie } static void -process_i386_operand_type (FILE *table, char *op, int macro, +process_i386_operand_type (FILE *table, char *op, enum stage stage, const char *indent, int lineno) { char *str, *next, *last; @@ -1044,15 +1062,32 @@ process_i386_operand_type (FILE *table, if (strcmp (op, "0")) { + int baseindex = 0; + last = op + strlen (op); for (next = op; next && next < last; ) { str = next_field (next, '|', &next, last); if (str) - set_bitfield (str, types, 1, ARRAY_SIZE (types), lineno); + { + set_bitfield (str, types, 1, ARRAY_SIZE (types), lineno); + if (strcasecmp(str, "BaseIndex") == 0) + baseindex = 1; + } + } + + if (stage == stage_opcodes && baseindex && !active_isstring) + { + set_bitfield("Disp8", types, 1, ARRAY_SIZE (types), lineno); + if (!active_cpu_flags.bitfield.cpu64 + && !active_cpu_flags.bitfield.cpumpx) + set_bitfield("Disp16", types, 1, ARRAY_SIZE (types), lineno); + set_bitfield("Disp32", types, 1, ARRAY_SIZE (types), lineno); + if (!active_cpu_flags.bitfield.cpuno64) + set_bitfield("Disp32S", types, 1, ARRAY_SIZE (types), lineno); } } - output_operand_type (table, types, ARRAY_SIZE (types), macro, + output_operand_type (table, types, ARRAY_SIZE (types), stage, indent); } @@ -1140,14 +1175,15 @@ output_i386_opcode (FILE *table, const c if (operand_types[i] == NULL || *operand_types[i] == '0') { if (i == 0) - process_i386_operand_type (table, "0", 0, "\t ", lineno); + process_i386_operand_type (table, "0", stage_opcodes, "\t ", + lineno); break; } if (i != 0) fprintf (table, ",\n "); - process_i386_operand_type (table, operand_types[i], 0, + process_i386_operand_type (table, operand_types[i], stage_opcodes, "\t ", lineno); } fprintf (table, " } },\n"); @@ -1309,7 +1345,7 @@ process_i386_opcodes (FILE *table) process_i386_opcode_modifier (table, "0", -1); fprintf (table, " { "); - process_i386_operand_type (table, "0", 0, "\t ", -1); + process_i386_operand_type (table, "0", stage_opcodes, "\t ", -1); fprintf (table, " } }\n"); fprintf (table, "};\n"); @@ -1378,7 +1414,8 @@ process_i386_registers (FILE *table) fprintf (table, " { \"%s\",\n ", reg_name); - process_i386_operand_type (table, reg_type, 0, "\t", lineno); + process_i386_operand_type (table, reg_type, stage_registers, "\t", + lineno); /* Find 32-bit Dwarf2 register number. */ dw2_32_num = next_field (str, ',', &str, last); @@ -1422,7 +1459,7 @@ process_i386_initializers (void) { fprintf (fp, "\n\n#define %s \\\n ", operand_type_init[i].name); init = xstrdup (operand_type_init[i].init); - process_i386_operand_type (fp, init, 1, " ", -1); + process_i386_operand_type (fp, init, stage_macros, " ", -1); free (init); } fprintf (fp, "\n");
Attachment:
binutils-master-x86-derive-DispN-from-BaseIndex.patch.bz2
Description: Binary data
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |