1 1.1 christos /* The IGEN simulator generator for GDB, the GNU Debugger. 2 1.1 christos 3 1.11 christos Copyright 2002-2024 Free Software Foundation, Inc. 4 1.1 christos 5 1.1 christos Contributed by Andrew Cagney. 6 1.1 christos 7 1.1 christos This file is part of GDB. 8 1.1 christos 9 1.1 christos This program is free software; you can redistribute it and/or modify 10 1.1 christos it under the terms of the GNU General Public License as published by 11 1.1 christos the Free Software Foundation; either version 3 of the License, or 12 1.1 christos (at your option) any later version. 13 1.1 christos 14 1.1 christos This program is distributed in the hope that it will be useful, 15 1.1 christos but WITHOUT ANY WARRANTY; without even the implied warranty of 16 1.1 christos MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 1.1 christos GNU General Public License for more details. 18 1.1 christos 19 1.1 christos You should have received a copy of the GNU General Public License 20 1.1 christos along with this program. If not, see <http://www.gnu.org/licenses/>. */ 21 1.1 christos 22 1.1 christos #include <getopt.h> 23 1.10 christos #include <stdlib.h> 24 1.1 christos 25 1.1 christos #include "misc.h" 26 1.1 christos #include "lf.h" 27 1.1 christos #include "table.h" 28 1.1 christos #include "filter.h" 29 1.1 christos 30 1.1 christos #include "igen.h" 31 1.1 christos 32 1.1 christos #include "ld-insn.h" 33 1.1 christos #include "ld-decode.h" 34 1.1 christos #include "ld-cache.h" 35 1.1 christos 36 1.1 christos #include "gen.h" 37 1.1 christos 38 1.1 christos #include "gen-model.h" 39 1.1 christos #include "gen-icache.h" 40 1.1 christos #include "gen-itable.h" 41 1.1 christos #include "gen-idecode.h" 42 1.1 christos #include "gen-semantics.h" 43 1.1 christos #include "gen-engine.h" 44 1.1 christos #include "gen-support.h" 45 1.1 christos #include "gen-engine.h" 46 1.1 christos 47 1.1 christos 48 1.1 christos /****************************************************************/ 49 1.1 christos 50 1.1 christos 51 1.1 christos /* Semantic functions */ 52 1.1 christos 53 1.1 christos int 54 1.1 christos print_semantic_function_formal (lf *file, int nr_prefetched_words) 55 1.1 christos { 56 1.1 christos int nr = 0; 57 1.1 christos int word_nr; 58 1.1 christos if (options.gen.icache || nr_prefetched_words < 0) 59 1.1 christos { 60 1.1 christos nr += lf_printf (file, "SIM_DESC sd,\n"); 61 1.1 christos nr += lf_printf (file, "%sidecode_cache *cache_entry,\n", 62 1.1 christos options.module.global.prefix.l); 63 1.1 christos nr += lf_printf (file, "%sinstruction_address cia", 64 1.1 christos options.module.global.prefix.l); 65 1.1 christos } 66 1.1 christos else if (options.gen.smp) 67 1.1 christos { 68 1.1 christos nr += lf_printf (file, "sim_cpu *cpu,\n"); 69 1.1 christos for (word_nr = 0; word_nr < nr_prefetched_words; word_nr++) 70 1.1 christos { 71 1.1 christos nr += lf_printf (file, "%sinstruction_word instruction_%d,\n", 72 1.1 christos options.module.global.prefix.l, word_nr); 73 1.1 christos } 74 1.1 christos nr += lf_printf (file, "%sinstruction_address cia", 75 1.1 christos options.module.global.prefix.l); 76 1.1 christos } 77 1.1 christos else 78 1.1 christos { 79 1.1 christos nr += lf_printf (file, "SIM_DESC sd,\n"); 80 1.1 christos for (word_nr = 0; word_nr < nr_prefetched_words; word_nr++) 81 1.1 christos { 82 1.1 christos nr += lf_printf (file, "%sinstruction_word instruction_%d,\n", 83 1.1 christos options.module.global.prefix.l, word_nr); 84 1.1 christos } 85 1.1 christos nr += lf_printf (file, "%sinstruction_address cia", 86 1.1 christos options.module.global.prefix.l); 87 1.1 christos } 88 1.1 christos return nr; 89 1.1 christos } 90 1.1 christos 91 1.1 christos int 92 1.1 christos print_semantic_function_actual (lf *file, int nr_prefetched_words) 93 1.1 christos { 94 1.1 christos int nr = 0; 95 1.1 christos int word_nr; 96 1.1 christos if (options.gen.icache || nr_prefetched_words < 0) 97 1.1 christos { 98 1.1 christos nr += lf_printf (file, "sd, cache_entry, cia"); 99 1.1 christos } 100 1.1 christos else 101 1.1 christos { 102 1.1 christos if (options.gen.smp) 103 1.1 christos nr += lf_printf (file, "cpu"); 104 1.1 christos else 105 1.1 christos nr += lf_printf (file, "sd"); 106 1.1 christos for (word_nr = 0; word_nr < nr_prefetched_words; word_nr++) 107 1.1 christos nr += lf_printf (file, ", instruction_%d", word_nr); 108 1.1 christos nr += lf_printf (file, ", cia"); 109 1.1 christos } 110 1.1 christos return nr; 111 1.1 christos } 112 1.1 christos 113 1.1 christos int 114 1.1 christos print_semantic_function_type (lf *file) 115 1.1 christos { 116 1.1 christos int nr = 0; 117 1.1 christos nr += lf_printf (file, "%sinstruction_address", 118 1.1 christos options.module.global.prefix.l); 119 1.1 christos return nr; 120 1.1 christos } 121 1.1 christos 122 1.1 christos 123 1.1 christos /* Idecode functions */ 124 1.1 christos 125 1.1 christos int 126 1.1 christos print_icache_function_formal (lf *file, int nr_prefetched_words) 127 1.1 christos { 128 1.1 christos int nr = 0; 129 1.1 christos int word_nr; 130 1.1 christos if (options.gen.smp) 131 1.1 christos nr += lf_printf (file, "sim_cpu *cpu,\n"); 132 1.1 christos else 133 1.1 christos nr += lf_printf (file, "SIM_DESC sd,\n"); 134 1.1 christos for (word_nr = 0; word_nr < nr_prefetched_words; word_nr++) 135 1.1 christos nr += lf_printf (file, " %sinstruction_word instruction_%d,\n", 136 1.1 christos options.module.global.prefix.l, word_nr); 137 1.1 christos nr += lf_printf (file, " %sinstruction_address cia,\n", 138 1.1 christos options.module.global.prefix.l); 139 1.1 christos nr += lf_printf (file, " %sidecode_cache *cache_entry", 140 1.1 christos options.module.global.prefix.l); 141 1.1 christos return nr; 142 1.1 christos } 143 1.1 christos 144 1.1 christos int 145 1.1 christos print_icache_function_actual (lf *file, int nr_prefetched_words) 146 1.1 christos { 147 1.1 christos int nr = 0; 148 1.1 christos int word_nr; 149 1.1 christos if (options.gen.smp) 150 1.1 christos nr += lf_printf (file, "cpu"); 151 1.1 christos else 152 1.1 christos nr += lf_printf (file, "sd"); 153 1.1 christos for (word_nr = 0; word_nr < nr_prefetched_words; word_nr++) 154 1.1 christos nr += lf_printf (file, ", instruction_%d", word_nr); 155 1.1 christos nr += lf_printf (file, ", cia, cache_entry"); 156 1.1 christos return nr; 157 1.1 christos } 158 1.1 christos 159 1.1 christos int 160 1.1 christos print_icache_function_type (lf *file) 161 1.1 christos { 162 1.1 christos int nr; 163 1.1 christos if (options.gen.semantic_icache) 164 1.1 christos { 165 1.1 christos nr = print_semantic_function_type (file); 166 1.1 christos } 167 1.1 christos else 168 1.1 christos { 169 1.1 christos nr = lf_printf (file, "%sidecode_semantic *", 170 1.1 christos options.module.global.prefix.l); 171 1.1 christos } 172 1.1 christos return nr; 173 1.1 christos } 174 1.1 christos 175 1.1 christos 176 1.1 christos /* Function names */ 177 1.1 christos 178 1.1 christos static int 179 1.10 christos print_opcode_bits (lf *file, const opcode_bits *bits) 180 1.1 christos { 181 1.1 christos int nr = 0; 182 1.1 christos if (bits == NULL) 183 1.1 christos return nr; 184 1.1 christos nr += lf_putchr (file, '_'); 185 1.1 christos nr += lf_putstr (file, bits->field->val_string); 186 1.1 christos if (bits->opcode->is_boolean && bits->value == 0) 187 1.1 christos nr += lf_putint (file, bits->opcode->boolean_constant); 188 1.1 christos else if (!bits->opcode->is_boolean) 189 1.1 christos { 190 1.1 christos if (bits->opcode->last < bits->field->last) 191 1.1 christos nr += 192 1.1 christos lf_putint (file, 193 1.1 christos bits->value << (bits->field->last - bits->opcode->last)); 194 1.1 christos else 195 1.1 christos nr += lf_putint (file, bits->value); 196 1.1 christos } 197 1.1 christos nr += print_opcode_bits (file, bits->next); 198 1.1 christos return nr; 199 1.1 christos } 200 1.1 christos 201 1.1 christos static int 202 1.1 christos print_c_name (lf *file, const char *name) 203 1.1 christos { 204 1.1 christos int nr = 0; 205 1.1 christos const char *pos; 206 1.1 christos for (pos = name; *pos != '\0'; pos++) 207 1.1 christos { 208 1.1 christos switch (*pos) 209 1.1 christos { 210 1.1 christos case '/': 211 1.1 christos case '-': 212 1.1 christos break; 213 1.1 christos case ' ': 214 1.1 christos case '.': 215 1.1 christos nr += lf_putchr (file, '_'); 216 1.1 christos break; 217 1.1 christos default: 218 1.1 christos nr += lf_putchr (file, *pos); 219 1.1 christos break; 220 1.1 christos } 221 1.1 christos } 222 1.1 christos return nr; 223 1.1 christos } 224 1.1 christos 225 1.1 christos extern int 226 1.1 christos print_function_name (lf *file, 227 1.1 christos const char *basename, 228 1.1 christos const char *format_name, 229 1.1 christos const char *model_name, 230 1.10 christos const opcode_bits *expanded_bits, 231 1.1 christos lf_function_name_prefixes prefix) 232 1.1 christos { 233 1.1 christos int nr = 0; 234 1.1 christos /* the prefix */ 235 1.1 christos switch (prefix) 236 1.1 christos { 237 1.1 christos case function_name_prefix_semantics: 238 1.1 christos nr += lf_printf (file, "%s", options.module.semantics.prefix.l); 239 1.1 christos nr += lf_printf (file, "semantic_"); 240 1.1 christos break; 241 1.1 christos case function_name_prefix_idecode: 242 1.1 christos nr += lf_printf (file, "%s", options.module.idecode.prefix.l); 243 1.1 christos nr += lf_printf (file, "idecode_"); 244 1.1 christos break; 245 1.1 christos case function_name_prefix_itable: 246 1.1 christos nr += lf_printf (file, "%sitable_", options.module.itable.prefix.l); 247 1.1 christos break; 248 1.1 christos case function_name_prefix_icache: 249 1.1 christos nr += lf_printf (file, "%s", options.module.icache.prefix.l); 250 1.1 christos nr += lf_printf (file, "icache_"); 251 1.1 christos break; 252 1.1 christos case function_name_prefix_engine: 253 1.1 christos nr += lf_printf (file, "%s", options.module.engine.prefix.l); 254 1.1 christos nr += lf_printf (file, "engine_"); 255 1.1 christos default: 256 1.1 christos break; 257 1.1 christos } 258 1.1 christos 259 1.1 christos if (model_name != NULL) 260 1.1 christos { 261 1.1 christos nr += print_c_name (file, model_name); 262 1.1 christos nr += lf_printf (file, "_"); 263 1.1 christos } 264 1.1 christos 265 1.1 christos /* the function name */ 266 1.1 christos nr += print_c_name (file, basename); 267 1.1 christos 268 1.1 christos /* the format name if available */ 269 1.1 christos if (format_name != NULL) 270 1.1 christos { 271 1.1 christos nr += lf_printf (file, "_"); 272 1.1 christos nr += print_c_name (file, format_name); 273 1.1 christos } 274 1.1 christos 275 1.1 christos /* the suffix */ 276 1.1 christos nr += print_opcode_bits (file, expanded_bits); 277 1.1 christos 278 1.1 christos return nr; 279 1.1 christos } 280 1.1 christos 281 1.1 christos 282 1.1 christos void 283 1.1 christos print_my_defines (lf *file, 284 1.1 christos const char *basename, 285 1.10 christos const char *format_name, 286 1.10 christos const opcode_bits *expanded_bits) 287 1.1 christos { 288 1.1 christos /* #define MY_INDEX xxxxx */ 289 1.1 christos lf_indent_suppress (file); 290 1.1 christos lf_printf (file, "#undef MY_INDEX\n"); 291 1.1 christos lf_indent_suppress (file); 292 1.1 christos lf_printf (file, "#define MY_INDEX "); 293 1.1 christos print_function_name (file, 294 1.1 christos basename, format_name, NULL, 295 1.1 christos NULL, function_name_prefix_itable); 296 1.1 christos lf_printf (file, "\n"); 297 1.1 christos /* #define MY_PREFIX xxxxxx */ 298 1.1 christos lf_indent_suppress (file); 299 1.1 christos lf_printf (file, "#undef "); 300 1.1 christos print_function_name (file, 301 1.1 christos basename, format_name, NULL, 302 1.1 christos expanded_bits, function_name_prefix_none); 303 1.1 christos lf_printf (file, "\n"); 304 1.1 christos lf_indent_suppress (file); 305 1.1 christos lf_printf (file, "#undef MY_PREFIX\n"); 306 1.1 christos lf_indent_suppress (file); 307 1.1 christos lf_printf (file, "#define MY_PREFIX "); 308 1.1 christos print_function_name (file, 309 1.1 christos basename, format_name, NULL, 310 1.1 christos expanded_bits, function_name_prefix_none); 311 1.1 christos lf_printf (file, "\n"); 312 1.1 christos /* #define MY_NAME xxxxxx */ 313 1.1 christos lf_indent_suppress (file); 314 1.1 christos lf_indent_suppress (file); 315 1.1 christos lf_printf (file, "#undef MY_NAME\n"); 316 1.1 christos lf_indent_suppress (file); 317 1.1 christos lf_printf (file, "#define MY_NAME \""); 318 1.1 christos print_function_name (file, 319 1.1 christos basename, format_name, NULL, 320 1.1 christos expanded_bits, function_name_prefix_none); 321 1.1 christos lf_printf (file, "\"\n"); 322 1.1 christos } 323 1.1 christos 324 1.1 christos 325 1.1 christos static int 326 1.1 christos print_itrace_prefix (lf *file) 327 1.1 christos { 328 1.1 christos const char *prefix = "trace_prefix ("; 329 1.1 christos int indent = strlen (prefix); 330 1.1 christos lf_printf (file, "%sSD, CPU, cia, CIA, TRACE_LINENUM_P (CPU), \\\n", 331 1.1 christos prefix); 332 1.1 christos lf_indent (file, +indent); 333 1.1 christos lf_printf (file, "%sitable[MY_INDEX].file, \\\n", 334 1.1 christos options.module.itable.prefix.l); 335 1.1 christos lf_printf (file, "%sitable[MY_INDEX].line_nr, \\\n", 336 1.1 christos options.module.itable.prefix.l); 337 1.1 christos lf_printf (file, "\""); 338 1.1 christos return indent; 339 1.1 christos } 340 1.1 christos 341 1.1 christos 342 1.1 christos static void 343 1.10 christos print_itrace_format (lf *file, const insn_mnemonic_entry *assembler) 344 1.1 christos { 345 1.1 christos /* pass=1 is fmt string; pass=2 is arguments */ 346 1.1 christos int pass; 347 1.1 christos /* print the format string */ 348 1.1 christos for (pass = 1; pass <= 2; pass++) 349 1.1 christos { 350 1.1 christos const char *chp = assembler->format; 351 1.1 christos chp++; /* skip the leading quote */ 352 1.1 christos /* write out the format/args */ 353 1.1 christos while (*chp != '\0') 354 1.1 christos { 355 1.1 christos if (chp[0] == '\\' && (chp[1] == '<' || chp[1] == '>')) 356 1.1 christos { 357 1.1 christos if (pass == 1) 358 1.1 christos lf_putchr (file, chp[1]); 359 1.1 christos chp += 2; 360 1.1 christos } 361 1.1 christos else if (chp[0] == '<' || chp[0] == '%') 362 1.1 christos { 363 1.1 christos /* parse [ "%" ... ] "<" [ func "#" ] param ">" */ 364 1.1 christos const char *fmt; 365 1.1 christos const char *func; 366 1.1 christos int strlen_func; 367 1.1 christos const char *param; 368 1.1 christos int strlen_param; 369 1.1 christos /* the "%" ... "<" format */ 370 1.1 christos fmt = chp; 371 1.1 christos while (chp[0] != '<' && chp[0] != '\0') 372 1.1 christos chp++; 373 1.1 christos if (chp[0] != '<') 374 1.1 christos error (assembler->line, "Missing `<' after `%%'\n"); 375 1.1 christos chp++; 376 1.1 christos /* [ "func" # ] OR "param" */ 377 1.1 christos func = chp; 378 1.1 christos param = chp; 379 1.1 christos while (chp[0] != '>' && chp[0] != '#' && chp[0] != '\0') 380 1.1 christos chp++; 381 1.1 christos strlen_func = chp - func; 382 1.1 christos if (chp[0] == '#') 383 1.1 christos { 384 1.1 christos chp++; 385 1.1 christos param = chp; 386 1.1 christos while (chp[0] != '>' && chp[0] != '\0') 387 1.1 christos chp++; 388 1.1 christos } 389 1.1 christos strlen_param = chp - param; 390 1.1 christos if (chp[0] != '>') 391 1.1 christos error (assembler->line, 392 1.1 christos "Missing closing `>' in assembler string\n"); 393 1.1 christos chp++; 394 1.1 christos /* now process it */ 395 1.1 christos if (pass == 2) 396 1.1 christos lf_printf (file, ", \\\n"); 397 1.1 christos if (strncmp (fmt, "<", 1) == 0) 398 1.1 christos /* implicit long int format */ 399 1.1 christos { 400 1.1 christos if (pass == 1) 401 1.1 christos lf_printf (file, "%%ld"); 402 1.1 christos else 403 1.1 christos { 404 1.1 christos lf_printf (file, "(long) "); 405 1.1 christos lf_write (file, param, strlen_param); 406 1.1 christos } 407 1.1 christos } 408 1.1 christos else if (strncmp (fmt, "%<", 2) == 0) 409 1.1 christos /* explicit format */ 410 1.1 christos { 411 1.1 christos if (pass == 1) 412 1.1 christos lf_printf (file, "%%"); 413 1.1 christos else 414 1.1 christos lf_write (file, param, strlen_param); 415 1.1 christos } 416 1.1 christos else if (strncmp (fmt, "%s<", 3) == 0) 417 1.1 christos /* string format */ 418 1.1 christos { 419 1.1 christos if (pass == 1) 420 1.1 christos lf_printf (file, "%%s"); 421 1.1 christos else 422 1.1 christos { 423 1.1 christos lf_printf (file, "%sstr_", 424 1.1 christos options.module.global.prefix.l); 425 1.1 christos lf_write (file, func, strlen_func); 426 1.1 christos lf_printf (file, " (SD_, "); 427 1.1 christos lf_write (file, param, strlen_param); 428 1.1 christos lf_printf (file, ")"); 429 1.1 christos } 430 1.1 christos } 431 1.1 christos else if (strncmp (fmt, "%lx<", 4) == 0) 432 1.1 christos /* simple hex */ 433 1.1 christos { 434 1.1 christos if (pass == 1) 435 1.1 christos lf_printf (file, "%%lx"); 436 1.1 christos else 437 1.1 christos { 438 1.1 christos lf_printf (file, "(unsigned long) "); 439 1.1 christos lf_write (file, param, strlen_param); 440 1.1 christos } 441 1.1 christos } 442 1.1 christos else if (strncmp (fmt, "%#lx<", 5) == 0) 443 1.1 christos /* simple hex with 0x prefix */ 444 1.1 christos { 445 1.1 christos if (pass == 1) 446 1.1 christos lf_printf (file, "%%#lx"); 447 1.1 christos else 448 1.1 christos { 449 1.1 christos lf_printf (file, "(unsigned long) "); 450 1.1 christos lf_write (file, param, strlen_param); 451 1.1 christos } 452 1.1 christos } 453 1.1 christos else if (strncmp (fmt, "%08lx<", 6) == 0) 454 1.1 christos /* simple hex */ 455 1.1 christos { 456 1.1 christos if (pass == 1) 457 1.1 christos lf_printf (file, "%%08lx"); 458 1.1 christos else 459 1.1 christos { 460 1.1 christos lf_printf (file, "(unsigned long) "); 461 1.1 christos lf_write (file, param, strlen_param); 462 1.1 christos } 463 1.1 christos } 464 1.1 christos else 465 1.1 christos error (assembler->line, "Unknown assembler string format\n"); 466 1.1 christos } 467 1.1 christos else 468 1.1 christos { 469 1.1 christos if (pass == 1) 470 1.1 christos lf_putchr (file, chp[0]); 471 1.1 christos chp += 1; 472 1.1 christos } 473 1.1 christos } 474 1.1 christos } 475 1.1 christos lf_printf (file, ");\n"); 476 1.1 christos } 477 1.1 christos 478 1.1 christos 479 1.1 christos void 480 1.10 christos print_itrace (lf *file, const insn_entry *insn, int idecode) 481 1.1 christos { 482 1.1 christos /* NB: Here we escape each EOLN. This is so that the the compiler 483 1.1 christos treats a trace function call as a single line. Consequently any 484 1.1 christos errors in the line are refered back to the same igen assembler 485 1.1 christos source line */ 486 1.1 christos const char *phase = (idecode) ? "DECODE" : "INSN"; 487 1.1 christos lf_printf (file, "\n"); 488 1.1 christos lf_indent_suppress (file); 489 1.1 christos lf_printf (file, "#if defined (WITH_TRACE)\n"); 490 1.1 christos lf_printf (file, "/* generate a trace prefix if any tracing enabled */\n"); 491 1.1 christos lf_printf (file, "if (TRACE_ANY_P (CPU))\n"); 492 1.1 christos lf_printf (file, " {\n"); 493 1.1 christos lf_indent (file, +4); 494 1.1 christos { 495 1.1 christos if (insn->mnemonics != NULL) 496 1.1 christos { 497 1.1 christos insn_mnemonic_entry *assembler = insn->mnemonics; 498 1.1 christos int is_first = 1; 499 1.1 christos do 500 1.1 christos { 501 1.1 christos if (assembler->condition != NULL) 502 1.1 christos { 503 1.1 christos int indent; 504 1.1 christos lf_printf (file, "%sif (%s)\n", 505 1.1 christos is_first ? "" : "else ", assembler->condition); 506 1.1 christos lf_indent (file, +2); 507 1.1 christos lf_print__line_ref (file, assembler->line); 508 1.1 christos indent = print_itrace_prefix (file); 509 1.1 christos print_itrace_format (file, assembler); 510 1.1 christos lf_print__internal_ref (file); 511 1.1 christos lf_indent (file, -indent); 512 1.1 christos lf_indent (file, -2); 513 1.1 christos if (assembler->next == NULL) 514 1.1 christos error (assembler->line, 515 1.1 christos "Missing final unconditional assembler\n"); 516 1.1 christos } 517 1.1 christos else 518 1.1 christos { 519 1.1 christos int indent; 520 1.1 christos if (!is_first) 521 1.1 christos { 522 1.1 christos lf_printf (file, "else\n"); 523 1.1 christos lf_indent (file, +2); 524 1.1 christos } 525 1.1 christos lf_print__line_ref (file, assembler->line); 526 1.1 christos indent = print_itrace_prefix (file); 527 1.1 christos print_itrace_format (file, assembler); 528 1.1 christos lf_print__internal_ref (file); 529 1.1 christos lf_indent (file, -indent); 530 1.1 christos if (!is_first) 531 1.1 christos lf_indent (file, -2); 532 1.1 christos if (assembler->next != NULL) 533 1.1 christos error (assembler->line, 534 1.1 christos "Unconditional assembler is not last\n"); 535 1.1 christos } 536 1.1 christos is_first = 0; 537 1.1 christos assembler = assembler->next; 538 1.1 christos } 539 1.1 christos while (assembler != NULL); 540 1.1 christos } 541 1.1 christos else 542 1.1 christos { 543 1.1 christos int indent; 544 1.1 christos lf_indent (file, +2); 545 1.1 christos lf_print__line_ref (file, insn->line); 546 1.1 christos indent = print_itrace_prefix (file); 547 1.1 christos lf_printf (file, "%%s\", \\\n"); 548 1.1 christos lf_printf (file, "itable[MY_INDEX].name);\n"); 549 1.1 christos lf_print__internal_ref (file); 550 1.1 christos lf_indent (file, -indent); 551 1.1 christos lf_indent (file, -2); 552 1.1 christos } 553 1.1 christos lf_printf (file, "/* trace the instruction execution if enabled */\n"); 554 1.1 christos lf_printf (file, "if (TRACE_%s_P (CPU))\n", phase); 555 1.1 christos lf_printf (file, 556 1.1 christos " trace_generic (SD, CPU, TRACE_%s_IDX, \" %%s\", itable[MY_INDEX].name);\n", 557 1.1 christos phase); 558 1.1 christos } 559 1.1 christos lf_indent (file, -4); 560 1.1 christos lf_printf (file, " }\n"); 561 1.1 christos lf_indent_suppress (file); 562 1.1 christos lf_printf (file, "#endif\n"); 563 1.1 christos } 564 1.1 christos 565 1.1 christos 566 1.1 christos void 567 1.1 christos print_sim_engine_abort (lf *file, const char *message) 568 1.1 christos { 569 1.1 christos lf_printf (file, "sim_engine_abort (SD, CPU, cia, "); 570 1.1 christos lf_printf (file, "\"%s\"", message); 571 1.1 christos lf_printf (file, ");\n"); 572 1.1 christos } 573 1.1 christos 574 1.1 christos 575 1.1 christos void 576 1.1 christos print_include (lf *file, igen_module module) 577 1.1 christos { 578 1.1 christos lf_printf (file, "#include \"%s%s.h\"\n", module.prefix.l, module.suffix.l); 579 1.1 christos } 580 1.1 christos 581 1.1 christos void 582 1.1 christos print_include_inline (lf *file, igen_module module) 583 1.1 christos { 584 1.1 christos lf_printf (file, "#if C_REVEALS_MODULE_P (%s_INLINE)\n", module.suffix.u); 585 1.1 christos lf_printf (file, "#include \"%s%s.c\"\n", module.prefix.l, module.suffix.l); 586 1.1 christos lf_printf (file, "#else\n"); 587 1.1 christos print_include (file, module); 588 1.1 christos lf_printf (file, "#endif\n"); 589 1.1 christos lf_printf (file, "\n"); 590 1.1 christos } 591 1.1 christos 592 1.1 christos void 593 1.1 christos print_includes (lf *file) 594 1.1 christos { 595 1.1 christos lf_printf (file, "\n"); 596 1.1 christos lf_printf (file, "#include \"sim-inline.c\"\n"); 597 1.1 christos lf_printf (file, "\n"); 598 1.1 christos print_include_inline (file, options.module.itable); 599 1.1 christos print_include_inline (file, options.module.idecode); 600 1.1 christos print_include_inline (file, options.module.support); 601 1.1 christos } 602 1.1 christos 603 1.1 christos 604 1.1 christos /****************************************************************/ 605 1.1 christos 606 1.1 christos 607 1.1 christos static void 608 1.10 christos gen_semantics_h (lf *file, const insn_list *semantics, int max_nr_words) 609 1.1 christos { 610 1.1 christos int word_nr; 611 1.10 christos const insn_list *semantic; 612 1.1 christos for (word_nr = -1; word_nr <= max_nr_words; word_nr++) 613 1.1 christos { 614 1.1 christos lf_printf (file, "typedef "); 615 1.1 christos print_semantic_function_type (file); 616 1.1 christos lf_printf (file, " %sidecode_semantic", options.module.global.prefix.l); 617 1.1 christos if (word_nr >= 0) 618 1.1 christos lf_printf (file, "_%d", word_nr); 619 1.1 christos lf_printf (file, "\n("); 620 1.1 christos lf_indent (file, +1); 621 1.1 christos print_semantic_function_formal (file, word_nr); 622 1.1 christos lf_indent (file, -1); 623 1.1 christos lf_printf (file, ");\n"); 624 1.1 christos lf_printf (file, "\n"); 625 1.1 christos } 626 1.1 christos switch (options.gen.code) 627 1.1 christos { 628 1.1 christos case generate_calls: 629 1.1 christos for (semantic = semantics; semantic != NULL; semantic = semantic->next) 630 1.1 christos { 631 1.1 christos /* Ignore any special/internal instructions */ 632 1.1 christos if (semantic->insn->nr_words == 0) 633 1.1 christos continue; 634 1.1 christos print_semantic_declaration (file, 635 1.1 christos semantic->insn, 636 1.1 christos semantic->expanded_bits, 637 1.1 christos semantic->opcodes, 638 1.1 christos semantic->nr_prefetched_words); 639 1.1 christos } 640 1.1 christos break; 641 1.1 christos case generate_jumps: 642 1.1 christos lf_print__this_file_is_empty (file, "generating jumps"); 643 1.1 christos break; 644 1.1 christos } 645 1.1 christos } 646 1.1 christos 647 1.1 christos 648 1.1 christos static void 649 1.10 christos gen_semantics_c (lf *file, const insn_list *semantics, cache_entry *cache_rules) 650 1.1 christos { 651 1.1 christos if (options.gen.code == generate_calls) 652 1.1 christos { 653 1.10 christos const insn_list *semantic; 654 1.1 christos print_includes (file); 655 1.1 christos print_include (file, options.module.semantics); 656 1.1 christos lf_printf (file, "\n"); 657 1.1 christos 658 1.1 christos for (semantic = semantics; semantic != NULL; semantic = semantic->next) 659 1.1 christos { 660 1.1 christos /* Ignore any special/internal instructions */ 661 1.1 christos if (semantic->insn->nr_words == 0) 662 1.1 christos continue; 663 1.1 christos print_semantic_definition (file, 664 1.1 christos semantic->insn, 665 1.1 christos semantic->expanded_bits, 666 1.1 christos semantic->opcodes, 667 1.1 christos cache_rules, 668 1.1 christos semantic->nr_prefetched_words); 669 1.1 christos } 670 1.1 christos } 671 1.1 christos else 672 1.1 christos { 673 1.1 christos lf_print__this_file_is_empty (file, "generating jump engine"); 674 1.1 christos } 675 1.1 christos } 676 1.1 christos 677 1.1 christos 678 1.1 christos /****************************************************************/ 679 1.1 christos 680 1.1 christos 681 1.1 christos static void 682 1.1 christos gen_icache_h (lf *file, 683 1.10 christos const insn_list *semantic, 684 1.10 christos const function_entry *functions, int max_nr_words) 685 1.1 christos { 686 1.1 christos int word_nr; 687 1.1 christos for (word_nr = 0; word_nr <= max_nr_words; word_nr++) 688 1.1 christos { 689 1.1 christos lf_printf (file, "typedef "); 690 1.1 christos print_icache_function_type (file); 691 1.1 christos lf_printf (file, " %sidecode_icache_%d\n(", 692 1.1 christos options.module.global.prefix.l, word_nr); 693 1.1 christos print_icache_function_formal (file, word_nr); 694 1.1 christos lf_printf (file, ");\n"); 695 1.1 christos lf_printf (file, "\n"); 696 1.1 christos } 697 1.1 christos if (options.gen.code == generate_calls && options.gen.icache) 698 1.1 christos { 699 1.1 christos function_entry_traverse (file, functions, 700 1.1 christos print_icache_internal_function_declaration, 701 1.1 christos NULL); 702 1.1 christos while (semantic != NULL) 703 1.1 christos { 704 1.1 christos print_icache_declaration (file, 705 1.1 christos semantic->insn, 706 1.1 christos semantic->expanded_bits, 707 1.1 christos semantic->opcodes, 708 1.1 christos semantic->nr_prefetched_words); 709 1.1 christos semantic = semantic->next; 710 1.1 christos } 711 1.1 christos } 712 1.1 christos else 713 1.1 christos { 714 1.1 christos lf_print__this_file_is_empty (file, "generating jump engine"); 715 1.1 christos } 716 1.1 christos } 717 1.1 christos 718 1.1 christos static void 719 1.1 christos gen_icache_c (lf *file, 720 1.10 christos const insn_list *semantic, 721 1.10 christos const function_entry *functions, cache_entry *cache_rules) 722 1.1 christos { 723 1.1 christos /* output `internal' invalid/floating-point unavailable functions 724 1.1 christos where needed */ 725 1.1 christos if (options.gen.code == generate_calls && options.gen.icache) 726 1.1 christos { 727 1.1 christos lf_printf (file, "\n"); 728 1.1 christos lf_printf (file, "#include \"cpu.h\"\n"); 729 1.1 christos lf_printf (file, "#include \"idecode.h\"\n"); 730 1.1 christos lf_printf (file, "#include \"semantics.h\"\n"); 731 1.1 christos lf_printf (file, "#include \"icache.h\"\n"); 732 1.1 christos lf_printf (file, "#include \"support.h\"\n"); 733 1.1 christos lf_printf (file, "\n"); 734 1.1 christos function_entry_traverse (file, functions, 735 1.1 christos print_icache_internal_function_definition, 736 1.1 christos NULL); 737 1.1 christos lf_printf (file, "\n"); 738 1.1 christos while (semantic != NULL) 739 1.1 christos { 740 1.1 christos print_icache_definition (file, 741 1.1 christos semantic->insn, 742 1.1 christos semantic->expanded_bits, 743 1.1 christos semantic->opcodes, 744 1.1 christos cache_rules, 745 1.1 christos semantic->nr_prefetched_words); 746 1.1 christos semantic = semantic->next; 747 1.1 christos } 748 1.1 christos } 749 1.1 christos else 750 1.1 christos { 751 1.1 christos lf_print__this_file_is_empty (file, "generating jump engine"); 752 1.1 christos } 753 1.1 christos } 754 1.1 christos 755 1.1 christos 756 1.1 christos /****************************************************************/ 757 1.1 christos 758 1.1 christos 759 1.1 christos static void 760 1.1 christos gen_idecode_h (lf *file, 761 1.10 christos const gen_table *gen, 762 1.10 christos const insn_table *insns, 763 1.10 christos cache_entry *cache_rules) 764 1.1 christos { 765 1.10 christos lf_printf (file, "typedef uint%d_t %sinstruction_word;\n", 766 1.1 christos options.insn_bit_size, options.module.global.prefix.l); 767 1.1 christos if (options.gen.delayed_branch) 768 1.1 christos { 769 1.1 christos lf_printf (file, "typedef struct _%sinstruction_address {\n", 770 1.1 christos options.module.global.prefix.l); 771 1.1 christos lf_printf (file, " address_word ip; /* instruction pointer */\n"); 772 1.1 christos lf_printf (file, " address_word dp; /* delayed-slot pointer */\n"); 773 1.1 christos lf_printf (file, "} %sinstruction_address;\n", 774 1.1 christos options.module.global.prefix.l); 775 1.1 christos } 776 1.1 christos else 777 1.1 christos { 778 1.1 christos lf_printf (file, "typedef address_word %sinstruction_address;\n", 779 1.1 christos options.module.global.prefix.l); 780 1.1 christos 781 1.1 christos } 782 1.1 christos if (options.gen.nia == nia_is_invalid 783 1.1 christos && strlen (options.module.global.prefix.u) > 0) 784 1.1 christos { 785 1.1 christos lf_indent_suppress (file); 786 1.1 christos lf_printf (file, "#define %sINVALID_INSTRUCTION_ADDRESS ", 787 1.1 christos options.module.global.prefix.u); 788 1.1 christos lf_printf (file, "INVALID_INSTRUCTION_ADDRESS\n"); 789 1.1 christos } 790 1.1 christos lf_printf (file, "\n"); 791 1.1 christos print_icache_struct (file, insns, cache_rules); 792 1.1 christos lf_printf (file, "\n"); 793 1.1 christos if (options.gen.icache) 794 1.1 christos { 795 1.1 christos ERROR ("FIXME - idecode with icache suffering from bit-rot"); 796 1.1 christos } 797 1.1 christos else 798 1.1 christos { 799 1.1 christos gen_list *entry; 800 1.1 christos for (entry = gen->tables; entry != NULL; entry = entry->next) 801 1.1 christos { 802 1.1 christos print_idecode_issue_function_header (file, 803 1.1 christos (options.gen.multi_sim 804 1.1 christos ? entry->model->name 805 1.1 christos : NULL), 806 1.1 christos is_function_declaration, 807 1.1 christos 1 /*ALWAYS ONE WORD */ ); 808 1.1 christos } 809 1.1 christos if (options.gen.multi_sim) 810 1.1 christos { 811 1.1 christos print_idecode_issue_function_header (file, 812 1.1 christos NULL, 813 1.1 christos is_function_variable, 814 1.1 christos 1 /*ALWAYS ONE WORD */ ); 815 1.1 christos } 816 1.1 christos } 817 1.1 christos } 818 1.1 christos 819 1.1 christos 820 1.1 christos static void 821 1.1 christos gen_idecode_c (lf *file, 822 1.10 christos const gen_table *gen, 823 1.10 christos const insn_table *isa, 824 1.10 christos cache_entry *cache_rules) 825 1.1 christos { 826 1.1 christos /* the intro */ 827 1.1 christos print_includes (file); 828 1.1 christos print_include_inline (file, options.module.semantics); 829 1.1 christos lf_printf (file, "\n"); 830 1.1 christos 831 1.1 christos print_idecode_globals (file); 832 1.1 christos lf_printf (file, "\n"); 833 1.1 christos 834 1.1 christos switch (options.gen.code) 835 1.1 christos { 836 1.1 christos case generate_calls: 837 1.1 christos { 838 1.1 christos gen_list *entry; 839 1.1 christos for (entry = gen->tables; entry != NULL; entry = entry->next) 840 1.1 christos { 841 1.1 christos print_idecode_lookups (file, entry->table, cache_rules); 842 1.1 christos 843 1.1 christos /* output the main idecode routine */ 844 1.1 christos if (!options.gen.icache) 845 1.1 christos { 846 1.1 christos print_idecode_issue_function_header (file, 847 1.1 christos (options.gen.multi_sim 848 1.1 christos ? entry->model->name 849 1.1 christos : NULL), 850 1.1 christos 1 /*is definition */ , 851 1.1 christos 1 /*ALWAYS ONE WORD */ ); 852 1.1 christos lf_printf (file, "{\n"); 853 1.1 christos lf_indent (file, +2); 854 1.1 christos lf_printf (file, "%sinstruction_address nia;\n", 855 1.1 christos options.module.global.prefix.l); 856 1.1 christos print_idecode_body (file, entry->table, "nia ="); 857 1.1 christos lf_printf (file, "return nia;"); 858 1.1 christos lf_indent (file, -2); 859 1.1 christos lf_printf (file, "}\n"); 860 1.1 christos } 861 1.1 christos } 862 1.1 christos break; 863 1.1 christos } 864 1.1 christos case generate_jumps: 865 1.1 christos { 866 1.1 christos lf_print__this_file_is_empty (file, "generating a jump engine"); 867 1.1 christos break; 868 1.1 christos } 869 1.1 christos } 870 1.1 christos } 871 1.1 christos 872 1.1 christos 873 1.1 christos /****************************************************************/ 874 1.1 christos 875 1.1 christos 876 1.1 christos static void 877 1.10 christos gen_run_c (lf *file, const gen_table *gen) 878 1.1 christos { 879 1.1 christos gen_list *entry; 880 1.1 christos lf_printf (file, "#include \"sim-main.h\"\n"); 881 1.1 christos lf_printf (file, "#include \"engine.h\"\n"); 882 1.1 christos lf_printf (file, "#include \"idecode.h\"\n"); 883 1.1 christos lf_printf (file, "#include \"bfd.h\"\n"); 884 1.1 christos lf_printf (file, "\n"); 885 1.1 christos 886 1.1 christos if (options.gen.multi_sim) 887 1.1 christos { 888 1.1 christos print_idecode_issue_function_header (file, NULL, is_function_variable, 889 1.1 christos 1); 890 1.1 christos lf_printf (file, "\n"); 891 1.1 christos print_engine_run_function_header (file, NULL, is_function_variable); 892 1.1 christos lf_printf (file, "\n"); 893 1.1 christos } 894 1.1 christos 895 1.1 christos lf_printf (file, "void\n"); 896 1.1 christos lf_printf (file, "sim_engine_run (SIM_DESC sd,\n"); 897 1.1 christos lf_printf (file, " int next_cpu_nr,\n"); 898 1.1 christos lf_printf (file, " int nr_cpus,\n"); 899 1.1 christos lf_printf (file, " int siggnal)\n"); 900 1.1 christos lf_printf (file, "{\n"); 901 1.1 christos lf_indent (file, +2); 902 1.1 christos if (options.gen.multi_sim) 903 1.1 christos { 904 1.1 christos lf_printf (file, "int mach;\n"); 905 1.1 christos lf_printf (file, "if (STATE_ARCHITECTURE (sd) == NULL)\n"); 906 1.1 christos lf_printf (file, " mach = 0;\n"); 907 1.1 christos lf_printf (file, "else\n"); 908 1.1 christos lf_printf (file, " mach = STATE_ARCHITECTURE (sd)->mach;\n"); 909 1.1 christos lf_printf (file, "switch (mach)\n"); 910 1.1 christos lf_printf (file, " {\n"); 911 1.1 christos lf_indent (file, +2); 912 1.1 christos for (entry = gen->tables; entry != NULL; entry = entry->next) 913 1.1 christos { 914 1.1 christos if (options.gen.default_model != NULL 915 1.1 christos && (strcmp (entry->model->name, options.gen.default_model) == 0 916 1.1 christos || strcmp (entry->model->full_name, 917 1.1 christos options.gen.default_model) == 0)) 918 1.1 christos lf_printf (file, "default:\n"); 919 1.1 christos lf_printf (file, "case bfd_mach_%s:\n", entry->model->full_name); 920 1.1 christos lf_indent (file, +2); 921 1.1 christos print_function_name (file, "issue", NULL, /* format name */ 922 1.1 christos NULL, /* NO processor */ 923 1.1 christos NULL, /* expanded bits */ 924 1.1 christos function_name_prefix_idecode); 925 1.1 christos lf_printf (file, " = "); 926 1.1 christos print_function_name (file, "issue", NULL, /* format name */ 927 1.1 christos entry->model->name, NULL, /* expanded bits */ 928 1.1 christos function_name_prefix_idecode); 929 1.1 christos lf_printf (file, ";\n"); 930 1.1 christos print_function_name (file, "run", NULL, /* format name */ 931 1.1 christos NULL, /* NO processor */ 932 1.1 christos NULL, /* expanded bits */ 933 1.1 christos function_name_prefix_engine); 934 1.1 christos lf_printf (file, " = "); 935 1.1 christos print_function_name (file, "run", NULL, /* format name */ 936 1.1 christos entry->model->name, NULL, /* expanded bits */ 937 1.1 christos function_name_prefix_engine); 938 1.1 christos lf_printf (file, ";\n"); 939 1.1 christos lf_printf (file, "break;\n"); 940 1.1 christos lf_indent (file, -2); 941 1.1 christos } 942 1.1 christos if (options.gen.default_model == NULL) 943 1.1 christos { 944 1.1 christos lf_printf (file, "default:\n"); 945 1.1 christos lf_indent (file, +2); 946 1.1 christos lf_printf (file, "sim_engine_abort (sd, NULL, NULL_CIA,\n"); 947 1.1 christos lf_printf (file, 948 1.1 christos " \"sim_engine_run - unknown machine\");\n"); 949 1.1 christos lf_printf (file, "break;\n"); 950 1.1 christos lf_indent (file, -2); 951 1.1 christos } 952 1.1 christos lf_indent (file, -2); 953 1.1 christos lf_printf (file, " }\n"); 954 1.1 christos } 955 1.1 christos print_function_name (file, "run", NULL, /* format name */ 956 1.1 christos NULL, /* NO processor */ 957 1.1 christos NULL, /* expanded bits */ 958 1.1 christos function_name_prefix_engine); 959 1.1 christos lf_printf (file, " (sd, next_cpu_nr, nr_cpus, siggnal);\n"); 960 1.1 christos lf_indent (file, -2); 961 1.1 christos lf_printf (file, "}\n"); 962 1.1 christos } 963 1.1 christos 964 1.1 christos /****************************************************************/ 965 1.1 christos 966 1.1 christos static gen_table * 967 1.10 christos do_gen (const insn_table *isa, const decode_table *decode_rules) 968 1.1 christos { 969 1.1 christos gen_table *gen; 970 1.1 christos if (decode_rules == NULL) 971 1.1 christos error (NULL, "Must specify a decode table\n"); 972 1.1 christos if (isa == NULL) 973 1.1 christos error (NULL, "Must specify an instruction table\n"); 974 1.1 christos if (decode_table_max_word_nr (decode_rules) > 0) 975 1.1 christos options.gen.multi_word = decode_table_max_word_nr (decode_rules); 976 1.1 christos gen = make_gen_tables (isa, decode_rules); 977 1.1 christos gen_tables_expand_insns (gen); 978 1.1 christos gen_tables_expand_semantics (gen); 979 1.1 christos return gen; 980 1.1 christos } 981 1.1 christos 982 1.1 christos /****************************************************************/ 983 1.1 christos 984 1.1 christos igen_options options; 985 1.1 christos 986 1.1 christos int 987 1.1 christos main (int argc, char **argv, char **envp) 988 1.1 christos { 989 1.1 christos cache_entry *cache_rules = NULL; 990 1.1 christos lf_file_references file_references = lf_include_references; 991 1.1 christos decode_table *decode_rules = NULL; 992 1.1 christos insn_table *isa = NULL; 993 1.1 christos gen_table *gen = NULL; 994 1.1 christos char *real_file_name = NULL; 995 1.1 christos int is_header = 0; 996 1.1 christos int ch; 997 1.10 christos static const struct option longopts[] = { { 0 } }; 998 1.1 christos lf *standard_out = 999 1.1 christos lf_open ("-", "stdout", lf_omit_references, lf_is_text, "igen"); 1000 1.1 christos 1001 1.1 christos INIT_OPTIONS (); 1002 1.1 christos 1003 1.1 christos if (argc == 1) 1004 1.1 christos { 1005 1.1 christos printf ("Usage:\n"); 1006 1.1 christos printf ("\n"); 1007 1.1 christos printf (" igen <config-opts> ... <input-opts>... <output-opts>...\n"); 1008 1.1 christos printf ("\n"); 1009 1.1 christos printf ("Config options:\n"); 1010 1.1 christos printf ("\n"); 1011 1.1 christos printf (" -B <bit-size>\n"); 1012 1.1 christos printf ("\t Set the number of bits in an instruction (deprecated).\n"); 1013 1.1 christos printf 1014 1.1 christos ("\t This option can now be set directly in the instruction table.\n"); 1015 1.1 christos printf ("\n"); 1016 1.1 christos printf (" -D <data-structure>\n"); 1017 1.1 christos printf 1018 1.1 christos ("\t Dump the specified data structure to stdout. Valid structures include:\n"); 1019 1.1 christos printf 1020 1.1 christos ("\t processor-names - list the names of all the processors (models)\n"); 1021 1.1 christos printf ("\n"); 1022 1.1 christos printf (" -F <filter-list>\n"); 1023 1.1 christos printf 1024 1.1 christos ("\t Filter out any instructions with a non-empty flags field that contains\n"); 1025 1.1 christos printf ("\t a flag not listed in the <filter-list>.\n"); 1026 1.1 christos printf ("\n"); 1027 1.1 christos printf (" -H <high-bit>\n"); 1028 1.1 christos printf 1029 1.1 christos ("\t Set the number of the high (most significant) instruction bit (deprecated).\n"); 1030 1.1 christos printf 1031 1.1 christos ("\t This option can now be set directly in the instruction table.\n"); 1032 1.1 christos printf ("\n"); 1033 1.1 christos printf (" -I <directory>\n"); 1034 1.1 christos printf 1035 1.1 christos ("\t Add <directory> to the list of directories searched when opening a file\n"); 1036 1.1 christos printf ("\n"); 1037 1.1 christos printf (" -M <model-list>\n"); 1038 1.1 christos printf 1039 1.1 christos ("\t Filter out any instructions that do not support at least one of the listed\n"); 1040 1.1 christos printf 1041 1.1 christos ("\t models (An instructions with no model information is considered to support\n"); 1042 1.1 christos printf ("\t all models.).\n"); 1043 1.1 christos printf ("\n"); 1044 1.1 christos printf (" -N <nr-cpus>\n"); 1045 1.1 christos printf ("\t Generate a simulator supporting <nr-cpus>\n"); 1046 1.1 christos printf 1047 1.1 christos ("\t Specify `-N 0' to disable generation of the SMP. Specifying `-N 1' will\n"); 1048 1.1 christos printf 1049 1.1 christos ("\t still generate an SMP enabled simulator but will only support one CPU.\n"); 1050 1.1 christos printf ("\n"); 1051 1.1 christos printf (" -T <mechanism>\n"); 1052 1.1 christos printf 1053 1.1 christos ("\t Override the decode mechanism specified by the decode rules\n"); 1054 1.1 christos printf ("\n"); 1055 1.1 christos printf (" -P <prefix>\n"); 1056 1.1 christos printf 1057 1.1 christos ("\t Prepend global names (except itable) with the string <prefix>.\n"); 1058 1.1 christos printf 1059 1.1 christos ("\t Specify -P <module>=<prefix> to set a specific <module>'s prefix.\n"); 1060 1.1 christos printf ("\n"); 1061 1.1 christos printf (" -S <suffix>\n"); 1062 1.1 christos printf 1063 1.1 christos ("\t Replace a global name (suffix) (except itable) with the string <suffix>.\n"); 1064 1.1 christos printf 1065 1.1 christos ("\t Specify -S <module>=<suffix> to change a specific <module>'s name (suffix).\n"); 1066 1.1 christos printf ("\n"); 1067 1.1 christos printf (" -Werror\n"); 1068 1.1 christos printf ("\t Make warnings errors\n"); 1069 1.1 christos printf (" -Wnodiscard\n"); 1070 1.1 christos printf 1071 1.1 christos ("\t Suppress warnings about discarded functions and instructions\n"); 1072 1.1 christos printf (" -Wnowidth\n"); 1073 1.1 christos printf 1074 1.1 christos ("\t Suppress warnings about instructions with invalid widths\n"); 1075 1.1 christos printf (" -Wnounimplemented\n"); 1076 1.1 christos printf ("\t Suppress warnings about unimplemented instructions\n"); 1077 1.1 christos printf ("\n"); 1078 1.1 christos printf (" -G [!]<gen-option>\n"); 1079 1.1 christos printf ("\t Any of the following options:\n"); 1080 1.1 christos printf ("\n"); 1081 1.1 christos printf 1082 1.1 christos ("\t decode-duplicate - Override the decode rules, forcing the duplication of\n"); 1083 1.1 christos printf ("\t semantic functions\n"); 1084 1.1 christos printf 1085 1.1 christos ("\t decode-combine - Combine any duplicated entries within a table\n"); 1086 1.1 christos printf 1087 1.1 christos ("\t decode-zero-reserved - Override the decode rules, forcing reserved bits to be\n"); 1088 1.1 christos printf ("\t treated as zero.\n"); 1089 1.1 christos printf 1090 1.1 christos ("\t decode-switch-is-goto - Overfide the padded-switch code type as a goto-switch\n"); 1091 1.1 christos printf ("\n"); 1092 1.1 christos printf 1093 1.1 christos ("\t gen-conditional-issue - conditionally issue each instruction\n"); 1094 1.1 christos printf 1095 1.1 christos ("\t gen-delayed-branch - need both cia and nia passed around\n"); 1096 1.1 christos printf 1097 1.1 christos ("\t gen-direct-access - use #defines to directly access values\n"); 1098 1.1 christos printf 1099 1.1 christos ("\t gen-zero-r<N> - arch assumes GPR(<N>) == 0, keep it that way\n"); 1100 1.1 christos printf 1101 1.1 christos ("\t gen-icache[=<N> - generate an instruction cracking cache of size <N>\n"); 1102 1.1 christos printf ("\t Default size is %d\n", 1103 1.1 christos options.gen.icache_size); 1104 1.1 christos printf 1105 1.1 christos ("\t gen-insn-in-icache - save original instruction when cracking\n"); 1106 1.1 christos printf 1107 1.1 christos ("\t gen-multi-sim[=MODEL] - generate multiple simulators - one per model\n"); 1108 1.1 christos printf 1109 1.1 christos ("\t If specified MODEL is made the default architecture.\n"); 1110 1.1 christos printf 1111 1.1 christos ("\t By default, a single simulator that will\n"); 1112 1.1 christos printf 1113 1.1 christos ("\t execute any instruction is generated\n"); 1114 1.1 christos printf 1115 1.1 christos ("\t gen-multi-word - generate code allowing for multi-word insns\n"); 1116 1.1 christos printf 1117 1.1 christos ("\t gen-semantic-icache - include semantic code in cracking functions\n"); 1118 1.1 christos printf 1119 1.1 christos ("\t gen-slot-verification - perform slot verification as part of decode\n"); 1120 1.1 christos printf ("\t gen-nia-invalid - NIA defaults to nia_invalid\n"); 1121 1.1 christos printf ("\t gen-nia-void - do not compute/return NIA\n"); 1122 1.1 christos printf ("\n"); 1123 1.1 christos printf 1124 1.1 christos ("\t trace-combine - report combined entries a rule application\n"); 1125 1.1 christos printf 1126 1.1 christos ("\t trace-entries - report entries after a rules application\n"); 1127 1.1 christos printf ("\t trace-rule-rejection - report each rule as rejected\n"); 1128 1.1 christos printf ("\t trace-rule-selection - report each rule as selected\n"); 1129 1.1 christos printf 1130 1.1 christos ("\t trace-insn-insertion - report each instruction as it is inserted into a decode table\n"); 1131 1.1 christos printf 1132 1.1 christos ("\t trace-rule-expansion - report each instruction as it is expanded (before insertion into a decode table)\n"); 1133 1.1 christos printf ("\t trace-all - enable all trace options\n"); 1134 1.1 christos printf ("\n"); 1135 1.1 christos printf 1136 1.1 christos ("\t field-widths - instruction formats specify widths (deprecated)\n"); 1137 1.1 christos printf 1138 1.1 christos ("\t By default, an instruction format specifies bit\n"); 1139 1.1 christos printf ("\t positions\n"); 1140 1.1 christos printf 1141 1.1 christos ("\t This option can now be set directly in the\n"); 1142 1.1 christos printf ("\t instruction table\n"); 1143 1.1 christos printf 1144 1.1 christos ("\t jumps - use jumps instead of function calls\n"); 1145 1.1 christos printf 1146 1.1 christos ("\t omit-line-numbers - do not include line number information in the output\n"); 1147 1.1 christos printf ("\n"); 1148 1.1 christos printf ("Input options:\n"); 1149 1.1 christos printf ("\n"); 1150 1.1 christos printf (" -k <cache-rules> (deprecated)\n"); 1151 1.1 christos printf (" -o <decode-rules>\n"); 1152 1.1 christos printf (" -i <instruction-table>\n"); 1153 1.1 christos printf ("\n"); 1154 1.1 christos printf ("Output options:\n"); 1155 1.1 christos printf ("\n"); 1156 1.1 christos printf (" -x Perform expansion (required)\n"); 1157 1.1 christos printf 1158 1.1 christos (" -n <real-name> Specify the real name of the next output file\n"); 1159 1.1 christos printf 1160 1.1 christos (" -h Generate the header (.h) file rather than the body (.c)\n"); 1161 1.1 christos printf (" -c <output-file> output icache\n"); 1162 1.1 christos printf (" -d <output-file> output idecode\n"); 1163 1.1 christos printf (" -e <output-file> output engine\n"); 1164 1.1 christos printf (" -f <output-file> output support functions\n"); 1165 1.1 christos printf (" -m <output-file> output model\n"); 1166 1.1 christos printf (" -r <output-file> output multi-sim run\n"); 1167 1.1 christos printf (" -s <output-file> output schematic\n"); 1168 1.1 christos printf (" -t <output-file> output itable\n"); 1169 1.1 christos } 1170 1.1 christos 1171 1.10 christos while ((ch = getopt_long (argc, argv, 1172 1.10 christos "B:D:F:G:H:I:M:N:P:T:W:o:k:i:n:hc:d:e:m:r:s:t:f:x", 1173 1.10 christos longopts, NULL)) 1174 1.1 christos != -1) 1175 1.1 christos { 1176 1.10 christos #if 0 /* For debugging. */ 1177 1.1 christos fprintf (stderr, " -%c ", ch); 1178 1.1 christos if (optarg) 1179 1.1 christos fprintf (stderr, "%s ", optarg); 1180 1.1 christos fprintf (stderr, "\\\n"); 1181 1.10 christos #endif 1182 1.1 christos 1183 1.1 christos switch (ch) 1184 1.1 christos { 1185 1.1 christos 1186 1.1 christos case 'M': 1187 1.1 christos filter_parse (&options.model_filter, optarg); 1188 1.1 christos break; 1189 1.1 christos 1190 1.1 christos case 'D': 1191 1.1 christos if (strcmp (optarg, "processor-names")) 1192 1.1 christos { 1193 1.10 christos const char *processor; 1194 1.1 christos for (processor = filter_next (options.model_filter, ""); 1195 1.1 christos processor != NULL; 1196 1.1 christos processor = filter_next (options.model_filter, processor)) 1197 1.1 christos lf_printf (standard_out, "%s\n", processor); 1198 1.1 christos } 1199 1.1 christos else 1200 1.1 christos error (NULL, "Unknown data structure %s, not dumped\n", optarg); 1201 1.1 christos break; 1202 1.1 christos 1203 1.1 christos case 'F': 1204 1.1 christos filter_parse (&options.flags_filter, optarg); 1205 1.1 christos break; 1206 1.1 christos 1207 1.1 christos case 'I': 1208 1.1 christos { 1209 1.1 christos table_include **dir = &options.include; 1210 1.1 christos while ((*dir) != NULL) 1211 1.1 christos dir = &(*dir)->next; 1212 1.1 christos (*dir) = ZALLOC (table_include); 1213 1.1 christos (*dir)->dir = strdup (optarg); 1214 1.1 christos } 1215 1.1 christos break; 1216 1.1 christos 1217 1.1 christos case 'B': 1218 1.1 christos options.insn_bit_size = a2i (optarg); 1219 1.1 christos if (options.insn_bit_size <= 0 1220 1.1 christos || options.insn_bit_size > max_insn_bit_size) 1221 1.1 christos { 1222 1.1 christos error (NULL, "Instruction bitsize must be in range 1..%d\n", 1223 1.1 christos max_insn_bit_size); 1224 1.1 christos } 1225 1.1 christos if (options.hi_bit_nr != options.insn_bit_size - 1 1226 1.1 christos && options.hi_bit_nr != 0) 1227 1.1 christos { 1228 1.1 christos error (NULL, "Conflict betweem hi-bit-nr and insn-bit-size\n"); 1229 1.1 christos } 1230 1.1 christos break; 1231 1.1 christos 1232 1.1 christos case 'H': 1233 1.1 christos options.hi_bit_nr = a2i (optarg); 1234 1.1 christos if (options.hi_bit_nr != options.insn_bit_size - 1 1235 1.1 christos && options.hi_bit_nr != 0) 1236 1.1 christos { 1237 1.1 christos error (NULL, "Conflict between hi-bit-nr and insn-bit-size\n"); 1238 1.1 christos } 1239 1.1 christos break; 1240 1.1 christos 1241 1.1 christos case 'N': 1242 1.1 christos options.gen.smp = a2i (optarg); 1243 1.1 christos break; 1244 1.1 christos 1245 1.1 christos case 'P': 1246 1.1 christos case 'S': 1247 1.1 christos { 1248 1.1 christos igen_module *names; 1249 1.1 christos igen_name *name; 1250 1.1 christos char *chp; 1251 1.1 christos chp = strchr (optarg, '='); 1252 1.1 christos if (chp == NULL) 1253 1.1 christos { 1254 1.1 christos names = &options.module.global; 1255 1.1 christos chp = optarg; 1256 1.1 christos } 1257 1.1 christos else 1258 1.1 christos { 1259 1.1 christos chp = chp + 1; /* skip `=' */ 1260 1.1 christos names = NULL; 1261 1.1 christos if (strncmp (optarg, "global=", chp - optarg) == 0) 1262 1.1 christos { 1263 1.1 christos names = &options.module.global; 1264 1.1 christos } 1265 1.1 christos if (strncmp (optarg, "engine=", chp - optarg) == 0) 1266 1.1 christos { 1267 1.1 christos names = &options.module.engine; 1268 1.1 christos } 1269 1.1 christos if (strncmp (optarg, "icache=", chp - optarg) == 0) 1270 1.1 christos { 1271 1.1 christos names = &options.module.icache; 1272 1.1 christos } 1273 1.1 christos if (strncmp (optarg, "idecode=", chp - optarg) == 0) 1274 1.1 christos { 1275 1.1 christos names = &options.module.idecode; 1276 1.1 christos } 1277 1.1 christos if (strncmp (optarg, "itable=", chp - optarg) == 0) 1278 1.1 christos { 1279 1.1 christos names = &options.module.itable; 1280 1.1 christos } 1281 1.1 christos if (strncmp (optarg, "semantics=", chp - optarg) == 0) 1282 1.1 christos { 1283 1.1 christos names = &options.module.semantics; 1284 1.1 christos } 1285 1.1 christos if (strncmp (optarg, "support=", chp - optarg) == 0) 1286 1.1 christos { 1287 1.1 christos names = &options.module.support; 1288 1.1 christos } 1289 1.1 christos if (names == NULL) 1290 1.1 christos { 1291 1.1 christos error (NULL, "Prefix `%s' unreconized\n", optarg); 1292 1.1 christos } 1293 1.1 christos } 1294 1.1 christos switch (ch) 1295 1.1 christos { 1296 1.1 christos case 'P': 1297 1.1 christos name = &names->prefix; 1298 1.1 christos break; 1299 1.1 christos case 'S': 1300 1.1 christos name = &names->suffix; 1301 1.1 christos break; 1302 1.1 christos default: 1303 1.1 christos abort (); /* Bad switch. */ 1304 1.1 christos } 1305 1.1 christos name->u = strdup (chp); 1306 1.1 christos name->l = strdup (chp); 1307 1.1 christos chp = name->u; 1308 1.1 christos while (*chp) 1309 1.1 christos { 1310 1.1 christos if (islower (*chp)) 1311 1.1 christos *chp = toupper (*chp); 1312 1.1 christos chp++; 1313 1.1 christos } 1314 1.1 christos if (name == &options.module.global.prefix) 1315 1.1 christos { 1316 1.1 christos options.module.engine.prefix = options.module.global.prefix; 1317 1.1 christos options.module.icache.prefix = options.module.global.prefix; 1318 1.1 christos options.module.idecode.prefix = options.module.global.prefix; 1319 1.1 christos /* options.module.itable.prefix = options.module.global.prefix; */ 1320 1.1 christos options.module.semantics.prefix = 1321 1.1 christos options.module.global.prefix; 1322 1.1 christos options.module.support.prefix = options.module.global.prefix; 1323 1.1 christos } 1324 1.1 christos if (name == &options.module.global.suffix) 1325 1.1 christos { 1326 1.1 christos options.module.engine.suffix = options.module.global.suffix; 1327 1.1 christos options.module.icache.suffix = options.module.global.suffix; 1328 1.1 christos options.module.idecode.suffix = options.module.global.suffix; 1329 1.1 christos /* options.module.itable.suffix = options.module.global.suffix; */ 1330 1.1 christos options.module.semantics.suffix = 1331 1.1 christos options.module.global.suffix; 1332 1.1 christos options.module.support.suffix = options.module.global.suffix; 1333 1.1 christos } 1334 1.1 christos break; 1335 1.1 christos } 1336 1.1 christos 1337 1.1 christos case 'W': 1338 1.1 christos { 1339 1.1 christos if (strcmp (optarg, "error") == 0) 1340 1.1 christos options.warning = error; 1341 1.1 christos else if (strcmp (optarg, "nodiscard") == 0) 1342 1.1 christos options.warn.discard = 0; 1343 1.1 christos else if (strcmp (optarg, "discard") == 0) 1344 1.1 christos options.warn.discard = 1; 1345 1.1 christos else if (strcmp (optarg, "nowidth") == 0) 1346 1.1 christos options.warn.width = 0; 1347 1.1 christos else if (strcmp (optarg, "width") == 0) 1348 1.1 christos options.warn.width = 1; 1349 1.1 christos else if (strcmp (optarg, "nounimplemented") == 0) 1350 1.1 christos options.warn.unimplemented = 0; 1351 1.1 christos else if (strcmp (optarg, "unimplemented") == 0) 1352 1.1 christos options.warn.unimplemented = 1; 1353 1.1 christos else 1354 1.1 christos error (NULL, "Unknown -W argument `%s'\n", optarg); 1355 1.1 christos break; 1356 1.1 christos } 1357 1.1 christos 1358 1.1 christos 1359 1.1 christos case 'G': 1360 1.1 christos { 1361 1.1 christos int enable_p; 1362 1.1 christos char *argp; 1363 1.1 christos if (strncmp (optarg, "no-", strlen ("no-")) == 0) 1364 1.1 christos { 1365 1.1 christos argp = optarg + strlen ("no-"); 1366 1.1 christos enable_p = 0; 1367 1.1 christos } 1368 1.1 christos else if (strncmp (optarg, "!", strlen ("!")) == 0) 1369 1.1 christos { 1370 1.1 christos argp = optarg + strlen ("no-"); 1371 1.1 christos enable_p = 0; 1372 1.1 christos } 1373 1.1 christos else 1374 1.1 christos { 1375 1.1 christos argp = optarg; 1376 1.1 christos enable_p = 1; 1377 1.1 christos } 1378 1.1 christos if (strcmp (argp, "decode-duplicate") == 0) 1379 1.1 christos { 1380 1.1 christos options.decode.duplicate = enable_p; 1381 1.1 christos } 1382 1.1 christos else if (strcmp (argp, "decode-combine") == 0) 1383 1.1 christos { 1384 1.1 christos options.decode.combine = enable_p; 1385 1.1 christos } 1386 1.1 christos else if (strcmp (argp, "decode-zero-reserved") == 0) 1387 1.1 christos { 1388 1.1 christos options.decode.zero_reserved = enable_p; 1389 1.1 christos } 1390 1.1 christos 1391 1.1 christos else if (strcmp (argp, "gen-conditional-issue") == 0) 1392 1.1 christos { 1393 1.1 christos options.gen.conditional_issue = enable_p; 1394 1.1 christos } 1395 1.1 christos else if (strcmp (argp, "conditional-issue") == 0) 1396 1.1 christos { 1397 1.1 christos options.gen.conditional_issue = enable_p; 1398 1.1 christos options.warning (NULL, 1399 1.1 christos "Option conditional-issue replaced by gen-conditional-issue\n"); 1400 1.1 christos } 1401 1.1 christos else if (strcmp (argp, "gen-delayed-branch") == 0) 1402 1.1 christos { 1403 1.1 christos options.gen.delayed_branch = enable_p; 1404 1.1 christos } 1405 1.1 christos else if (strcmp (argp, "delayed-branch") == 0) 1406 1.1 christos { 1407 1.1 christos options.gen.delayed_branch = enable_p; 1408 1.1 christos options.warning (NULL, 1409 1.1 christos "Option delayed-branch replaced by gen-delayed-branch\n"); 1410 1.1 christos } 1411 1.1 christos else if (strcmp (argp, "gen-direct-access") == 0) 1412 1.1 christos { 1413 1.1 christos options.gen.direct_access = enable_p; 1414 1.1 christos } 1415 1.1 christos else if (strcmp (argp, "direct-access") == 0) 1416 1.1 christos { 1417 1.1 christos options.gen.direct_access = enable_p; 1418 1.1 christos options.warning (NULL, 1419 1.1 christos "Option direct-access replaced by gen-direct-access\n"); 1420 1.1 christos } 1421 1.1 christos else if (strncmp (argp, "gen-zero-r", strlen ("gen-zero-r")) == 0) 1422 1.1 christos { 1423 1.1 christos options.gen.zero_reg = enable_p; 1424 1.1 christos options.gen.zero_reg_nr = atoi (argp + strlen ("gen-zero-r")); 1425 1.1 christos } 1426 1.1 christos else if (strncmp (argp, "zero-r", strlen ("zero-r")) == 0) 1427 1.1 christos { 1428 1.1 christos options.gen.zero_reg = enable_p; 1429 1.1 christos options.gen.zero_reg_nr = atoi (argp + strlen ("zero-r")); 1430 1.1 christos options.warning (NULL, 1431 1.1 christos "Option zero-r<N> replaced by gen-zero-r<N>\n"); 1432 1.1 christos } 1433 1.1 christos else if (strncmp (argp, "gen-icache", strlen ("gen-icache")) == 0) 1434 1.1 christos { 1435 1.1 christos switch (argp[strlen ("gen-icache")]) 1436 1.1 christos { 1437 1.1 christos case '=': 1438 1.1 christos options.gen.icache_size = 1439 1.1 christos atoi (argp + strlen ("gen-icache") + 1); 1440 1.1 christos options.gen.icache = enable_p; 1441 1.1 christos break; 1442 1.1 christos case '\0': 1443 1.1 christos options.gen.icache = enable_p; 1444 1.1 christos break; 1445 1.1 christos default: 1446 1.1 christos error (NULL, 1447 1.1 christos "Expecting -Ggen-icache or -Ggen-icache=<N>\n"); 1448 1.1 christos } 1449 1.1 christos } 1450 1.1 christos else if (strcmp (argp, "gen-insn-in-icache") == 0) 1451 1.1 christos { 1452 1.1 christos options.gen.insn_in_icache = enable_p; 1453 1.1 christos } 1454 1.1 christos else if (strncmp (argp, "gen-multi-sim", strlen ("gen-multi-sim")) 1455 1.1 christos == 0) 1456 1.1 christos { 1457 1.1 christos char *arg = &argp[strlen ("gen-multi-sim")]; 1458 1.1 christos switch (arg[0]) 1459 1.1 christos { 1460 1.1 christos case '=': 1461 1.1 christos options.gen.multi_sim = enable_p; 1462 1.1 christos options.gen.default_model = arg + 1; 1463 1.1 christos if (!filter_is_member 1464 1.1 christos (options.model_filter, options.gen.default_model)) 1465 1.1 christos error (NULL, "multi-sim model %s unknown\n", 1466 1.1 christos options.gen.default_model); 1467 1.1 christos break; 1468 1.1 christos case '\0': 1469 1.1 christos options.gen.multi_sim = enable_p; 1470 1.1 christos options.gen.default_model = NULL; 1471 1.1 christos break; 1472 1.1 christos default: 1473 1.1 christos error (NULL, 1474 1.1 christos "Expecting -Ggen-multi-sim or -Ggen-multi-sim=<MODEL>\n"); 1475 1.1 christos break; 1476 1.1 christos } 1477 1.1 christos } 1478 1.1 christos else if (strcmp (argp, "gen-multi-word") == 0) 1479 1.1 christos { 1480 1.1 christos options.gen.multi_word = enable_p; 1481 1.1 christos } 1482 1.1 christos else if (strcmp (argp, "gen-semantic-icache") == 0) 1483 1.1 christos { 1484 1.1 christos options.gen.semantic_icache = enable_p; 1485 1.1 christos } 1486 1.1 christos else if (strcmp (argp, "gen-slot-verification") == 0) 1487 1.1 christos { 1488 1.1 christos options.gen.slot_verification = enable_p; 1489 1.1 christos } 1490 1.1 christos else if (strcmp (argp, "verify-slot") == 0) 1491 1.1 christos { 1492 1.1 christos options.gen.slot_verification = enable_p; 1493 1.1 christos options.warning (NULL, 1494 1.1 christos "Option verify-slot replaced by gen-slot-verification\n"); 1495 1.1 christos } 1496 1.1 christos else if (strcmp (argp, "gen-nia-invalid") == 0) 1497 1.1 christos { 1498 1.1 christos options.gen.nia = nia_is_invalid; 1499 1.1 christos } 1500 1.1 christos else if (strcmp (argp, "default-nia-minus-one") == 0) 1501 1.1 christos { 1502 1.1 christos options.gen.nia = nia_is_invalid; 1503 1.1 christos options.warning (NULL, 1504 1.1 christos "Option default-nia-minus-one replaced by gen-nia-invalid\n"); 1505 1.1 christos } 1506 1.1 christos else if (strcmp (argp, "gen-nia-void") == 0) 1507 1.1 christos { 1508 1.1 christos options.gen.nia = nia_is_void; 1509 1.1 christos } 1510 1.1 christos else if (strcmp (argp, "trace-all") == 0) 1511 1.1 christos { 1512 1.1 christos memset (&options.trace, enable_p, sizeof (options.trace)); 1513 1.1 christos } 1514 1.1 christos else if (strcmp (argp, "trace-combine") == 0) 1515 1.1 christos { 1516 1.1 christos options.trace.combine = enable_p; 1517 1.1 christos } 1518 1.1 christos else if (strcmp (argp, "trace-entries") == 0) 1519 1.1 christos { 1520 1.1 christos options.trace.entries = enable_p; 1521 1.1 christos } 1522 1.1 christos else if (strcmp (argp, "trace-rule-rejection") == 0) 1523 1.1 christos { 1524 1.1 christos options.trace.rule_rejection = enable_p; 1525 1.1 christos } 1526 1.1 christos else if (strcmp (argp, "trace-rule-selection") == 0) 1527 1.1 christos { 1528 1.1 christos options.trace.rule_selection = enable_p; 1529 1.1 christos } 1530 1.1 christos else if (strcmp (argp, "trace-insn-insertion") == 0) 1531 1.1 christos { 1532 1.1 christos options.trace.insn_insertion = enable_p; 1533 1.1 christos } 1534 1.1 christos else if (strcmp (argp, "trace-insn-expansion") == 0) 1535 1.1 christos { 1536 1.1 christos options.trace.insn_expansion = enable_p; 1537 1.1 christos } 1538 1.1 christos else if (strcmp (argp, "jumps") == 0) 1539 1.1 christos { 1540 1.1 christos options.gen.code = generate_jumps; 1541 1.1 christos } 1542 1.1 christos else if (strcmp (argp, "field-widths") == 0) 1543 1.1 christos { 1544 1.1 christos options.insn_specifying_widths = enable_p; 1545 1.1 christos } 1546 1.1 christos else if (strcmp (argp, "omit-line-numbers") == 0) 1547 1.1 christos { 1548 1.1 christos file_references = lf_omit_references; 1549 1.1 christos } 1550 1.1 christos else 1551 1.1 christos { 1552 1.1 christos error (NULL, "Unknown option %s\n", optarg); 1553 1.1 christos } 1554 1.1 christos break; 1555 1.1 christos } 1556 1.1 christos 1557 1.1 christos case 'i': 1558 1.1 christos isa = load_insn_table (optarg, cache_rules); 1559 1.1 christos if (isa->illegal_insn == NULL) 1560 1.1 christos error (NULL, "illegal-instruction missing from insn table\n"); 1561 1.1 christos break; 1562 1.1 christos 1563 1.1 christos case 'x': 1564 1.1 christos gen = do_gen (isa, decode_rules); 1565 1.1 christos break; 1566 1.1 christos 1567 1.1 christos case 'o': 1568 1.1 christos decode_rules = load_decode_table (optarg); 1569 1.1 christos break; 1570 1.1 christos 1571 1.1 christos case 'k': 1572 1.1 christos if (isa != NULL) 1573 1.1 christos error (NULL, "Cache file must appear before the insn file\n"); 1574 1.1 christos cache_rules = load_cache_table (optarg); 1575 1.1 christos break; 1576 1.1 christos 1577 1.1 christos case 'n': 1578 1.1 christos real_file_name = strdup (optarg); 1579 1.1 christos break; 1580 1.1 christos 1581 1.1 christos case 'h': 1582 1.1 christos is_header = 1; 1583 1.1 christos break; 1584 1.1 christos 1585 1.1 christos case 'c': 1586 1.1 christos case 'd': 1587 1.1 christos case 'e': 1588 1.1 christos case 'f': 1589 1.1 christos case 'm': 1590 1.1 christos case 'r': 1591 1.1 christos case 's': 1592 1.1 christos case 't': 1593 1.1 christos { 1594 1.1 christos lf *file = lf_open (optarg, real_file_name, file_references, 1595 1.1 christos (is_header ? lf_is_h : lf_is_c), 1596 1.1 christos argv[0]); 1597 1.1 christos if (gen == NULL && ch != 't' && ch != 'm' && ch != 'f') 1598 1.1 christos { 1599 1.1 christos options.warning (NULL, 1600 1.1 christos "Explicitly generate tables with -x option\n"); 1601 1.1 christos gen = do_gen (isa, decode_rules); 1602 1.1 christos } 1603 1.1 christos lf_print__file_start (file); 1604 1.1 christos switch (ch) 1605 1.1 christos { 1606 1.1 christos case 'm': 1607 1.1 christos if (is_header) 1608 1.1 christos gen_model_h (file, isa); 1609 1.1 christos else 1610 1.1 christos gen_model_c (file, isa); 1611 1.1 christos break; 1612 1.1 christos case 't': 1613 1.1 christos if (is_header) 1614 1.1 christos gen_itable_h (file, isa); 1615 1.1 christos else 1616 1.1 christos gen_itable_c (file, isa); 1617 1.1 christos break; 1618 1.1 christos case 'f': 1619 1.1 christos if (is_header) 1620 1.1 christos gen_support_h (file, isa); 1621 1.1 christos else 1622 1.1 christos gen_support_c (file, isa); 1623 1.1 christos break; 1624 1.1 christos case 'r': 1625 1.1 christos if (is_header) 1626 1.1 christos options.warning (NULL, "-hr option ignored\n"); 1627 1.1 christos else 1628 1.1 christos gen_run_c (file, gen); 1629 1.1 christos break; 1630 1.1 christos case 's': 1631 1.1 christos if (is_header) 1632 1.1 christos gen_semantics_h (file, gen->semantics, isa->max_nr_words); 1633 1.1 christos else 1634 1.1 christos gen_semantics_c (file, gen->semantics, isa->caches); 1635 1.1 christos break; 1636 1.1 christos case 'd': 1637 1.1 christos if (is_header) 1638 1.1 christos gen_idecode_h (file, gen, isa, cache_rules); 1639 1.1 christos else 1640 1.1 christos gen_idecode_c (file, gen, isa, cache_rules); 1641 1.1 christos break; 1642 1.1 christos case 'e': 1643 1.1 christos if (is_header) 1644 1.1 christos gen_engine_h (file, gen, isa, cache_rules); 1645 1.1 christos else 1646 1.1 christos gen_engine_c (file, gen, isa, cache_rules); 1647 1.1 christos break; 1648 1.1 christos case 'c': 1649 1.1 christos if (is_header) 1650 1.1 christos gen_icache_h (file, 1651 1.1 christos gen->semantics, 1652 1.1 christos isa->functions, isa->max_nr_words); 1653 1.1 christos else 1654 1.1 christos gen_icache_c (file, 1655 1.1 christos gen->semantics, isa->functions, cache_rules); 1656 1.1 christos break; 1657 1.1 christos } 1658 1.1 christos lf_print__file_finish (file); 1659 1.1 christos lf_close (file); 1660 1.1 christos is_header = 0; 1661 1.1 christos } 1662 1.1 christos real_file_name = NULL; 1663 1.1 christos break; 1664 1.1 christos default: 1665 1.1 christos ERROR ("Bad switch"); 1666 1.1 christos } 1667 1.1 christos } 1668 1.1 christos return (0); 1669 1.1 christos } 1670