1 /* gdb-if.c -- sim interface to GDB. 2 3 Copyright (C) 2011-2013 Free Software Foundation, Inc. 4 Contributed by Red Hat, Inc. 5 6 This file is part of the GNU simulators. 7 8 This program is free software; you can redistribute it and/or modify 9 it under the terms of the GNU General Public License as published by 10 the Free Software Foundation; either version 3 of the License, or 11 (at your option) any later version. 12 13 This program is distributed in the hope that it will be useful, 14 but WITHOUT ANY WARRANTY; without even the implied warranty of 15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 GNU General Public License for more details. 17 18 You should have received a copy of the GNU General Public License 19 along with this program. If not, see <http://www.gnu.org/licenses/>. */ 20 21 #include "config.h" 22 #include <stdio.h> 23 #include <assert.h> 24 #include <signal.h> 25 #include <string.h> 26 #include <ctype.h> 27 #include <stdlib.h> 28 29 #include "ansidecl.h" 30 #include "gdb/callback.h" 31 #include "gdb/remote-sim.h" 32 #include "gdb/signals.h" 33 #include "gdb/sim-rl78.h" 34 35 #include "cpu.h" 36 #include "mem.h" 37 #include "load.h" 38 #include "trace.h" 39 40 /* Ideally, we'd wrap up all the minisim's data structures in an 41 object and pass that around. However, neither GDB nor run needs 42 that ability. 43 44 So we just have one instance, that lives in global variables, and 45 each time we open it, we re-initialize it. */ 46 47 struct sim_state 48 { 49 const char *message; 50 }; 51 52 static struct sim_state the_minisim = { 53 "This is the sole rl78 minisim instance." 54 }; 55 56 static int open; 57 58 static unsigned char hw_breakpoints[MEM_SIZE/8]; 59 60 static struct host_callback_struct *host_callbacks; 61 62 /* Open an instance of the sim. For this sim, only one instance 63 is permitted. If sim_open() is called multiple times, the sim 64 will be reset. */ 65 66 SIM_DESC 67 sim_open (SIM_OPEN_KIND kind, 68 struct host_callback_struct *callback, 69 struct bfd *abfd, char **argv) 70 { 71 if (open) 72 fprintf (stderr, "rl78 minisim: re-opened sim\n"); 73 74 /* The 'run' interface doesn't use this function, so we don't care 75 about KIND; it's always SIM_OPEN_DEBUG. */ 76 if (kind != SIM_OPEN_DEBUG) 77 fprintf (stderr, "rl78 minisim: sim_open KIND != SIM_OPEN_DEBUG: %d\n", 78 kind); 79 80 /* We use this for the load command. Perhaps someday, it'll be used 81 for syscalls too. */ 82 host_callbacks = callback; 83 84 /* We don't expect any command-line arguments. */ 85 86 init_cpu (); 87 trace = 0; 88 89 sim_disasm_init (abfd); 90 open = 1; 91 return &the_minisim; 92 } 93 94 /* Verify the sim descriptor. Just print a message if the descriptor 95 doesn't match. Nothing bad will happen if the descriptor doesn't 96 match because all of the state is global. But if it doesn't 97 match, that means there's a problem with the caller. */ 98 99 static void 100 check_desc (SIM_DESC sd) 101 { 102 if (sd != &the_minisim) 103 fprintf (stderr, "rl78 minisim: desc != &the_minisim\n"); 104 } 105 106 /* Close the sim. */ 107 108 void 109 sim_close (SIM_DESC sd, int quitting) 110 { 111 check_desc (sd); 112 113 /* Not much to do. At least free up our memory. */ 114 init_mem (); 115 116 open = 0; 117 } 118 119 /* Open the program to run; print a message if the program cannot 120 be opened. */ 121 122 static bfd * 123 open_objfile (const char *filename) 124 { 125 bfd *prog = bfd_openr (filename, 0); 126 127 if (!prog) 128 { 129 fprintf (stderr, "Can't read %s\n", filename); 130 return 0; 131 } 132 133 if (!bfd_check_format (prog, bfd_object)) 134 { 135 fprintf (stderr, "%s not a rl78 program\n", filename); 136 return 0; 137 } 138 139 return prog; 140 } 141 142 /* Load a program. */ 143 144 SIM_RC 145 sim_load (SIM_DESC sd, char *prog, struct bfd *abfd, int from_tty) 146 { 147 check_desc (sd); 148 149 if (!abfd) 150 abfd = open_objfile (prog); 151 if (!abfd) 152 return SIM_RC_FAIL; 153 154 rl78_load (abfd, host_callbacks, "sim"); 155 156 return SIM_RC_OK; 157 } 158 159 /* Create inferior. */ 160 161 SIM_RC 162 sim_create_inferior (SIM_DESC sd, struct bfd *abfd, char **argv, char **env) 163 { 164 check_desc (sd); 165 166 if (abfd) 167 rl78_load (abfd, 0, "sim"); 168 169 return SIM_RC_OK; 170 } 171 172 /* Read memory. */ 173 174 int 175 sim_read (SIM_DESC sd, SIM_ADDR mem, unsigned char *buf, int length) 176 { 177 check_desc (sd); 178 179 if (mem >= MEM_SIZE) 180 return 0; 181 else if (mem + length > MEM_SIZE) 182 length = MEM_SIZE - mem; 183 184 mem_get_blk (mem, buf, length); 185 return length; 186 } 187 188 /* Write memory. */ 189 190 int 191 sim_write (SIM_DESC sd, SIM_ADDR mem, const unsigned char *buf, int length) 192 { 193 check_desc (sd); 194 195 if (mem >= MEM_SIZE) 196 return 0; 197 else if (mem + length > MEM_SIZE) 198 length = MEM_SIZE - mem; 199 200 mem_put_blk (mem, buf, length); 201 return length; 202 } 203 204 /* Read the LENGTH bytes at BUF as an little-endian value. */ 205 206 static SI 207 get_le (unsigned char *buf, int length) 208 { 209 SI acc = 0; 210 211 while (--length >= 0) 212 acc = (acc << 8) + buf[length]; 213 214 return acc; 215 } 216 217 /* Store VAL as a little-endian value in the LENGTH bytes at BUF. */ 218 219 static void 220 put_le (unsigned char *buf, int length, SI val) 221 { 222 int i; 223 224 for (i = 0; i < length; i++) 225 { 226 buf[i] = val & 0xff; 227 val >>= 8; 228 } 229 } 230 231 /* Verify that REGNO is in the proper range. Return 0 if not and 232 something non-zero if so. */ 233 234 static int 235 check_regno (enum sim_rl78_regnum regno) 236 { 237 return 0 <= regno && regno < sim_rl78_num_regs; 238 } 239 240 /* Return the size of the register REGNO. */ 241 242 static size_t 243 reg_size (enum sim_rl78_regnum regno) 244 { 245 size_t size; 246 247 if (regno == sim_rl78_pc_regnum) 248 size = 4; 249 else 250 size = 1; 251 252 return size; 253 } 254 255 /* Return the register address associated with the register specified by 256 REGNO. */ 257 258 static unsigned long 259 reg_addr (enum sim_rl78_regnum regno) 260 { 261 if (sim_rl78_bank0_r0_regnum <= regno 262 && regno <= sim_rl78_bank0_r7_regnum) 263 return 0xffef8 + (regno - sim_rl78_bank0_r0_regnum); 264 else if (sim_rl78_bank1_r0_regnum <= regno 265 && regno <= sim_rl78_bank1_r7_regnum) 266 return 0xffef0 + (regno - sim_rl78_bank1_r0_regnum); 267 else if (sim_rl78_bank2_r0_regnum <= regno 268 && regno <= sim_rl78_bank2_r7_regnum) 269 return 0xffee8 + (regno - sim_rl78_bank2_r0_regnum); 270 else if (sim_rl78_bank3_r0_regnum <= regno 271 && regno <= sim_rl78_bank3_r7_regnum) 272 return 0xffee0 + (regno - sim_rl78_bank3_r0_regnum); 273 else if (regno == sim_rl78_psw_regnum) 274 return 0xffffa; 275 else if (regno == sim_rl78_es_regnum) 276 return 0xffffd; 277 else if (regno == sim_rl78_cs_regnum) 278 return 0xffffc; 279 /* Note: We can't handle PC here because it's not memory mapped. */ 280 else if (regno == sim_rl78_spl_regnum) 281 return 0xffff8; 282 else if (regno == sim_rl78_sph_regnum) 283 return 0xffff9; 284 else if (regno == sim_rl78_pmc_regnum) 285 return 0xffffe; 286 else if (regno == sim_rl78_mem_regnum) 287 return 0xfffff; 288 289 return 0; 290 } 291 292 /* Fetch the contents of the register specified by REGNO, placing the 293 contents in BUF. The length LENGTH must match the sim's internal 294 notion of the register's size. */ 295 296 int 297 sim_fetch_register (SIM_DESC sd, int regno, unsigned char *buf, int length) 298 { 299 size_t size; 300 SI val; 301 302 check_desc (sd); 303 304 if (!check_regno (regno)) 305 return 0; 306 307 size = reg_size (regno); 308 309 if (length != size) 310 return 0; 311 312 if (regno == sim_rl78_pc_regnum) 313 val = pc; 314 else 315 val = memory[reg_addr (regno)]; 316 317 put_le (buf, length, val); 318 319 return size; 320 } 321 322 /* Store the value stored in BUF to the register REGNO. The length 323 LENGTH must match the sim's internal notion of the register size. */ 324 325 int 326 sim_store_register (SIM_DESC sd, int regno, unsigned char *buf, int length) 327 { 328 size_t size; 329 SI val; 330 331 check_desc (sd); 332 333 if (!check_regno (regno)) 334 return -1; 335 336 size = reg_size (regno); 337 338 if (length != size) 339 return -1; 340 341 val = get_le (buf, length); 342 343 if (regno == sim_rl78_pc_regnum) 344 pc = val; 345 else 346 memory[reg_addr (regno)] = val; 347 return size; 348 } 349 350 /* Print out message associated with "info target". */ 351 352 void 353 sim_info (SIM_DESC sd, int verbose) 354 { 355 check_desc (sd); 356 357 printf ("The rl78 minisim doesn't collect any statistics.\n"); 358 } 359 360 static volatile int stop; 361 static enum sim_stop reason; 362 int siggnal; 363 364 365 /* Given a signal number used by the rl78 bsp (that is, newlib), 366 return the corresponding signal numbers. */ 367 368 int 369 rl78_signal_to_target (int sig) 370 { 371 switch (sig) 372 { 373 case 4: 374 return GDB_SIGNAL_ILL; 375 376 case 5: 377 return GDB_SIGNAL_TRAP; 378 379 case 10: 380 return GDB_SIGNAL_BUS; 381 382 case 11: 383 return GDB_SIGNAL_SEGV; 384 385 case 24: 386 return GDB_SIGNAL_XCPU; 387 break; 388 389 case 2: 390 return GDB_SIGNAL_INT; 391 392 case 8: 393 return GDB_SIGNAL_FPE; 394 break; 395 396 case 6: 397 return GDB_SIGNAL_ABRT; 398 } 399 400 return 0; 401 } 402 403 404 /* Take a step return code RC and set up the variables consulted by 405 sim_stop_reason appropriately. */ 406 407 void 408 handle_step (int rc) 409 { 410 if (RL78_STEPPED (rc) || RL78_HIT_BREAK (rc)) 411 { 412 reason = sim_stopped; 413 siggnal = GDB_SIGNAL_TRAP; 414 } 415 else if (RL78_STOPPED (rc)) 416 { 417 reason = sim_stopped; 418 siggnal = rl78_signal_to_target (RL78_STOP_SIG (rc)); 419 } 420 else 421 { 422 assert (RL78_EXITED (rc)); 423 reason = sim_exited; 424 siggnal = RL78_EXIT_STATUS (rc); 425 } 426 } 427 428 429 /* Resume execution after a stop. */ 430 431 void 432 sim_resume (SIM_DESC sd, int step, int sig_to_deliver) 433 { 434 int rc; 435 436 check_desc (sd); 437 438 if (sig_to_deliver != 0) 439 { 440 fprintf (stderr, 441 "Warning: the rl78 minisim does not implement " 442 "signal delivery yet.\n" "Resuming with no signal.\n"); 443 } 444 445 /* We don't clear 'stop' here, because then we would miss 446 interrupts that arrived on the way here. Instead, we clear 447 the flag in sim_stop_reason, after GDB has disabled the 448 interrupt signal handler. */ 449 for (;;) 450 { 451 if (stop) 452 { 453 stop = 0; 454 reason = sim_stopped; 455 siggnal = GDB_SIGNAL_INT; 456 break; 457 } 458 459 if (hw_breakpoints[pc >> 3] 460 && (hw_breakpoints[pc >> 3] & (1 << (pc & 0x7)))) 461 { 462 reason = sim_stopped; 463 siggnal = GDB_SIGNAL_TRAP; 464 break; 465 } 466 rc = setjmp (decode_jmp_buf); 467 if (rc == 0) 468 rc = decode_opcode (); 469 470 if (!RL78_STEPPED (rc) || step) 471 { 472 handle_step (rc); 473 break; 474 } 475 } 476 } 477 478 /* Stop the sim. */ 479 480 int 481 sim_stop (SIM_DESC sd) 482 { 483 stop = 1; 484 485 return 1; 486 } 487 488 /* Fetch the stop reason and signal. */ 489 490 void 491 sim_stop_reason (SIM_DESC sd, enum sim_stop *reason_p, int *sigrc_p) 492 { 493 check_desc (sd); 494 495 *reason_p = reason; 496 *sigrc_p = siggnal; 497 } 498 499 /* Execute the sim-specific command associated with GDB's "sim ..." 500 command. */ 501 502 void 503 sim_do_command (SIM_DESC sd, char *cmd) 504 { 505 char *args; 506 507 check_desc (sd); 508 509 if (cmd == NULL) 510 { 511 cmd = ""; 512 args = ""; 513 } 514 else 515 { 516 char *p = cmd; 517 518 /* Skip leading whitespace. */ 519 while (isspace (*p)) 520 p++; 521 522 /* Find the extent of the command word. */ 523 for (p = cmd; *p; p++) 524 if (isspace (*p)) 525 break; 526 527 /* Null-terminate the command word, and record the start of any 528 further arguments. */ 529 if (*p) 530 { 531 *p = '\0'; 532 args = p + 1; 533 while (isspace (*args)) 534 args++; 535 } 536 else 537 args = p; 538 } 539 540 if (strcmp (cmd, "trace") == 0) 541 { 542 if (strcmp (args, "on") == 0) 543 trace = 1; 544 else if (strcmp (args, "off") == 0) 545 trace = 0; 546 else 547 printf ("The 'sim trace' command expects 'on' or 'off' " 548 "as an argument.\n"); 549 } 550 else if (strcmp (cmd, "verbose") == 0) 551 { 552 if (strcmp (args, "on") == 0) 553 verbose = 1; 554 else if (strcmp (args, "noisy") == 0) 555 verbose = 2; 556 else if (strcmp (args, "off") == 0) 557 verbose = 0; 558 else 559 printf ("The 'sim verbose' command expects 'on', 'noisy', or 'off'" 560 " as an argument.\n"); 561 } 562 else 563 printf ("The 'sim' command expects either 'trace' or 'verbose'" 564 " as a subcommand.\n"); 565 } 566 567 /* Stub for command completion. */ 568 569 char ** 570 sim_complete_command (SIM_DESC sd, char *text, char *word) 571 { 572 return NULL; 573 } 574