1 /* The IGEN simulator generator for GDB, the GNU Debugger. 2 3 Copyright 2002-2023 Free Software Foundation, Inc. 4 5 Contributed by Andrew Cagney. 6 7 This file is part of GDB. 8 9 This program is free software; you can redistribute it and/or modify 10 it under the terms of the GNU General Public License as published by 11 the Free Software Foundation; either version 3 of the License, or 12 (at your option) any later version. 13 14 This program is distributed in the hope that it will be useful, 15 but WITHOUT ANY WARRANTY; without even the implied warranty of 16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 GNU General Public License for more details. 18 19 You should have received a copy of the GNU General Public License 20 along with this program. If not, see <http://www.gnu.org/licenses/>. */ 21 22 23 /* load the opcode stat structure */ 24 25 #include "misc.h" 26 #include "lf.h" 27 #include "table.h" 28 #include "filter.h" 29 30 #include "igen.h" 31 32 #include "ld-decode.h" 33 34 35 static const name_map decode_type_map[] = { 36 {"normal", normal_decode_rule}, 37 {"boolean", boolean_rule}, 38 {NULL, normal_decode_rule}, 39 }; 40 41 static const name_map decode_gen_map[] = { 42 {"array", array_gen}, 43 {"switch", switch_gen}, 44 {"padded-switch", padded_switch_gen}, 45 {"goto-switch", goto_switch_gen}, 46 {NULL, -1}, 47 }; 48 49 static const name_map decode_reserved_map[] = { 50 {"zero-reserved", 1}, 51 {NULL, 0}, 52 }; 53 54 static const name_map decode_duplicates_map[] = { 55 {"duplicate", 1}, 56 {NULL, 0}, 57 }; 58 59 static const name_map decode_combine_map[] = { 60 {"combine", 1}, 61 {NULL, 0}, 62 }; 63 64 static const name_map decode_search_map[] = { 65 {"constants", decode_find_constants}, 66 {"mixed", decode_find_mixed}, 67 {"strings", decode_find_strings}, 68 {NULL, decode_find_mixed}, 69 }; 70 71 72 static void 73 set_bits (int bit[max_insn_bit_size], uint64_t value) 74 { 75 int bit_nr; 76 for (bit_nr = 0; bit_nr < max_insn_bit_size; bit_nr++) 77 { 78 if (bit_nr < options.insn_bit_size) 79 bit[bit_nr] = (value >> (options.insn_bit_size - bit_nr - 1)) & 1; 80 else 81 bit[bit_nr] = 0; 82 } 83 } 84 85 decode_table * 86 load_decode_table (const char *file_name) 87 { 88 table *file = table_open (file_name); 89 table_entry *entry; 90 decode_table *table = NULL; 91 decode_table **curr_rule = &table; 92 while ((entry = table_read (file)) != NULL) 93 { 94 char *decode_options = entry->field[decode_options_field]; 95 decode_table *new_rule = ZALLOC (decode_table); 96 if (entry->nr_fields < min_nr_decode_fields) 97 error (entry->line, "Missing decode table fields\n"); 98 new_rule->line = entry->line; 99 100 /* the options field */ 101 new_rule->type = name2i (decode_options, decode_type_map); 102 if (options.decode.overriding_gen != NULL) 103 new_rule->gen = 104 name2i (options.decode.overriding_gen, decode_gen_map); 105 else 106 new_rule->gen = name2i (decode_options, decode_gen_map); 107 if (new_rule->gen == padded_switch_gen && options.decode.switch_as_goto) 108 new_rule->gen = goto_switch_gen; 109 if (options.decode.zero_reserved) 110 new_rule->with_zero_reserved = 1; 111 else 112 new_rule->with_zero_reserved = 113 name2i (decode_options, decode_reserved_map); 114 if (options.decode.duplicate) 115 new_rule->with_duplicates = 1; 116 else 117 new_rule->with_duplicates = 118 name2i (decode_options, decode_duplicates_map); 119 if (options.decode.combine) 120 new_rule->with_combine = 1; 121 else 122 new_rule->with_combine = name2i (decode_options, decode_combine_map); 123 if (new_rule->type == boolean_rule) 124 { 125 char *chp = decode_options; 126 while (*chp != '\0') 127 { 128 if (isdigit (*chp)) 129 { 130 new_rule->constant = a2i (chp); 131 break; 132 } 133 chp = skip_to_separator (chp, ","); 134 if (*chp == ',') 135 ++chp; 136 chp = skip_spaces (chp); 137 } 138 } 139 140 /* First and last */ 141 if (entry->nr_fields > decode_first_field 142 && strlen (entry->field[decode_first_field]) > 0) 143 { 144 new_rule->first = target_a2i (options.hi_bit_nr, 145 entry->field[decode_first_field]); 146 if (new_rule->first < 0 || new_rule->first >= options.insn_bit_size) 147 error (new_rule->line, "First field out of range\n"); 148 } 149 else 150 new_rule->first = 0; 151 if (entry->nr_fields > decode_last_field 152 && strlen (entry->field[decode_last_field]) > 0) 153 { 154 new_rule->last = target_a2i (options.hi_bit_nr, 155 entry->field[decode_last_field]); 156 if (new_rule->last < 0 || new_rule->last >= options.insn_bit_size) 157 error (new_rule->line, "Last field out of range\n"); 158 } 159 else 160 new_rule->last = options.insn_bit_size - 1; 161 if (new_rule->first > new_rule->last) 162 error (new_rule->line, "First must preceed last\n"); 163 164 /* force first/last, with default values based on first/last */ 165 if (entry->nr_fields > decode_force_first_field 166 && strlen (entry->field[decode_force_first_field]) > 0) 167 { 168 new_rule->force_first = target_a2i (options.hi_bit_nr, 169 entry-> 170 field 171 [decode_force_first_field]); 172 if (new_rule->force_first < new_rule->first 173 || new_rule->force_first > new_rule->last + 1) 174 error (new_rule->line, "Force first out of range\n"); 175 } 176 else 177 new_rule->force_first = new_rule->last + 1; 178 if (entry->nr_fields > decode_force_last_field 179 && strlen (entry->field[decode_force_last_field]) > 0) 180 { 181 new_rule->force_last = target_a2i (options.hi_bit_nr, 182 entry-> 183 field[decode_force_last_field]); 184 if (new_rule->force_last > new_rule->last 185 || new_rule->force_last < new_rule->first - 1) 186 error (new_rule->line, "Force-last out of range\n"); 187 } 188 else 189 new_rule->force_last = new_rule->first - 1; 190 191 /* fields to be treated as constant */ 192 if (entry->nr_fields > decode_constant_field_names_field) 193 filter_parse (&new_rule->constant_field_names, 194 entry->field[decode_constant_field_names_field]); 195 196 /* applicable word nr */ 197 if (entry->nr_fields > decode_word_nr_field) 198 new_rule->word_nr = a2i (entry->field[decode_word_nr_field]); 199 200 /* required instruction format names */ 201 if (entry->nr_fields > decode_format_names_field) 202 filter_parse (&new_rule->format_names, 203 entry->field[decode_format_names_field]); 204 205 /* required processor models */ 206 if (entry->nr_fields > decode_model_names_field) 207 filter_parse (&new_rule->model_names, 208 entry->field[decode_model_names_field]); 209 210 /* required paths */ 211 if (entry->nr_fields > decode_paths_field 212 && strlen (entry->field[decode_paths_field]) > 0) 213 { 214 decode_path_list **last = &new_rule->paths; 215 char *chp = entry->field[decode_paths_field]; 216 do 217 { 218 (*last) = ZALLOC (decode_path_list); 219 /* extra root/zero entry */ 220 (*last)->path = ZALLOC (decode_path); 221 do 222 { 223 decode_path *entry = ZALLOC (decode_path); 224 entry->opcode_nr = a2i (chp); 225 entry->parent = (*last)->path; 226 (*last)->path = entry; 227 chp = skip_digits (chp); 228 chp = skip_spaces (chp); 229 } 230 while (*chp == '.'); 231 last = &(*last)->next; 232 } 233 while (*chp == ','); 234 if (*chp != '\0') 235 error (entry->line, "Invalid path field\n"); 236 } 237 238 /* collect up the list of optional special conditions applicable 239 to the rule */ 240 { 241 int field_nr = nr_decode_fields; 242 while (entry->nr_fields > field_nr) 243 { 244 decode_cond *cond = ZALLOC (decode_cond); 245 decode_cond **last; 246 if (entry->nr_fields > field_nr + decode_cond_mask_field) 247 set_bits (cond->mask, 248 a2i (entry-> 249 field[field_nr + decode_cond_mask_field])); 250 if (entry->nr_fields > field_nr + decode_cond_value_field) 251 { 252 if (entry->field[field_nr + decode_cond_value_field][0] == 253 '!') 254 { 255 cond->is_equal = 0; 256 set_bits (cond->value, 257 a2i (entry-> 258 field[field_nr + decode_cond_value_field] + 259 1)); 260 } 261 else 262 { 263 cond->is_equal = 1; 264 set_bits (cond->value, 265 a2i (entry-> 266 field[field_nr + 267 decode_cond_value_field])); 268 } 269 } 270 if (entry->nr_fields > field_nr + decode_cond_word_nr_field) 271 cond->word_nr = 272 a2i (entry->field[field_nr + decode_cond_word_nr_field]); 273 field_nr += nr_decode_cond_fields; 274 /* insert it */ 275 last = &new_rule->conditions; 276 while (*last != NULL) 277 last = &(*last)->next; 278 *last = cond; 279 } 280 } 281 *curr_rule = new_rule; 282 curr_rule = &new_rule->next; 283 } 284 return table; 285 } 286 287 288 int 289 decode_table_max_word_nr (const decode_table *entry) 290 { 291 int max_word_nr = 0; 292 while (entry != NULL) 293 { 294 decode_cond *cond; 295 if (entry->word_nr > max_word_nr) 296 max_word_nr = entry->word_nr; 297 for (cond = entry->conditions; cond != NULL; cond = cond->next) 298 { 299 if (cond->word_nr > max_word_nr) 300 max_word_nr = cond->word_nr; 301 } 302 entry = entry->next; 303 } 304 return max_word_nr; 305 } 306 307 308 static void 309 dump_decode_cond (lf *file, const char *prefix, const decode_cond *cond, 310 const char *suffix) 311 { 312 lf_printf (file, "%s(decode_cond *) %p", prefix, cond); 313 if (cond != NULL) 314 { 315 lf_indent (file, +1); 316 lf_printf (file, "\n(word_nr %d)", cond->word_nr); 317 lf_printf (file, "\n(mask %p)", cond->mask); 318 lf_printf (file, "\n(value %p)", cond->value); 319 lf_printf (file, "\n(is_equal %d)", cond->is_equal); 320 lf_printf (file, "\n(next (decode_cond *) %p)", cond->next); 321 lf_indent (file, -1); 322 } 323 lf_printf (file, "%s", suffix); 324 } 325 326 327 static void 328 dump_decode_conds (lf *file, const char *prefix, const decode_cond *cond, 329 const char *suffix) 330 { 331 lf_printf (file, "%s(decode_cond *) %p", prefix, cond); 332 while (cond != NULL) 333 { 334 dump_decode_cond (file, "\n(", cond, ")"); 335 cond = cond->next; 336 } 337 lf_printf (file, "%s", suffix); 338 } 339 340 341 void 342 dump_decode_rule (lf *file, const char *prefix, const decode_table *rule, 343 const char *suffix) 344 { 345 lf_printf (file, "%s(decode_table *) %p", prefix, rule); 346 if (rule != NULL) 347 { 348 lf_indent (file, +1); 349 dump_line_ref (file, "\n(line ", rule->line, ")"); 350 lf_printf (file, "\n(type %s)", i2name (rule->type, decode_type_map)); 351 lf_printf (file, "\n(gen %s)", i2name (rule->gen, decode_gen_map)); 352 lf_printf (file, "\n(first %d)", rule->first); 353 lf_printf (file, "\n(last %d)", rule->last); 354 lf_printf (file, "\n(force_first %d)", rule->force_first); 355 lf_printf (file, "\n(force_last %d)", rule->force_last); 356 dump_filter (file, "\n(constant_field_names \"", 357 rule->constant_field_names, "\")"); 358 lf_printf (file, "\n(constant 0x%x)", rule->constant); 359 lf_printf (file, "\n(word_nr %d)", rule->word_nr); 360 lf_printf (file, "\n(with_zero_reserved %d)", rule->with_zero_reserved); 361 lf_printf (file, "\n(with_duplicates %d)", rule->with_duplicates); 362 lf_printf (file, "\n(with_combine %d)", rule->with_combine); 363 dump_filter (file, "\n(format_names \"", rule->format_names, "\")"); 364 dump_filter (file, "\n(model_names \"", rule->model_names, "\")"); 365 dump_decode_conds (file, "\n(conditions ", rule->conditions, ")"); 366 lf_printf (file, "\n(next %p)", rule->next); 367 lf_indent (file, -1); 368 } 369 lf_printf (file, "%s", suffix); 370 } 371 372 373 #ifdef MAIN 374 375 static void 376 dump_decode_rules (lf *file, 377 const char *prefix, 378 const decode_table *rule, 379 const char *suffix) 380 { 381 lf_printf (file, "%s", prefix); 382 while (rule != NULL) 383 { 384 lf_indent (file, +1); 385 dump_decode_rule (file, "\n(", rule, ")"); 386 lf_indent (file, -1); 387 rule = rule->next; 388 } 389 lf_printf (file, "%s", suffix); 390 } 391 392 igen_options options; 393 394 int 395 main (int argc, char **argv) 396 { 397 lf *l; 398 decode_table *rules; 399 400 INIT_OPTIONS (); 401 402 if (argc != 3) 403 error (NULL, "Usage: decode <decode-file> <hi-bit-nr>\n"); 404 405 options.hi_bit_nr = a2i (argv[2]); 406 rules = load_decode_table (argv[1]); 407 l = lf_open ("-", "stdout", lf_omit_references, lf_is_text, "tmp-ld-insn"); 408 dump_decode_rules (l, "(rules ", rules, ")\n"); 409 410 return 0; 411 } 412 #endif 413