1/* Simulator for the Renesas (formerly Hitachi) / SuperH Inc. SH architecture. 2 3 Written by Steve Chamberlain of Cygnus Support. 4 sac@cygnus.com 5 6 This file is part of SH sim 7 8 9 THIS SOFTWARE IS NOT COPYRIGHTED 10 11 Cygnus offers the following for use in the public domain. Cygnus 12 makes no warranty with regard to the software or it's performance 13 and the user accepts the software "AS IS" with all faults. 14 15 CYGNUS DISCLAIMS ANY WARRANTIES, EXPRESS OR IMPLIED, WITH REGARD TO 16 THIS SOFTWARE INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 17 MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 18 19*/ 20 21#include "config.h" 22 23#include <stdio.h> 24#include <errno.h> 25#include <signal.h> 26#ifdef HAVE_UNISTD_H 27#include <unistd.h> 28#endif 29#ifdef HAVE_MMAP 30#include <sys/mman.h> 31# ifndef MAP_FAILED 32# define MAP_FAILED -1 33# endif 34# if !defined (MAP_ANONYMOUS) && defined (MAP_ANON) 35# define MAP_ANONYMOUS MAP_ANON 36# endif 37#endif 38 39#ifdef HAVE_STRING_H 40#include <string.h> 41#else 42#ifdef HAVE_STRINGS_H 43#include <strings.h> 44#endif 45#endif 46 47#ifdef HAVE_STDLIB_H 48#include <stdlib.h> 49#endif 50 51#ifdef HAVE_SYS_STAT_H 52#include <sys/stat.h> 53#endif 54 55#include "bfd.h" 56#include "gdb/callback.h" 57#include "gdb/remote-sim.h" 58#include "gdb/sim-sh.h" 59 60/* This file is local - if newlib changes, then so should this. */ 61#include "syscall.h" 62 63#include <math.h> 64 65#ifdef _WIN32 66#include <float.h> /* Needed for _isnan() */ 67#define isnan _isnan 68#endif 69 70#ifndef SIGBUS 71#define SIGBUS SIGSEGV 72#endif 73 74#ifndef SIGQUIT 75#define SIGQUIT SIGTERM 76#endif 77 78#ifndef SIGTRAP 79#define SIGTRAP 5 80#endif 81 82extern unsigned short sh_jump_table[], sh_dsp_table[0x1000], ppi_table[]; 83 84int sim_write (SIM_DESC sd, SIM_ADDR addr, const unsigned char *buffer, int size); 85 86#define O_RECOMPILE 85 87#define DEFINE_TABLE 88#define DISASSEMBLER_TABLE 89 90/* Define the rate at which the simulator should poll the host 91 for a quit. */ 92#define POLL_QUIT_INTERVAL 0x60000 93 94typedef struct 95{ 96 int regs[20]; 97} regstacktype; 98 99typedef union 100{ 101 102 struct 103 { 104 int regs[16]; 105 int pc; 106 107 /* System registers. For sh-dsp this also includes A0 / X0 / X1 / Y0 / Y1 108 which are located in fregs, i.e. strictly speaking, these are 109 out-of-bounds accesses of sregs.i . This wart of the code could be 110 fixed by making fregs part of sregs, and including pc too - to avoid 111 alignment repercussions - but this would cause very onerous union / 112 structure nesting, which would only be managable with anonymous 113 unions and structs. */ 114 union 115 { 116 struct 117 { 118 int mach; 119 int macl; 120 int pr; 121 int dummy3, dummy4; 122 int fpul; /* A1 for sh-dsp - but only for movs etc. */ 123 int fpscr; /* dsr for sh-dsp */ 124 } named; 125 int i[7]; 126 } sregs; 127 128 /* sh3e / sh-dsp */ 129 union fregs_u 130 { 131 float f[16]; 132 double d[8]; 133 int i[16]; 134 } 135 fregs[2]; 136 137 /* Control registers; on the SH4, ldc / stc is privileged, except when 138 accessing gbr. */ 139 union 140 { 141 struct 142 { 143 int sr; 144 int gbr; 145 int vbr; 146 int ssr; 147 int spc; 148 int mod; 149 /* sh-dsp */ 150 int rs; 151 int re; 152 /* sh3 */ 153 int bank[8]; 154 int dbr; /* debug base register */ 155 int sgr; /* saved gr15 */ 156 int ldst; /* load/store flag (boolean) */ 157 int tbr; 158 int ibcr; /* sh2a bank control register */ 159 int ibnr; /* sh2a bank number register */ 160 } named; 161 int i[16]; 162 } cregs; 163 164 unsigned char *insn_end; 165 166 int ticks; 167 int stalls; 168 int memstalls; 169 int cycles; 170 int insts; 171 172 int prevlock; 173 int thislock; 174 int exception; 175 176 int end_of_registers; 177 178 int msize; 179#define PROFILE_FREQ 1 180#define PROFILE_SHIFT 2 181 int profile; 182 unsigned short *profile_hist; 183 unsigned char *memory; 184 int xyram_select, xram_start, yram_start; 185 unsigned char *xmem; 186 unsigned char *ymem; 187 unsigned char *xmem_offset; 188 unsigned char *ymem_offset; 189 unsigned long bfd_mach; 190 regstacktype *regstack; 191 } 192 asregs; 193 int asints[40]; 194} saved_state_type; 195 196saved_state_type saved_state; 197 198struct loop_bounds { unsigned char *start, *end; }; 199 200/* These variables are at file scope so that functions other than 201 sim_resume can use the fetch/store macros */ 202 203static int target_little_endian; 204static int global_endianw, endianb; 205static int target_dsp; 206static int host_little_endian; 207static char **prog_argv; 208 209static int maskw = 0; 210static int maskl = 0; 211 212static SIM_OPEN_KIND sim_kind; 213static char *myname; 214static int tracing = 0; 215 216 217/* Short hand definitions of the registers */ 218 219#define SBIT(x) ((x)&sbit) 220#define R0 saved_state.asregs.regs[0] 221#define Rn saved_state.asregs.regs[n] 222#define Rm saved_state.asregs.regs[m] 223#define UR0 (unsigned int) (saved_state.asregs.regs[0]) 224#define UR (unsigned int) R 225#define UR (unsigned int) R 226#define SR0 saved_state.asregs.regs[0] 227#define CREG(n) (saved_state.asregs.cregs.i[(n)]) 228#define GBR saved_state.asregs.cregs.named.gbr 229#define VBR saved_state.asregs.cregs.named.vbr 230#define DBR saved_state.asregs.cregs.named.dbr 231#define TBR saved_state.asregs.cregs.named.tbr 232#define IBCR saved_state.asregs.cregs.named.ibcr 233#define IBNR saved_state.asregs.cregs.named.ibnr 234#define BANKN (saved_state.asregs.cregs.named.ibnr & 0x1ff) 235#define ME ((saved_state.asregs.cregs.named.ibnr >> 14) & 0x3) 236#define SSR saved_state.asregs.cregs.named.ssr 237#define SPC saved_state.asregs.cregs.named.spc 238#define SGR saved_state.asregs.cregs.named.sgr 239#define SREG(n) (saved_state.asregs.sregs.i[(n)]) 240#define MACH saved_state.asregs.sregs.named.mach 241#define MACL saved_state.asregs.sregs.named.macl 242#define PR saved_state.asregs.sregs.named.pr 243#define FPUL saved_state.asregs.sregs.named.fpul 244 245#define PC insn_ptr 246 247 248 249/* Alternate bank of registers r0-r7 */ 250 251/* Note: code controling SR handles flips between BANK0 and BANK1 */ 252#define Rn_BANK(n) (saved_state.asregs.cregs.named.bank[(n)]) 253#define SET_Rn_BANK(n, EXP) do { saved_state.asregs.cregs.named.bank[(n)] = (EXP); } while (0) 254 255 256/* Manipulate SR */ 257 258#define SR_MASK_BO (1 << 14) 259#define SR_MASK_CS (1 << 13) 260#define SR_MASK_DMY (1 << 11) 261#define SR_MASK_DMX (1 << 10) 262#define SR_MASK_M (1 << 9) 263#define SR_MASK_Q (1 << 8) 264#define SR_MASK_I (0xf << 4) 265#define SR_MASK_S (1 << 1) 266#define SR_MASK_T (1 << 0) 267 268#define SR_MASK_BL (1 << 28) 269#define SR_MASK_RB (1 << 29) 270#define SR_MASK_MD (1 << 30) 271#define SR_MASK_RC 0x0fff0000 272#define SR_RC_INCREMENT -0x00010000 273 274#define BO ((saved_state.asregs.cregs.named.sr & SR_MASK_BO) != 0) 275#define CS ((saved_state.asregs.cregs.named.sr & SR_MASK_CS) != 0) 276#define M ((saved_state.asregs.cregs.named.sr & SR_MASK_M) != 0) 277#define Q ((saved_state.asregs.cregs.named.sr & SR_MASK_Q) != 0) 278#define S ((saved_state.asregs.cregs.named.sr & SR_MASK_S) != 0) 279#define T ((saved_state.asregs.cregs.named.sr & SR_MASK_T) != 0) 280#define LDST ((saved_state.asregs.cregs.named.ldst) != 0) 281 282#define SR_BL ((saved_state.asregs.cregs.named.sr & SR_MASK_BL) != 0) 283#define SR_RB ((saved_state.asregs.cregs.named.sr & SR_MASK_RB) != 0) 284#define SR_MD ((saved_state.asregs.cregs.named.sr & SR_MASK_MD) != 0) 285#define SR_DMY ((saved_state.asregs.cregs.named.sr & SR_MASK_DMY) != 0) 286#define SR_DMX ((saved_state.asregs.cregs.named.sr & SR_MASK_DMX) != 0) 287#define SR_RC ((saved_state.asregs.cregs.named.sr & SR_MASK_RC)) 288 289/* Note: don't use this for privileged bits */ 290#define SET_SR_BIT(EXP, BIT) \ 291do { \ 292 if ((EXP) & 1) \ 293 saved_state.asregs.cregs.named.sr |= (BIT); \ 294 else \ 295 saved_state.asregs.cregs.named.sr &= ~(BIT); \ 296} while (0) 297 298#define SET_SR_BO(EXP) SET_SR_BIT ((EXP), SR_MASK_BO) 299#define SET_SR_CS(EXP) SET_SR_BIT ((EXP), SR_MASK_CS) 300#define SET_BANKN(EXP) \ 301do { \ 302 IBNR = (IBNR & 0xfe00) | (EXP & 0x1f); \ 303} while (0) 304#define SET_ME(EXP) \ 305do { \ 306 IBNR = (IBNR & 0x3fff) | ((EXP & 0x3) << 14); \ 307} while (0) 308#define SET_SR_M(EXP) SET_SR_BIT ((EXP), SR_MASK_M) 309#define SET_SR_Q(EXP) SET_SR_BIT ((EXP), SR_MASK_Q) 310#define SET_SR_S(EXP) SET_SR_BIT ((EXP), SR_MASK_S) 311#define SET_SR_T(EXP) SET_SR_BIT ((EXP), SR_MASK_T) 312#define SET_LDST(EXP) (saved_state.asregs.cregs.named.ldst = ((EXP) != 0)) 313 314/* stc currently relies on being able to read SR without modifications. */ 315#define GET_SR() (saved_state.asregs.cregs.named.sr - 0) 316 317#define SET_SR(x) set_sr (x) 318 319#define SET_RC(x) \ 320 (saved_state.asregs.cregs.named.sr \ 321 = saved_state.asregs.cregs.named.sr & 0xf000ffff | ((x) & 0xfff) << 16) 322 323/* Manipulate FPSCR */ 324 325#define FPSCR_MASK_FR (1 << 21) 326#define FPSCR_MASK_SZ (1 << 20) 327#define FPSCR_MASK_PR (1 << 19) 328 329#define FPSCR_FR ((GET_FPSCR () & FPSCR_MASK_FR) != 0) 330#define FPSCR_SZ ((GET_FPSCR () & FPSCR_MASK_SZ) != 0) 331#define FPSCR_PR ((GET_FPSCR () & FPSCR_MASK_PR) != 0) 332 333/* Count the number of arguments in an argv. */ 334static int 335count_argc (char **argv) 336{ 337 int i; 338 339 if (! argv) 340 return -1; 341 342 for (i = 0; argv[i] != NULL; ++i) 343 continue; 344 return i; 345} 346 347static void 348set_fpscr1 (x) 349 int x; 350{ 351 int old = saved_state.asregs.sregs.named.fpscr; 352 saved_state.asregs.sregs.named.fpscr = (x); 353 /* swap the floating point register banks */ 354 if ((saved_state.asregs.sregs.named.fpscr ^ old) & FPSCR_MASK_FR 355 /* Ignore bit change if simulating sh-dsp. */ 356 && ! target_dsp) 357 { 358 union fregs_u tmpf = saved_state.asregs.fregs[0]; 359 saved_state.asregs.fregs[0] = saved_state.asregs.fregs[1]; 360 saved_state.asregs.fregs[1] = tmpf; 361 } 362} 363 364/* sts relies on being able to read fpscr directly. */ 365#define GET_FPSCR() (saved_state.asregs.sregs.named.fpscr) 366#define SET_FPSCR(x) \ 367do { \ 368 set_fpscr1 (x); \ 369} while (0) 370 371#define DSR (saved_state.asregs.sregs.named.fpscr) 372 373int 374fail () 375{ 376 abort (); 377} 378 379#define RAISE_EXCEPTION(x) \ 380 (saved_state.asregs.exception = x, saved_state.asregs.insn_end = 0) 381 382#define RAISE_EXCEPTION_IF_IN_DELAY_SLOT() \ 383 if (in_delay_slot) RAISE_EXCEPTION (SIGILL) 384 385/* This function exists mainly for the purpose of setting a breakpoint to 386 catch simulated bus errors when running the simulator under GDB. */ 387 388void 389raise_exception (x) 390 int x; 391{ 392 RAISE_EXCEPTION (x); 393} 394 395void 396raise_buserror () 397{ 398 raise_exception (SIGBUS); 399} 400 401#define PROCESS_SPECIAL_ADDRESS(addr, endian, ptr, bits_written, \ 402 forbidden_addr_bits, data, retval) \ 403do { \ 404 if (addr & forbidden_addr_bits) \ 405 { \ 406 raise_buserror (); \ 407 return retval; \ 408 } \ 409 else if ((addr & saved_state.asregs.xyram_select) \ 410 == saved_state.asregs.xram_start) \ 411 ptr = (void *) &saved_state.asregs.xmem_offset[addr ^ endian]; \ 412 else if ((addr & saved_state.asregs.xyram_select) \ 413 == saved_state.asregs.yram_start) \ 414 ptr = (void *) &saved_state.asregs.ymem_offset[addr ^ endian]; \ 415 else if ((unsigned) addr >> 24 == 0xf0 \ 416 && bits_written == 32 && (data & 1) == 0) \ 417 /* This invalidates (if not associative) or might invalidate \ 418 (if associative) an instruction cache line. This is used for \ 419 trampolines. Since we don't simulate the cache, this is a no-op \ 420 as far as the simulator is concerned. */ \ 421 return retval; \ 422 else \ 423 { \ 424 if (bits_written == 8 && addr > 0x5000000) \ 425 IOMEM (addr, 1, data); \ 426 /* We can't do anything useful with the other stuff, so fail. */ \ 427 raise_buserror (); \ 428 return retval; \ 429 } \ 430} while (0) 431 432/* FIXME: sim_resume should be renamed to sim_engine_run. sim_resume 433 being implemented by ../common/sim_resume.c and the below should 434 make a call to sim_engine_halt */ 435 436#define BUSERROR(addr, mask) ((addr) & (mask)) 437 438#define WRITE_BUSERROR(addr, mask, data, addr_func) \ 439 do \ 440 { \ 441 if (addr & mask) \ 442 { \ 443 addr_func (addr, data); \ 444 return; \ 445 } \ 446 } \ 447 while (0) 448 449#define READ_BUSERROR(addr, mask, addr_func) \ 450 do \ 451 { \ 452 if (addr & mask) \ 453 return addr_func (addr); \ 454 } \ 455 while (0) 456 457/* Define this to enable register lifetime checking. 458 The compiler generates "add #0,rn" insns to mark registers as invalid, 459 the simulator uses this info to call fail if it finds a ref to an invalid 460 register before a def 461 462 #define PARANOID 463*/ 464 465#ifdef PARANOID 466int valid[16]; 467#define CREF(x) if (!valid[x]) fail (); 468#define CDEF(x) valid[x] = 1; 469#define UNDEF(x) valid[x] = 0; 470#else 471#define CREF(x) 472#define CDEF(x) 473#define UNDEF(x) 474#endif 475 476static void parse_and_set_memory_size PARAMS ((char *str)); 477static int IOMEM PARAMS ((int addr, int write, int value)); 478static struct loop_bounds get_loop_bounds PARAMS ((int, int, unsigned char *, 479 unsigned char *, int, int)); 480static void process_wlat_addr PARAMS ((int, int)); 481static void process_wwat_addr PARAMS ((int, int)); 482static void process_wbat_addr PARAMS ((int, int)); 483static int process_rlat_addr PARAMS ((int)); 484static int process_rwat_addr PARAMS ((int)); 485static int process_rbat_addr PARAMS ((int)); 486static void INLINE wlat_fast PARAMS ((unsigned char *, int, int, int)); 487static void INLINE wwat_fast PARAMS ((unsigned char *, int, int, int, int)); 488static void INLINE wbat_fast PARAMS ((unsigned char *, int, int, int)); 489static int INLINE rlat_fast PARAMS ((unsigned char *, int, int)); 490static int INLINE rwat_fast PARAMS ((unsigned char *, int, int, int)); 491static int INLINE rbat_fast PARAMS ((unsigned char *, int, int)); 492 493static host_callback *callback; 494 495 496 497/* Floating point registers */ 498 499#define DR(n) (get_dr (n)) 500static double 501get_dr (n) 502 int n; 503{ 504 n = (n & ~1); 505 if (host_little_endian) 506 { 507 union 508 { 509 int i[2]; 510 double d; 511 } dr; 512 dr.i[1] = saved_state.asregs.fregs[0].i[n + 0]; 513 dr.i[0] = saved_state.asregs.fregs[0].i[n + 1]; 514 return dr.d; 515 } 516 else 517 return (saved_state.asregs.fregs[0].d[n >> 1]); 518} 519 520#define SET_DR(n, EXP) set_dr ((n), (EXP)) 521static void 522set_dr (n, exp) 523 int n; 524 double exp; 525{ 526 n = (n & ~1); 527 if (host_little_endian) 528 { 529 union 530 { 531 int i[2]; 532 double d; 533 } dr; 534 dr.d = exp; 535 saved_state.asregs.fregs[0].i[n + 0] = dr.i[1]; 536 saved_state.asregs.fregs[0].i[n + 1] = dr.i[0]; 537 } 538 else 539 saved_state.asregs.fregs[0].d[n >> 1] = exp; 540} 541 542#define SET_FI(n,EXP) (saved_state.asregs.fregs[0].i[(n)] = (EXP)) 543#define FI(n) (saved_state.asregs.fregs[0].i[(n)]) 544 545#define FR(n) (saved_state.asregs.fregs[0].f[(n)]) 546#define SET_FR(n,EXP) (saved_state.asregs.fregs[0].f[(n)] = (EXP)) 547 548#define XD_TO_XF(n) ((((n) & 1) << 5) | ((n) & 0x1e)) 549#define XF(n) (saved_state.asregs.fregs[(n) >> 5].i[(n) & 0x1f]) 550#define SET_XF(n,EXP) (saved_state.asregs.fregs[(n) >> 5].i[(n) & 0x1f] = (EXP)) 551 552#define RS saved_state.asregs.cregs.named.rs 553#define RE saved_state.asregs.cregs.named.re 554#define MOD (saved_state.asregs.cregs.named.mod) 555#define SET_MOD(i) \ 556(MOD = (i), \ 557 MOD_ME = (unsigned) MOD >> 16 | (SR_DMY ? ~0xffff : (SR_DMX ? 0 : 0x10000)), \ 558 MOD_DELTA = (MOD & 0xffff) - ((unsigned) MOD >> 16)) 559 560#define DSP_R(n) saved_state.asregs.sregs.i[(n)] 561#define DSP_GRD(n) DSP_R ((n) + 8) 562#define GET_DSP_GRD(n) ((n | 2) == 7 ? SEXT (DSP_GRD (n)) : SIGN32 (DSP_R (n))) 563#define A1 DSP_R (5) 564#define A0 DSP_R (7) 565#define X0 DSP_R (8) 566#define X1 DSP_R (9) 567#define Y0 DSP_R (10) 568#define Y1 DSP_R (11) 569#define M0 DSP_R (12) 570#define A1G DSP_R (13) 571#define M1 DSP_R (14) 572#define A0G DSP_R (15) 573/* DSP_R (16) / DSP_GRD (16) are used as a fake destination for pcmp. */ 574#define MOD_ME DSP_GRD (17) 575#define MOD_DELTA DSP_GRD (18) 576 577#define FP_OP(n, OP, m) \ 578{ \ 579 if (FPSCR_PR) \ 580 { \ 581 if (((n) & 1) || ((m) & 1)) \ 582 RAISE_EXCEPTION (SIGILL); \ 583 else \ 584 SET_DR (n, (DR (n) OP DR (m))); \ 585 } \ 586 else \ 587 SET_FR (n, (FR (n) OP FR (m))); \ 588} while (0) 589 590#define FP_UNARY(n, OP) \ 591{ \ 592 if (FPSCR_PR) \ 593 { \ 594 if ((n) & 1) \ 595 RAISE_EXCEPTION (SIGILL); \ 596 else \ 597 SET_DR (n, (OP (DR (n)))); \ 598 } \ 599 else \ 600 SET_FR (n, (OP (FR (n)))); \ 601} while (0) 602 603#define FP_CMP(n, OP, m) \ 604{ \ 605 if (FPSCR_PR) \ 606 { \ 607 if (((n) & 1) || ((m) & 1)) \ 608 RAISE_EXCEPTION (SIGILL); \ 609 else \ 610 SET_SR_T (DR (n) OP DR (m)); \ 611 } \ 612 else \ 613 SET_SR_T (FR (n) OP FR (m)); \ 614} while (0) 615 616static void 617set_sr (new_sr) 618 int new_sr; 619{ 620 /* do we need to swap banks */ 621 int old_gpr = SR_MD && SR_RB; 622 int new_gpr = (new_sr & SR_MASK_MD) && (new_sr & SR_MASK_RB); 623 if (old_gpr != new_gpr) 624 { 625 int i, tmp; 626 for (i = 0; i < 8; i++) 627 { 628 tmp = saved_state.asregs.cregs.named.bank[i]; 629 saved_state.asregs.cregs.named.bank[i] = saved_state.asregs.regs[i]; 630 saved_state.asregs.regs[i] = tmp; 631 } 632 } 633 saved_state.asregs.cregs.named.sr = new_sr; 634 SET_MOD (MOD); 635} 636 637static void INLINE 638wlat_fast (memory, x, value, maskl) 639 unsigned char *memory; 640{ 641 int v = value; 642 unsigned int *p = (unsigned int *) (memory + x); 643 WRITE_BUSERROR (x, maskl, v, process_wlat_addr); 644 *p = v; 645} 646 647static void INLINE 648wwat_fast (memory, x, value, maskw, endianw) 649 unsigned char *memory; 650{ 651 int v = value; 652 unsigned short *p = (unsigned short *) (memory + (x ^ endianw)); 653 WRITE_BUSERROR (x, maskw, v, process_wwat_addr); 654 *p = v; 655} 656 657static void INLINE 658wbat_fast (memory, x, value, maskb) 659 unsigned char *memory; 660{ 661 unsigned char *p = memory + (x ^ endianb); 662 WRITE_BUSERROR (x, maskb, value, process_wbat_addr); 663 664 p[0] = value; 665} 666 667/* Read functions */ 668 669static int INLINE 670rlat_fast (memory, x, maskl) 671 unsigned char *memory; 672{ 673 unsigned int *p = (unsigned int *) (memory + x); 674 READ_BUSERROR (x, maskl, process_rlat_addr); 675 676 return *p; 677} 678 679static int INLINE 680rwat_fast (memory, x, maskw, endianw) 681 unsigned char *memory; 682 int x, maskw, endianw; 683{ 684 unsigned short *p = (unsigned short *) (memory + (x ^ endianw)); 685 READ_BUSERROR (x, maskw, process_rwat_addr); 686 687 return *p; 688} 689 690static int INLINE 691riat_fast (insn_ptr, endianw) 692 unsigned char *insn_ptr; 693{ 694 unsigned short *p = (unsigned short *) ((size_t) insn_ptr ^ endianw); 695 696 return *p; 697} 698 699static int INLINE 700rbat_fast (memory, x, maskb) 701 unsigned char *memory; 702{ 703 unsigned char *p = memory + (x ^ endianb); 704 READ_BUSERROR (x, maskb, process_rbat_addr); 705 706 return *p; 707} 708 709#define RWAT(x) (rwat_fast (memory, x, maskw, endianw)) 710#define RLAT(x) (rlat_fast (memory, x, maskl)) 711#define RBAT(x) (rbat_fast (memory, x, maskb)) 712#define RIAT(p) (riat_fast ((p), endianw)) 713#define WWAT(x,v) (wwat_fast (memory, x, v, maskw, endianw)) 714#define WLAT(x,v) (wlat_fast (memory, x, v, maskl)) 715#define WBAT(x,v) (wbat_fast (memory, x, v, maskb)) 716 717#define RUWAT(x) (RWAT (x) & 0xffff) 718#define RSWAT(x) ((short) (RWAT (x))) 719#define RSLAT(x) ((long) (RLAT (x))) 720#define RSBAT(x) (SEXT (RBAT (x))) 721 722#define RDAT(x, n) (do_rdat (memory, (x), (n), (maskl))) 723static int 724do_rdat (memory, x, n, maskl) 725 char *memory; 726 int x; 727 int n; 728 int maskl; 729{ 730 int f0; 731 int f1; 732 int i = (n & 1); 733 int j = (n & ~1); 734 f0 = rlat_fast (memory, x + 0, maskl); 735 f1 = rlat_fast (memory, x + 4, maskl); 736 saved_state.asregs.fregs[i].i[(j + 0)] = f0; 737 saved_state.asregs.fregs[i].i[(j + 1)] = f1; 738 return 0; 739} 740 741#define WDAT(x, n) (do_wdat (memory, (x), (n), (maskl))) 742static int 743do_wdat (memory, x, n, maskl) 744 char *memory; 745 int x; 746 int n; 747 int maskl; 748{ 749 int f0; 750 int f1; 751 int i = (n & 1); 752 int j = (n & ~1); 753 f0 = saved_state.asregs.fregs[i].i[(j + 0)]; 754 f1 = saved_state.asregs.fregs[i].i[(j + 1)]; 755 wlat_fast (memory, (x + 0), f0, maskl); 756 wlat_fast (memory, (x + 4), f1, maskl); 757 return 0; 758} 759 760static void 761process_wlat_addr (addr, value) 762 int addr; 763 int value; 764{ 765 unsigned int *ptr; 766 767 PROCESS_SPECIAL_ADDRESS (addr, endianb, ptr, 32, 3, value, ); 768 *ptr = value; 769} 770 771static void 772process_wwat_addr (addr, value) 773 int addr; 774 int value; 775{ 776 unsigned short *ptr; 777 778 PROCESS_SPECIAL_ADDRESS (addr, endianb, ptr, 16, 1, value, ); 779 *ptr = value; 780} 781 782static void 783process_wbat_addr (addr, value) 784 int addr; 785 int value; 786{ 787 unsigned char *ptr; 788 789 PROCESS_SPECIAL_ADDRESS (addr, endianb, ptr, 8, 0, value, ); 790 *ptr = value; 791} 792 793static int 794process_rlat_addr (addr) 795 int addr; 796{ 797 unsigned char *ptr; 798 799 PROCESS_SPECIAL_ADDRESS (addr, endianb, ptr, -32, 3, -1, 0); 800 return *ptr; 801} 802 803static int 804process_rwat_addr (addr) 805 int addr; 806{ 807 unsigned char *ptr; 808 809 PROCESS_SPECIAL_ADDRESS (addr, endianb, ptr, -16, 1, -1, 0); 810 return *ptr; 811} 812 813static int 814process_rbat_addr (addr) 815 int addr; 816{ 817 unsigned char *ptr; 818 819 PROCESS_SPECIAL_ADDRESS (addr, endianb, ptr, -8, 0, -1, 0); 820 return *ptr; 821} 822 823#define SEXT(x) (((x & 0xff) ^ (~0x7f))+0x80) 824#define SEXT12(x) (((x & 0xfff) ^ 0x800) - 0x800) 825#define SEXTW(y) ((int) ((short) y)) 826#if 0 827#define SEXT32(x) ((int) ((x & 0xffffffff) ^ 0x80000000U) - 0x7fffffff - 1) 828#else 829#define SEXT32(x) ((int) (x)) 830#endif 831#define SIGN32(x) (SEXT32 (x) >> 31) 832 833/* convert pointer from target to host value. */ 834#define PT2H(x) ((x) + memory) 835/* convert pointer from host to target value. */ 836#define PH2T(x) ((x) - memory) 837 838#define SKIP_INSN(p) ((p) += ((RIAT (p) & 0xfc00) == 0xf800 ? 4 : 2)) 839 840#define SET_NIP(x) nip = (x); CHECK_INSN_PTR (nip); 841 842static int in_delay_slot = 0; 843#define Delay_Slot(TEMPPC) iword = RIAT (TEMPPC); in_delay_slot = 1; goto top; 844 845#define CHECK_INSN_PTR(p) \ 846do { \ 847 if (saved_state.asregs.exception || PH2T (p) & maskw) \ 848 saved_state.asregs.insn_end = 0; \ 849 else if (p < loop.end) \ 850 saved_state.asregs.insn_end = loop.end; \ 851 else \ 852 saved_state.asregs.insn_end = mem_end; \ 853} while (0) 854 855#ifdef ACE_FAST 856 857#define MA(n) 858#define L(x) 859#define TL(x) 860#define TB(x) 861 862#else 863 864#define MA(n) \ 865 do { memstalls += ((((int) PC & 3) != 0) ? (n) : ((n) - 1)); } while (0) 866 867#define L(x) thislock = x; 868#define TL(x) if ((x) == prevlock) stalls++; 869#define TB(x,y) if ((x) == prevlock || (y) == prevlock) stalls++; 870 871#endif 872 873#if defined(__GO32__) 874int sim_memory_size = 19; 875#else 876int sim_memory_size = 24; 877#endif 878 879static int sim_profile_size = 17; 880static int nsamples; 881 882#undef TB 883#define TB(x,y) 884 885#define SMR1 (0x05FFFEC8) /* Channel 1 serial mode register */ 886#define BRR1 (0x05FFFEC9) /* Channel 1 bit rate register */ 887#define SCR1 (0x05FFFECA) /* Channel 1 serial control register */ 888#define TDR1 (0x05FFFECB) /* Channel 1 transmit data register */ 889#define SSR1 (0x05FFFECC) /* Channel 1 serial status register */ 890#define RDR1 (0x05FFFECD) /* Channel 1 receive data register */ 891 892#define SCI_RDRF 0x40 /* Recieve data register full */ 893#define SCI_TDRE 0x80 /* Transmit data register empty */ 894 895static int 896IOMEM (addr, write, value) 897 int addr; 898 int write; 899 int value; 900{ 901 if (write) 902 { 903 switch (addr) 904 { 905 case TDR1: 906 if (value != '\r') 907 { 908 putchar (value); 909 fflush (stdout); 910 } 911 break; 912 } 913 } 914 else 915 { 916 switch (addr) 917 { 918 case RDR1: 919 return getchar (); 920 } 921 } 922 return 0; 923} 924 925static int 926get_now () 927{ 928 return time ((long *) 0); 929} 930 931static int 932now_persec () 933{ 934 return 1; 935} 936 937static FILE *profile_file; 938 939static unsigned INLINE 940swap (n) 941 unsigned n; 942{ 943 if (endianb) 944 n = (n << 24 | (n & 0xff00) << 8 945 | (n & 0xff0000) >> 8 | (n & 0xff000000) >> 24); 946 return n; 947} 948 949static unsigned short INLINE 950swap16 (n) 951 unsigned short n; 952{ 953 if (endianb) 954 n = n << 8 | (n & 0xff00) >> 8; 955 return n; 956} 957 958static void 959swapout (n) 960 int n; 961{ 962 if (profile_file) 963 { 964 union { char b[4]; int n; } u; 965 u.n = swap (n); 966 fwrite (u.b, 4, 1, profile_file); 967 } 968} 969 970static void 971swapout16 (n) 972 int n; 973{ 974 union { char b[4]; int n; } u; 975 u.n = swap16 (n); 976 fwrite (u.b, 2, 1, profile_file); 977} 978 979/* Turn a pointer in a register into a pointer into real memory. */ 980 981static char * 982ptr (x) 983 int x; 984{ 985 return (char *) (x + saved_state.asregs.memory); 986} 987 988/* STR points to a zero-terminated string in target byte order. Return 989 the number of bytes that need to be converted to host byte order in order 990 to use this string as a zero-terminated string on the host. 991 (Not counting the rounding up needed to operate on entire words.) */ 992static int 993strswaplen (str) 994 int str; 995{ 996 unsigned char *memory = saved_state.asregs.memory; 997 int start, end; 998 int endian = endianb; 999 1000 if (! endian) 1001 return 0; 1002 end = str; 1003 for (end = str; memory[end ^ endian]; end++) ; 1004 return end - str + 1; 1005} 1006 1007static void 1008strnswap (str, len) 1009 int str; 1010 int len; 1011{ 1012 int *start, *end; 1013 1014 if (! endianb || ! len) 1015 return; 1016 start = (int *) ptr (str & ~3); 1017 end = (int *) ptr (str + len); 1018 do 1019 { 1020 int old = *start; 1021 *start = (old << 24 | (old & 0xff00) << 8 1022 | (old & 0xff0000) >> 8 | (old & 0xff000000) >> 24); 1023 start++; 1024 } 1025 while (start < end); 1026} 1027 1028/* Simulate a monitor trap, put the result into r0 and errno into r1 1029 return offset by which to adjust pc. */ 1030 1031static int 1032trap (i, regs, insn_ptr, memory, maskl, maskw, endianw) 1033 int i; 1034 int *regs; 1035 unsigned char *insn_ptr; 1036 unsigned char *memory; 1037{ 1038 switch (i) 1039 { 1040 case 1: 1041 printf ("%c", regs[0]); 1042 break; 1043 case 2: 1044 raise_exception (SIGQUIT); 1045 break; 1046 case 3: /* FIXME: for backwards compat, should be removed */ 1047 case 33: 1048 { 1049 unsigned int countp = * (unsigned int *) (insn_ptr + 4); 1050 1051 WLAT (countp, RLAT (countp) + 1); 1052 return 6; 1053 } 1054 case 34: 1055 { 1056 extern int errno; 1057 int perrno = errno; 1058 errno = 0; 1059 1060 switch (regs[4]) 1061 { 1062 1063#if !defined(__GO32__) && !defined(_WIN32) 1064 case SYS_fork: 1065 regs[0] = fork (); 1066 break; 1067/* This would work only if endianness matched between host and target. 1068 Besides, it's quite dangerous. */ 1069#if 0 1070 case SYS_execve: 1071 regs[0] = execve (ptr (regs[5]), (char **) ptr (regs[6]), 1072 (char **) ptr (regs[7])); 1073 break; 1074 case SYS_execv: 1075 regs[0] = execve (ptr (regs[5]), (char **) ptr (regs[6]), 0); 1076 break; 1077#endif 1078 case SYS_pipe: 1079 { 1080 regs[0] = (BUSERROR (regs[5], maskl) 1081 ? -EINVAL 1082 : pipe ((int *) ptr (regs[5]))); 1083 } 1084 break; 1085 1086 case SYS_wait: 1087 regs[0] = wait (ptr (regs[5])); 1088 break; 1089#endif /* !defined(__GO32__) && !defined(_WIN32) */ 1090 1091 case SYS_read: 1092 strnswap (regs[6], regs[7]); 1093 regs[0] 1094 = callback->read (callback, regs[5], ptr (regs[6]), regs[7]); 1095 strnswap (regs[6], regs[7]); 1096 break; 1097 case SYS_write: 1098 strnswap (regs[6], regs[7]); 1099 if (regs[5] == 1) 1100 regs[0] = (int) callback->write_stdout (callback, 1101 ptr (regs[6]), regs[7]); 1102 else 1103 regs[0] = (int) callback->write (callback, regs[5], 1104 ptr (regs[6]), regs[7]); 1105 strnswap (regs[6], regs[7]); 1106 break; 1107 case SYS_lseek: 1108 regs[0] = callback->lseek (callback,regs[5], regs[6], regs[7]); 1109 break; 1110 case SYS_close: 1111 regs[0] = callback->close (callback,regs[5]); 1112 break; 1113 case SYS_open: 1114 { 1115 int len = strswaplen (regs[5]); 1116 strnswap (regs[5], len); 1117 regs[0] = callback->open (callback, ptr (regs[5]), regs[6]); 1118 strnswap (regs[5], len); 1119 break; 1120 } 1121 case SYS_exit: 1122 /* EXIT - caller can look in r5 to work out the reason */ 1123 raise_exception (SIGQUIT); 1124 regs[0] = regs[5]; 1125 break; 1126 1127 case SYS_stat: /* added at hmsi */ 1128 /* stat system call */ 1129 { 1130 struct stat host_stat; 1131 int buf; 1132 int len = strswaplen (regs[5]); 1133 1134 strnswap (regs[5], len); 1135 regs[0] = stat (ptr (regs[5]), &host_stat); 1136 strnswap (regs[5], len); 1137 1138 buf = regs[6]; 1139 1140 WWAT (buf, host_stat.st_dev); 1141 buf += 2; 1142 WWAT (buf, host_stat.st_ino); 1143 buf += 2; 1144 WLAT (buf, host_stat.st_mode); 1145 buf += 4; 1146 WWAT (buf, host_stat.st_nlink); 1147 buf += 2; 1148 WWAT (buf, host_stat.st_uid); 1149 buf += 2; 1150 WWAT (buf, host_stat.st_gid); 1151 buf += 2; 1152 WWAT (buf, host_stat.st_rdev); 1153 buf += 2; 1154 WLAT (buf, host_stat.st_size); 1155 buf += 4; 1156 WLAT (buf, host_stat.st_atime); 1157 buf += 4; 1158 WLAT (buf, 0); 1159 buf += 4; 1160 WLAT (buf, host_stat.st_mtime); 1161 buf += 4; 1162 WLAT (buf, 0); 1163 buf += 4; 1164 WLAT (buf, host_stat.st_ctime); 1165 buf += 4; 1166 WLAT (buf, 0); 1167 buf += 4; 1168 WLAT (buf, 0); 1169 buf += 4; 1170 WLAT (buf, 0); 1171 buf += 4; 1172 } 1173 break; 1174 1175#ifndef _WIN32 1176 case SYS_chown: 1177 { 1178 int len = strswaplen (regs[5]); 1179 1180 strnswap (regs[5], len); 1181 regs[0] = chown (ptr (regs[5]), regs[6], regs[7]); 1182 strnswap (regs[5], len); 1183 break; 1184 } 1185#endif /* _WIN32 */ 1186 case SYS_chmod: 1187 { 1188 int len = strswaplen (regs[5]); 1189 1190 strnswap (regs[5], len); 1191 regs[0] = chmod (ptr (regs[5]), regs[6]); 1192 strnswap (regs[5], len); 1193 break; 1194 } 1195 case SYS_utime: 1196 { 1197 /* Cast the second argument to void *, to avoid type mismatch 1198 if a prototype is present. */ 1199 int len = strswaplen (regs[5]); 1200 1201 strnswap (regs[5], len); 1202 regs[0] = utime (ptr (regs[5]), (void *) ptr (regs[6])); 1203 strnswap (regs[5], len); 1204 break; 1205 } 1206 case SYS_argc: 1207 regs[0] = count_argc (prog_argv); 1208 break; 1209 case SYS_argnlen: 1210 if (regs[5] < count_argc (prog_argv)) 1211 regs[0] = strlen (prog_argv[regs[5]]); 1212 else 1213 regs[0] = -1; 1214 break; 1215 case SYS_argn: 1216 if (regs[5] < count_argc (prog_argv)) 1217 { 1218 /* Include the termination byte. */ 1219 int i = strlen (prog_argv[regs[5]]) + 1; 1220 regs[0] = sim_write (0, regs[6], prog_argv[regs[5]], i); 1221 } 1222 else 1223 regs[0] = -1; 1224 break; 1225 case SYS_time: 1226 regs[0] = get_now (); 1227 break; 1228 case SYS_ftruncate: 1229 regs[0] = callback->ftruncate (callback, regs[5], regs[6]); 1230 break; 1231 case SYS_truncate: 1232 { 1233 int len = strswaplen (regs[5]); 1234 strnswap (regs[5], len); 1235 regs[0] = callback->truncate (callback, ptr (regs[5]), regs[6]); 1236 strnswap (regs[5], len); 1237 break; 1238 } 1239 default: 1240 regs[0] = -1; 1241 break; 1242 } 1243 regs[1] = callback->get_errno (callback); 1244 errno = perrno; 1245 } 1246 break; 1247 1248 case 13: /* Set IBNR */ 1249 IBNR = regs[0] & 0xffff; 1250 break; 1251 case 14: /* Set IBCR */ 1252 IBCR = regs[0] & 0xffff; 1253 break; 1254 case 0xc3: 1255 case 255: 1256 raise_exception (SIGTRAP); 1257 if (i == 0xc3) 1258 return -2; 1259 break; 1260 } 1261 return 0; 1262} 1263 1264void 1265control_c (sig, code, scp, addr) 1266 int sig; 1267 int code; 1268 char *scp; 1269 char *addr; 1270{ 1271 raise_exception (SIGINT); 1272} 1273 1274static int 1275div1 (R, iRn2, iRn1/*, T*/) 1276 int *R; 1277 int iRn1; 1278 int iRn2; 1279 /* int T;*/ 1280{ 1281 unsigned long tmp0; 1282 unsigned char old_q, tmp1; 1283 1284 old_q = Q; 1285 SET_SR_Q ((unsigned char) ((0x80000000 & R[iRn1]) != 0)); 1286 R[iRn1] <<= 1; 1287 R[iRn1] |= (unsigned long) T; 1288 1289 switch (old_q) 1290 { 1291 case 0: 1292 switch (M) 1293 { 1294 case 0: 1295 tmp0 = R[iRn1]; 1296 R[iRn1] -= R[iRn2]; 1297 tmp1 = (R[iRn1] > tmp0); 1298 switch (Q) 1299 { 1300 case 0: 1301 SET_SR_Q (tmp1); 1302 break; 1303 case 1: 1304 SET_SR_Q ((unsigned char) (tmp1 == 0)); 1305 break; 1306 } 1307 break; 1308 case 1: 1309 tmp0 = R[iRn1]; 1310 R[iRn1] += R[iRn2]; 1311 tmp1 = (R[iRn1] < tmp0); 1312 switch (Q) 1313 { 1314 case 0: 1315 SET_SR_Q ((unsigned char) (tmp1 == 0)); 1316 break; 1317 case 1: 1318 SET_SR_Q (tmp1); 1319 break; 1320 } 1321 break; 1322 } 1323 break; 1324 case 1: 1325 switch (M) 1326 { 1327 case 0: 1328 tmp0 = R[iRn1]; 1329 R[iRn1] += R[iRn2]; 1330 tmp1 = (R[iRn1] < tmp0); 1331 switch (Q) 1332 { 1333 case 0: 1334 SET_SR_Q (tmp1); 1335 break; 1336 case 1: 1337 SET_SR_Q ((unsigned char) (tmp1 == 0)); 1338 break; 1339 } 1340 break; 1341 case 1: 1342 tmp0 = R[iRn1]; 1343 R[iRn1] -= R[iRn2]; 1344 tmp1 = (R[iRn1] > tmp0); 1345 switch (Q) 1346 { 1347 case 0: 1348 SET_SR_Q ((unsigned char) (tmp1 == 0)); 1349 break; 1350 case 1: 1351 SET_SR_Q (tmp1); 1352 break; 1353 } 1354 break; 1355 } 1356 break; 1357 } 1358 /*T = (Q == M);*/ 1359 SET_SR_T (Q == M); 1360 /*return T;*/ 1361} 1362 1363static void 1364dmul (sign, rm, rn) 1365 int sign; 1366 unsigned int rm; 1367 unsigned int rn; 1368{ 1369 unsigned long RnL, RnH; 1370 unsigned long RmL, RmH; 1371 unsigned long temp0, temp1, temp2, temp3; 1372 unsigned long Res2, Res1, Res0; 1373 1374 RnL = rn & 0xffff; 1375 RnH = (rn >> 16) & 0xffff; 1376 RmL = rm & 0xffff; 1377 RmH = (rm >> 16) & 0xffff; 1378 temp0 = RmL * RnL; 1379 temp1 = RmH * RnL; 1380 temp2 = RmL * RnH; 1381 temp3 = RmH * RnH; 1382 Res2 = 0; 1383 Res1 = temp1 + temp2; 1384 if (Res1 < temp1) 1385 Res2 += 0x00010000; 1386 temp1 = (Res1 << 16) & 0xffff0000; 1387 Res0 = temp0 + temp1; 1388 if (Res0 < temp0) 1389 Res2 += 1; 1390 Res2 += ((Res1 >> 16) & 0xffff) + temp3; 1391 1392 if (sign) 1393 { 1394 if (rn & 0x80000000) 1395 Res2 -= rm; 1396 if (rm & 0x80000000) 1397 Res2 -= rn; 1398 } 1399 1400 MACH = Res2; 1401 MACL = Res0; 1402} 1403 1404static void 1405macw (regs, memory, n, m, endianw) 1406 int *regs; 1407 unsigned char *memory; 1408 int m, n; 1409 int endianw; 1410{ 1411 long tempm, tempn; 1412 long prod, macl, sum; 1413 1414 tempm=RSWAT (regs[m]); regs[m]+=2; 1415 tempn=RSWAT (regs[n]); regs[n]+=2; 1416 1417 macl = MACL; 1418 prod = (long) (short) tempm * (long) (short) tempn; 1419 sum = prod + macl; 1420 if (S) 1421 { 1422 if ((~(prod ^ macl) & (sum ^ prod)) < 0) 1423 { 1424 /* MACH's lsb is a sticky overflow bit. */ 1425 MACH |= 1; 1426 /* Store the smallest negative number in MACL if prod is 1427 negative, and the largest positive number otherwise. */ 1428 sum = 0x7fffffff + (prod < 0); 1429 } 1430 } 1431 else 1432 { 1433 long mach; 1434 /* Add to MACH the sign extended product, and carry from low sum. */ 1435 mach = MACH + (-(prod < 0)) + ((unsigned long) sum < prod); 1436 /* Sign extend at 10:th bit in MACH. */ 1437 MACH = (mach & 0x1ff) | -(mach & 0x200); 1438 } 1439 MACL = sum; 1440} 1441 1442static void 1443macl (regs, memory, n, m) 1444 int *regs; 1445 unsigned char *memory; 1446 int m, n; 1447{ 1448 long tempm, tempn; 1449 long macl, mach; 1450 long long ans; 1451 long long mac64; 1452 1453 tempm = RSLAT (regs[m]); 1454 regs[m] += 4; 1455 1456 tempn = RSLAT (regs[n]); 1457 regs[n] += 4; 1458 1459 mach = MACH; 1460 macl = MACL; 1461 1462 mac64 = ((long long) macl & 0xffffffff) | 1463 ((long long) mach & 0xffffffff) << 32; 1464 1465 ans = (long long) tempm * (long long) tempn; /* Multiply 32bit * 32bit */ 1466 1467 mac64 += ans; /* Accumulate 64bit + 64 bit */ 1468 1469 macl = (long) (mac64 & 0xffffffff); 1470 mach = (long) ((mac64 >> 32) & 0xffffffff); 1471 1472 if (S) /* Store only 48 bits of the result */ 1473 { 1474 if (mach < 0) /* Result is negative */ 1475 { 1476 mach = mach & 0x0000ffff; /* Mask higher 16 bits */ 1477 mach |= 0xffff8000; /* Sign extend higher 16 bits */ 1478 } 1479 else 1480 mach = mach & 0x00007fff; /* Postive Result */ 1481 } 1482 1483 MACL = macl; 1484 MACH = mach; 1485} 1486 1487enum { 1488 B_BCLR = 0, 1489 B_BSET = 1, 1490 B_BST = 2, 1491 B_BLD = 3, 1492 B_BAND = 4, 1493 B_BOR = 5, 1494 B_BXOR = 6, 1495 B_BLDNOT = 11, 1496 B_BANDNOT = 12, 1497 B_BORNOT = 13, 1498 1499 MOVB_RM = 0x0000, 1500 MOVW_RM = 0x1000, 1501 MOVL_RM = 0x2000, 1502 FMOV_RM = 0x3000, 1503 MOVB_MR = 0x4000, 1504 MOVW_MR = 0x5000, 1505 MOVL_MR = 0x6000, 1506 FMOV_MR = 0x7000, 1507 MOVU_BMR = 0x8000, 1508 MOVU_WMR = 0x9000, 1509}; 1510 1511/* Do extended displacement move instructions. */ 1512void 1513do_long_move_insn (int op, int disp12, int m, int n, int *thatlock) 1514{ 1515 int memstalls = 0; 1516 int thislock = *thatlock; 1517 int endianw = global_endianw; 1518 int *R = &(saved_state.asregs.regs[0]); 1519 unsigned char *memory = saved_state.asregs.memory; 1520 int maskb = ~((saved_state.asregs.msize - 1) & ~0); 1521 unsigned char *insn_ptr = PT2H (saved_state.asregs.pc); 1522 1523 switch (op) { 1524 case MOVB_RM: /* signed */ 1525 WBAT (disp12 * 1 + R[n], R[m]); 1526 break; 1527 case MOVW_RM: 1528 WWAT (disp12 * 2 + R[n], R[m]); 1529 break; 1530 case MOVL_RM: 1531 WLAT (disp12 * 4 + R[n], R[m]); 1532 break; 1533 case FMOV_RM: /* floating point */ 1534 if (FPSCR_SZ) 1535 { 1536 MA (1); 1537 WDAT (R[n] + 8 * disp12, m); 1538 } 1539 else 1540 WLAT (R[n] + 4 * disp12, FI (m)); 1541 break; 1542 case MOVB_MR: 1543 R[n] = RSBAT (disp12 * 1 + R[m]); 1544 L (n); 1545 break; 1546 case MOVW_MR: 1547 R[n] = RSWAT (disp12 * 2 + R[m]); 1548 L (n); 1549 break; 1550 case MOVL_MR: 1551 R[n] = RLAT (disp12 * 4 + R[m]); 1552 L (n); 1553 break; 1554 case FMOV_MR: 1555 if (FPSCR_SZ) { 1556 MA (1); 1557 RDAT (R[m] + 8 * disp12, n); 1558 } 1559 else 1560 SET_FI (n, RLAT (R[m] + 4 * disp12)); 1561 break; 1562 case MOVU_BMR: /* unsigned */ 1563 R[n] = RBAT (disp12 * 1 + R[m]); 1564 L (n); 1565 break; 1566 case MOVU_WMR: 1567 R[n] = RWAT (disp12 * 2 + R[m]); 1568 L (n); 1569 break; 1570 default: 1571 RAISE_EXCEPTION (SIGINT); 1572 exit (1); 1573 } 1574 saved_state.asregs.memstalls += memstalls; 1575 *thatlock = thislock; 1576} 1577 1578/* Do binary logical bit-manipulation insns. */ 1579void 1580do_blog_insn (int imm, int addr, int binop, 1581 unsigned char *memory, int maskb) 1582{ 1583 int oldval = RBAT (addr); 1584 1585 switch (binop) { 1586 case B_BCLR: /* bclr.b */ 1587 WBAT (addr, oldval & ~imm); 1588 break; 1589 case B_BSET: /* bset.b */ 1590 WBAT (addr, oldval | imm); 1591 break; 1592 case B_BST: /* bst.b */ 1593 if (T) 1594 WBAT (addr, oldval | imm); 1595 else 1596 WBAT (addr, oldval & ~imm); 1597 break; 1598 case B_BLD: /* bld.b */ 1599 SET_SR_T ((oldval & imm) != 0); 1600 break; 1601 case B_BAND: /* band.b */ 1602 SET_SR_T (T && ((oldval & imm) != 0)); 1603 break; 1604 case B_BOR: /* bor.b */ 1605 SET_SR_T (T || ((oldval & imm) != 0)); 1606 break; 1607 case B_BXOR: /* bxor.b */ 1608 SET_SR_T (T ^ ((oldval & imm) != 0)); 1609 break; 1610 case B_BLDNOT: /* bldnot.b */ 1611 SET_SR_T ((oldval & imm) == 0); 1612 break; 1613 case B_BANDNOT: /* bandnot.b */ 1614 SET_SR_T (T && ((oldval & imm) == 0)); 1615 break; 1616 case B_BORNOT: /* bornot.b */ 1617 SET_SR_T (T || ((oldval & imm) == 0)); 1618 break; 1619 } 1620} 1621float 1622fsca_s (int in, double (*f) (double)) 1623{ 1624 double rad = ldexp ((in & 0xffff), -15) * 3.141592653589793238462643383; 1625 double result = (*f) (rad); 1626 double error, upper, lower, frac; 1627 int exp; 1628 1629 /* Search the value with the maximum error that is still within the 1630 architectural spec. */ 1631 error = ldexp (1., -21); 1632 /* compensate for calculation inaccuracy by reducing error. */ 1633 error = error - ldexp (1., -50); 1634 upper = result + error; 1635 frac = frexp (upper, &exp); 1636 upper = ldexp (floor (ldexp (frac, 24)), exp - 24); 1637 lower = result - error; 1638 frac = frexp (lower, &exp); 1639 lower = ldexp (ceil (ldexp (frac, 24)), exp - 24); 1640 return abs (upper - result) >= abs (lower - result) ? upper : lower; 1641} 1642 1643float 1644fsrra_s (float in) 1645{ 1646 double result = 1. / sqrt (in); 1647 int exp; 1648 double frac, upper, lower, error, eps; 1649 1650 /* refine result */ 1651 result = result - (result * result * in - 1) * 0.5 * result; 1652 /* Search the value with the maximum error that is still within the 1653 architectural spec. */ 1654 frac = frexp (result, &exp); 1655 frac = ldexp (frac, 24); 1656 error = 4.0; /* 1 << 24-1-21 */ 1657 /* use eps to compensate for possible 1 ulp error in our 'exact' result. */ 1658 eps = ldexp (1., -29); 1659 upper = floor (frac + error - eps); 1660 if (upper > 16777216.) 1661 upper = floor ((frac + error - eps) * 0.5) * 2.; 1662 lower = ceil ((frac - error + eps) * 2) * .5; 1663 if (lower > 8388608.) 1664 lower = ceil (frac - error + eps); 1665 upper = ldexp (upper, exp - 24); 1666 lower = ldexp (lower, exp - 24); 1667 return upper - result >= result - lower ? upper : lower; 1668} 1669 1670 1671/* GET_LOOP_BOUNDS {EXTENDED} 1672 These two functions compute the actual starting and ending point 1673 of the repeat loop, based on the RS and RE registers (repeat start, 1674 repeat stop). The extended version is called for LDRC, and the 1675 regular version is called for SETRC. The difference is that for 1676 LDRC, the loop start and end instructions are literally the ones 1677 pointed to by RS and RE -- for SETRC, they're not (see docs). */ 1678 1679static struct loop_bounds 1680get_loop_bounds_ext (rs, re, memory, mem_end, maskw, endianw) 1681 int rs, re; 1682 unsigned char *memory, *mem_end; 1683 int maskw, endianw; 1684{ 1685 struct loop_bounds loop; 1686 1687 /* FIXME: should I verify RS < RE? */ 1688 loop.start = PT2H (RS); /* FIXME not using the params? */ 1689 loop.end = PT2H (RE & ~1); /* Ignore bit 0 of RE. */ 1690 SKIP_INSN (loop.end); 1691 if (loop.end >= mem_end) 1692 loop.end = PT2H (0); 1693 return loop; 1694} 1695 1696static struct loop_bounds 1697get_loop_bounds (rs, re, memory, mem_end, maskw, endianw) 1698 int rs, re; 1699 unsigned char *memory, *mem_end; 1700 int maskw, endianw; 1701{ 1702 struct loop_bounds loop; 1703 1704 if (SR_RC) 1705 { 1706 if (RS >= RE) 1707 { 1708 loop.start = PT2H (RE - 4); 1709 SKIP_INSN (loop.start); 1710 loop.end = loop.start; 1711 if (RS - RE == 0) 1712 SKIP_INSN (loop.end); 1713 if (RS - RE <= 2) 1714 SKIP_INSN (loop.end); 1715 SKIP_INSN (loop.end); 1716 } 1717 else 1718 { 1719 loop.start = PT2H (RS); 1720 loop.end = PT2H (RE - 4); 1721 SKIP_INSN (loop.end); 1722 SKIP_INSN (loop.end); 1723 SKIP_INSN (loop.end); 1724 SKIP_INSN (loop.end); 1725 } 1726 if (loop.end >= mem_end) 1727 loop.end = PT2H (0); 1728 } 1729 else 1730 loop.end = PT2H (0); 1731 1732 return loop; 1733} 1734 1735static void ppi_insn (); 1736 1737#include "ppi.c" 1738 1739/* Provide calloc / free versions that use an anonymous mmap. This can 1740 significantly cut the start-up time when a large simulator memory is 1741 required, because pages are only zeroed on demand. */ 1742#ifdef MAP_ANONYMOUS 1743void * 1744mcalloc (size_t nmemb, size_t size) 1745{ 1746 void *page; 1747 1748 if (nmemb != 1) 1749 size *= nmemb; 1750 return mmap (0, size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, 1751 -1, 0); 1752} 1753 1754#define mfree(start,length) munmap ((start), (length)) 1755#else 1756#define mcalloc calloc 1757#define mfree(start,length) free(start) 1758#endif 1759 1760/* Set the memory size to the power of two provided. */ 1761 1762void 1763sim_size (power) 1764 int power; 1765 1766{ 1767 sim_memory_size = power; 1768 1769 if (saved_state.asregs.memory) 1770 { 1771 mfree (saved_state.asregs.memory, saved_state.asregs.msize); 1772 } 1773 1774 saved_state.asregs.msize = 1 << power; 1775 1776 saved_state.asregs.memory = 1777 (unsigned char *) mcalloc (1, saved_state.asregs.msize); 1778 1779 if (!saved_state.asregs.memory) 1780 { 1781 fprintf (stderr, 1782 "Not enough VM for simulation of %d bytes of RAM\n", 1783 saved_state.asregs.msize); 1784 1785 saved_state.asregs.msize = 1; 1786 saved_state.asregs.memory = (unsigned char *) mcalloc (1, 1); 1787 } 1788} 1789 1790static void 1791init_dsp (abfd) 1792 struct bfd *abfd; 1793{ 1794 int was_dsp = target_dsp; 1795 unsigned long mach = bfd_get_mach (abfd); 1796 1797 if (mach == bfd_mach_sh_dsp || 1798 mach == bfd_mach_sh4al_dsp || 1799 mach == bfd_mach_sh3_dsp) 1800 { 1801 int ram_area_size, xram_start, yram_start; 1802 int new_select; 1803 1804 target_dsp = 1; 1805 if (mach == bfd_mach_sh_dsp) 1806 { 1807 /* SH7410 (orig. sh-sdp): 1808 4KB each for X & Y memory; 1809 On-chip X RAM 0x0800f000-0x0800ffff 1810 On-chip Y RAM 0x0801f000-0x0801ffff */ 1811 xram_start = 0x0800f000; 1812 ram_area_size = 0x1000; 1813 } 1814 if (mach == bfd_mach_sh3_dsp || mach == bfd_mach_sh4al_dsp) 1815 { 1816 /* SH7612: 1817 8KB each for X & Y memory; 1818 On-chip X RAM 0x1000e000-0x1000ffff 1819 On-chip Y RAM 0x1001e000-0x1001ffff */ 1820 xram_start = 0x1000e000; 1821 ram_area_size = 0x2000; 1822 } 1823 yram_start = xram_start + 0x10000; 1824 new_select = ~(ram_area_size - 1); 1825 if (saved_state.asregs.xyram_select != new_select) 1826 { 1827 saved_state.asregs.xyram_select = new_select; 1828 free (saved_state.asregs.xmem); 1829 free (saved_state.asregs.ymem); 1830 saved_state.asregs.xmem = 1831 (unsigned char *) calloc (1, ram_area_size); 1832 saved_state.asregs.ymem = 1833 (unsigned char *) calloc (1, ram_area_size); 1834 1835 /* Disable use of X / Y mmeory if not allocated. */ 1836 if (! saved_state.asregs.xmem || ! saved_state.asregs.ymem) 1837 { 1838 saved_state.asregs.xyram_select = 0; 1839 if (saved_state.asregs.xmem) 1840 free (saved_state.asregs.xmem); 1841 if (saved_state.asregs.ymem) 1842 free (saved_state.asregs.ymem); 1843 } 1844 } 1845 saved_state.asregs.xram_start = xram_start; 1846 saved_state.asregs.yram_start = yram_start; 1847 saved_state.asregs.xmem_offset = saved_state.asregs.xmem - xram_start; 1848 saved_state.asregs.ymem_offset = saved_state.asregs.ymem - yram_start; 1849 } 1850 else 1851 { 1852 target_dsp = 0; 1853 if (saved_state.asregs.xyram_select) 1854 { 1855 saved_state.asregs.xyram_select = 0; 1856 free (saved_state.asregs.xmem); 1857 free (saved_state.asregs.ymem); 1858 } 1859 } 1860 1861 if (! saved_state.asregs.xyram_select) 1862 { 1863 saved_state.asregs.xram_start = 1; 1864 saved_state.asregs.yram_start = 1; 1865 } 1866 1867 if (saved_state.asregs.regstack == NULL) 1868 saved_state.asregs.regstack = 1869 calloc (512, sizeof *saved_state.asregs.regstack); 1870 1871 if (target_dsp != was_dsp) 1872 { 1873 int i, tmp; 1874 1875 for (i = (sizeof sh_dsp_table / sizeof sh_dsp_table[0]) - 1; i >= 0; i--) 1876 { 1877 tmp = sh_jump_table[0xf000 + i]; 1878 sh_jump_table[0xf000 + i] = sh_dsp_table[i]; 1879 sh_dsp_table[i] = tmp; 1880 } 1881 } 1882} 1883 1884static void 1885init_pointers () 1886{ 1887 host_little_endian = 0; 1888 * (char*) &host_little_endian = 1; 1889 host_little_endian &= 1; 1890 1891 if (saved_state.asregs.msize != 1 << sim_memory_size) 1892 { 1893 sim_size (sim_memory_size); 1894 } 1895 1896 if (saved_state.asregs.profile && !profile_file) 1897 { 1898 profile_file = fopen ("gmon.out", "wb"); 1899 /* Seek to where to put the call arc data */ 1900 nsamples = (1 << sim_profile_size); 1901 1902 fseek (profile_file, nsamples * 2 + 12, 0); 1903 1904 if (!profile_file) 1905 { 1906 fprintf (stderr, "Can't open gmon.out\n"); 1907 } 1908 else 1909 { 1910 saved_state.asregs.profile_hist = 1911 (unsigned short *) calloc (64, (nsamples * sizeof (short) / 64)); 1912 } 1913 } 1914} 1915 1916static void 1917dump_profile () 1918{ 1919 unsigned int minpc; 1920 unsigned int maxpc; 1921 unsigned short *p; 1922 int i; 1923 1924 p = saved_state.asregs.profile_hist; 1925 minpc = 0; 1926 maxpc = (1 << sim_profile_size); 1927 1928 fseek (profile_file, 0L, 0); 1929 swapout (minpc << PROFILE_SHIFT); 1930 swapout (maxpc << PROFILE_SHIFT); 1931 swapout (nsamples * 2 + 12); 1932 for (i = 0; i < nsamples; i++) 1933 swapout16 (saved_state.asregs.profile_hist[i]); 1934 1935} 1936 1937static void 1938gotcall (from, to) 1939 int from; 1940 int to; 1941{ 1942 swapout (from); 1943 swapout (to); 1944 swapout (1); 1945} 1946 1947#define MMASKB ((saved_state.asregs.msize -1) & ~0) 1948 1949int 1950sim_stop (sd) 1951 SIM_DESC sd; 1952{ 1953 raise_exception (SIGINT); 1954 return 1; 1955} 1956 1957void 1958sim_resume (sd, step, siggnal) 1959 SIM_DESC sd; 1960 int step, siggnal; 1961{ 1962 register unsigned char *insn_ptr; 1963 unsigned char *mem_end; 1964 struct loop_bounds loop; 1965 register int cycles = 0; 1966 register int stalls = 0; 1967 register int memstalls = 0; 1968 register int insts = 0; 1969 register int prevlock; 1970#if 1 1971 int thislock; 1972#else 1973 register int thislock; 1974#endif 1975 register unsigned int doprofile; 1976 register int pollcount = 0; 1977 /* endianw is used for every insn fetch, hence it makes sense to cache it. 1978 endianb is used less often. */ 1979 register int endianw = global_endianw; 1980 1981 int tick_start = get_now (); 1982 void (*prev) (); 1983 void (*prev_fpe) (); 1984 1985 register unsigned short *jump_table = sh_jump_table; 1986 1987 register int *R = &(saved_state.asregs.regs[0]); 1988 /*register int T;*/ 1989#ifndef PR 1990 register int PR; 1991#endif 1992 1993 register int maskb = ~((saved_state.asregs.msize - 1) & ~0); 1994 register int maskw = ~((saved_state.asregs.msize - 1) & ~1); 1995 register int maskl = ~((saved_state.asregs.msize - 1) & ~3); 1996 register unsigned char *memory; 1997 register unsigned int sbit = ((unsigned int) 1 << 31); 1998 1999 prev = signal (SIGINT, control_c); 2000 prev_fpe = signal (SIGFPE, SIG_IGN); 2001 2002 init_pointers (); 2003 saved_state.asregs.exception = 0; 2004 2005 memory = saved_state.asregs.memory; 2006 mem_end = memory + saved_state.asregs.msize; 2007 2008 if (RE & 1) 2009 loop = get_loop_bounds_ext (RS, RE, memory, mem_end, maskw, endianw); 2010 else 2011 loop = get_loop_bounds (RS, RE, memory, mem_end, maskw, endianw); 2012 2013 insn_ptr = PT2H (saved_state.asregs.pc); 2014 CHECK_INSN_PTR (insn_ptr); 2015 2016#ifndef PR 2017 PR = saved_state.asregs.sregs.named.pr; 2018#endif 2019 /*T = GET_SR () & SR_MASK_T;*/ 2020 prevlock = saved_state.asregs.prevlock; 2021 thislock = saved_state.asregs.thislock; 2022 doprofile = saved_state.asregs.profile; 2023 2024 /* If profiling not enabled, disable it by asking for 2025 profiles infrequently. */ 2026 if (doprofile == 0) 2027 doprofile = ~0; 2028 2029 loop: 2030 if (step && insn_ptr < saved_state.asregs.insn_end) 2031 { 2032 if (saved_state.asregs.exception) 2033 /* This can happen if we've already been single-stepping and 2034 encountered a loop end. */ 2035 saved_state.asregs.insn_end = insn_ptr; 2036 else 2037 { 2038 saved_state.asregs.exception = SIGTRAP; 2039 saved_state.asregs.insn_end = insn_ptr + 2; 2040 } 2041 } 2042 2043 while (insn_ptr < saved_state.asregs.insn_end) 2044 { 2045 register unsigned int iword = RIAT (insn_ptr); 2046 register unsigned int ult; 2047 register unsigned char *nip = insn_ptr + 2; 2048 2049#ifndef ACE_FAST 2050 insts++; 2051#endif 2052 top: 2053 if (tracing) 2054 fprintf (stderr, "PC: %08x, insn: %04x\n", PH2T (insn_ptr), iword); 2055 2056#include "code.c" 2057 2058 2059 in_delay_slot = 0; 2060 insn_ptr = nip; 2061 2062 if (--pollcount < 0) 2063 { 2064 pollcount = POLL_QUIT_INTERVAL; 2065 if ((*callback->poll_quit) != NULL 2066 && (*callback->poll_quit) (callback)) 2067 { 2068 sim_stop (sd); 2069 } 2070 } 2071 2072#ifndef ACE_FAST 2073 prevlock = thislock; 2074 thislock = 30; 2075 cycles++; 2076 2077 if (cycles >= doprofile) 2078 { 2079 2080 saved_state.asregs.cycles += doprofile; 2081 cycles -= doprofile; 2082 if (saved_state.asregs.profile_hist) 2083 { 2084 int n = PH2T (insn_ptr) >> PROFILE_SHIFT; 2085 if (n < nsamples) 2086 { 2087 int i = saved_state.asregs.profile_hist[n]; 2088 if (i < 65000) 2089 saved_state.asregs.profile_hist[n] = i + 1; 2090 } 2091 2092 } 2093 } 2094#endif 2095 } 2096 if (saved_state.asregs.insn_end == loop.end) 2097 { 2098 saved_state.asregs.cregs.named.sr += SR_RC_INCREMENT; 2099 if (SR_RC) 2100 insn_ptr = loop.start; 2101 else 2102 { 2103 saved_state.asregs.insn_end = mem_end; 2104 loop.end = PT2H (0); 2105 } 2106 goto loop; 2107 } 2108 2109 if (saved_state.asregs.exception == SIGILL 2110 || saved_state.asregs.exception == SIGBUS) 2111 { 2112 insn_ptr -= 2; 2113 } 2114 /* Check for SIGBUS due to insn fetch. */ 2115 else if (! saved_state.asregs.exception) 2116 saved_state.asregs.exception = SIGBUS; 2117 2118 saved_state.asregs.ticks += get_now () - tick_start; 2119 saved_state.asregs.cycles += cycles; 2120 saved_state.asregs.stalls += stalls; 2121 saved_state.asregs.memstalls += memstalls; 2122 saved_state.asregs.insts += insts; 2123 saved_state.asregs.pc = PH2T (insn_ptr); 2124#ifndef PR 2125 saved_state.asregs.sregs.named.pr = PR; 2126#endif 2127 2128 saved_state.asregs.prevlock = prevlock; 2129 saved_state.asregs.thislock = thislock; 2130 2131 if (profile_file) 2132 { 2133 dump_profile (); 2134 } 2135 2136 signal (SIGFPE, prev_fpe); 2137 signal (SIGINT, prev); 2138} 2139 2140int 2141sim_write (sd, addr, buffer, size) 2142 SIM_DESC sd; 2143 SIM_ADDR addr; 2144 const unsigned char *buffer; 2145 int size; 2146{ 2147 int i; 2148 2149 init_pointers (); 2150 2151 for (i = 0; i < size; i++) 2152 { 2153 saved_state.asregs.memory[(MMASKB & (addr + i)) ^ endianb] = buffer[i]; 2154 } 2155 return size; 2156} 2157 2158int 2159sim_read (sd, addr, buffer, size) 2160 SIM_DESC sd; 2161 SIM_ADDR addr; 2162 unsigned char *buffer; 2163 int size; 2164{ 2165 int i; 2166 2167 init_pointers (); 2168 2169 for (i = 0; i < size; i++) 2170 { 2171 buffer[i] = saved_state.asregs.memory[(MMASKB & (addr + i)) ^ endianb]; 2172 } 2173 return size; 2174} 2175 2176static int gdb_bank_number; 2177enum { 2178 REGBANK_MACH = 15, 2179 REGBANK_IVN = 16, 2180 REGBANK_PR = 17, 2181 REGBANK_GBR = 18, 2182 REGBANK_MACL = 19 2183}; 2184 2185int 2186sim_store_register (sd, rn, memory, length) 2187 SIM_DESC sd; 2188 int rn; 2189 unsigned char *memory; 2190 int length; 2191{ 2192 unsigned val; 2193 2194 init_pointers (); 2195 val = swap (* (int *) memory); 2196 switch (rn) 2197 { 2198 case SIM_SH_R0_REGNUM: case SIM_SH_R1_REGNUM: case SIM_SH_R2_REGNUM: 2199 case SIM_SH_R3_REGNUM: case SIM_SH_R4_REGNUM: case SIM_SH_R5_REGNUM: 2200 case SIM_SH_R6_REGNUM: case SIM_SH_R7_REGNUM: case SIM_SH_R8_REGNUM: 2201 case SIM_SH_R9_REGNUM: case SIM_SH_R10_REGNUM: case SIM_SH_R11_REGNUM: 2202 case SIM_SH_R12_REGNUM: case SIM_SH_R13_REGNUM: case SIM_SH_R14_REGNUM: 2203 case SIM_SH_R15_REGNUM: 2204 saved_state.asregs.regs[rn] = val; 2205 break; 2206 case SIM_SH_PC_REGNUM: 2207 saved_state.asregs.pc = val; 2208 break; 2209 case SIM_SH_PR_REGNUM: 2210 PR = val; 2211 break; 2212 case SIM_SH_GBR_REGNUM: 2213 GBR = val; 2214 break; 2215 case SIM_SH_VBR_REGNUM: 2216 VBR = val; 2217 break; 2218 case SIM_SH_MACH_REGNUM: 2219 MACH = val; 2220 break; 2221 case SIM_SH_MACL_REGNUM: 2222 MACL = val; 2223 break; 2224 case SIM_SH_SR_REGNUM: 2225 SET_SR (val); 2226 break; 2227 case SIM_SH_FPUL_REGNUM: 2228 FPUL = val; 2229 break; 2230 case SIM_SH_FPSCR_REGNUM: 2231 SET_FPSCR (val); 2232 break; 2233 case SIM_SH_FR0_REGNUM: case SIM_SH_FR1_REGNUM: case SIM_SH_FR2_REGNUM: 2234 case SIM_SH_FR3_REGNUM: case SIM_SH_FR4_REGNUM: case SIM_SH_FR5_REGNUM: 2235 case SIM_SH_FR6_REGNUM: case SIM_SH_FR7_REGNUM: case SIM_SH_FR8_REGNUM: 2236 case SIM_SH_FR9_REGNUM: case SIM_SH_FR10_REGNUM: case SIM_SH_FR11_REGNUM: 2237 case SIM_SH_FR12_REGNUM: case SIM_SH_FR13_REGNUM: case SIM_SH_FR14_REGNUM: 2238 case SIM_SH_FR15_REGNUM: 2239 SET_FI (rn - SIM_SH_FR0_REGNUM, val); 2240 break; 2241 case SIM_SH_DSR_REGNUM: 2242 DSR = val; 2243 break; 2244 case SIM_SH_A0G_REGNUM: 2245 A0G = val; 2246 break; 2247 case SIM_SH_A0_REGNUM: 2248 A0 = val; 2249 break; 2250 case SIM_SH_A1G_REGNUM: 2251 A1G = val; 2252 break; 2253 case SIM_SH_A1_REGNUM: 2254 A1 = val; 2255 break; 2256 case SIM_SH_M0_REGNUM: 2257 M0 = val; 2258 break; 2259 case SIM_SH_M1_REGNUM: 2260 M1 = val; 2261 break; 2262 case SIM_SH_X0_REGNUM: 2263 X0 = val; 2264 break; 2265 case SIM_SH_X1_REGNUM: 2266 X1 = val; 2267 break; 2268 case SIM_SH_Y0_REGNUM: 2269 Y0 = val; 2270 break; 2271 case SIM_SH_Y1_REGNUM: 2272 Y1 = val; 2273 break; 2274 case SIM_SH_MOD_REGNUM: 2275 SET_MOD (val); 2276 break; 2277 case SIM_SH_RS_REGNUM: 2278 RS = val; 2279 break; 2280 case SIM_SH_RE_REGNUM: 2281 RE = val; 2282 break; 2283 case SIM_SH_SSR_REGNUM: 2284 SSR = val; 2285 break; 2286 case SIM_SH_SPC_REGNUM: 2287 SPC = val; 2288 break; 2289 /* The rn_bank idiosyncracies are not due to hardware differences, but to 2290 a weird aliasing naming scheme for sh3 / sh3e / sh4. */ 2291 case SIM_SH_R0_BANK0_REGNUM: case SIM_SH_R1_BANK0_REGNUM: 2292 case SIM_SH_R2_BANK0_REGNUM: case SIM_SH_R3_BANK0_REGNUM: 2293 case SIM_SH_R4_BANK0_REGNUM: case SIM_SH_R5_BANK0_REGNUM: 2294 case SIM_SH_R6_BANK0_REGNUM: case SIM_SH_R7_BANK0_REGNUM: 2295 if (saved_state.asregs.bfd_mach == bfd_mach_sh2a) 2296 { 2297 rn -= SIM_SH_R0_BANK0_REGNUM; 2298 saved_state.asregs.regstack[gdb_bank_number].regs[rn] = val; 2299 } 2300 else 2301 if (SR_MD && SR_RB) 2302 Rn_BANK (rn - SIM_SH_R0_BANK0_REGNUM) = val; 2303 else 2304 saved_state.asregs.regs[rn - SIM_SH_R0_BANK0_REGNUM] = val; 2305 break; 2306 case SIM_SH_R0_BANK1_REGNUM: case SIM_SH_R1_BANK1_REGNUM: 2307 case SIM_SH_R2_BANK1_REGNUM: case SIM_SH_R3_BANK1_REGNUM: 2308 case SIM_SH_R4_BANK1_REGNUM: case SIM_SH_R5_BANK1_REGNUM: 2309 case SIM_SH_R6_BANK1_REGNUM: case SIM_SH_R7_BANK1_REGNUM: 2310 if (saved_state.asregs.bfd_mach == bfd_mach_sh2a) 2311 { 2312 rn -= SIM_SH_R0_BANK1_REGNUM; 2313 saved_state.asregs.regstack[gdb_bank_number].regs[rn + 8] = val; 2314 } 2315 else 2316 if (SR_MD && SR_RB) 2317 saved_state.asregs.regs[rn - SIM_SH_R0_BANK1_REGNUM] = val; 2318 else 2319 Rn_BANK (rn - SIM_SH_R0_BANK1_REGNUM) = val; 2320 break; 2321 case SIM_SH_R0_BANK_REGNUM: case SIM_SH_R1_BANK_REGNUM: 2322 case SIM_SH_R2_BANK_REGNUM: case SIM_SH_R3_BANK_REGNUM: 2323 case SIM_SH_R4_BANK_REGNUM: case SIM_SH_R5_BANK_REGNUM: 2324 case SIM_SH_R6_BANK_REGNUM: case SIM_SH_R7_BANK_REGNUM: 2325 SET_Rn_BANK (rn - SIM_SH_R0_BANK_REGNUM, val); 2326 break; 2327 case SIM_SH_TBR_REGNUM: 2328 TBR = val; 2329 break; 2330 case SIM_SH_IBNR_REGNUM: 2331 IBNR = val; 2332 break; 2333 case SIM_SH_IBCR_REGNUM: 2334 IBCR = val; 2335 break; 2336 case SIM_SH_BANK_REGNUM: 2337 /* This is a pseudo-register maintained just for gdb. 2338 It tells us what register bank gdb would like to read/write. */ 2339 gdb_bank_number = val; 2340 break; 2341 case SIM_SH_BANK_MACL_REGNUM: 2342 saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_MACL] = val; 2343 break; 2344 case SIM_SH_BANK_GBR_REGNUM: 2345 saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_GBR] = val; 2346 break; 2347 case SIM_SH_BANK_PR_REGNUM: 2348 saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_PR] = val; 2349 break; 2350 case SIM_SH_BANK_IVN_REGNUM: 2351 saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_IVN] = val; 2352 break; 2353 case SIM_SH_BANK_MACH_REGNUM: 2354 saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_MACH] = val; 2355 break; 2356 default: 2357 return 0; 2358 } 2359 return -1; 2360} 2361 2362int 2363sim_fetch_register (sd, rn, memory, length) 2364 SIM_DESC sd; 2365 int rn; 2366 unsigned char *memory; 2367 int length; 2368{ 2369 int val; 2370 2371 init_pointers (); 2372 switch (rn) 2373 { 2374 case SIM_SH_R0_REGNUM: case SIM_SH_R1_REGNUM: case SIM_SH_R2_REGNUM: 2375 case SIM_SH_R3_REGNUM: case SIM_SH_R4_REGNUM: case SIM_SH_R5_REGNUM: 2376 case SIM_SH_R6_REGNUM: case SIM_SH_R7_REGNUM: case SIM_SH_R8_REGNUM: 2377 case SIM_SH_R9_REGNUM: case SIM_SH_R10_REGNUM: case SIM_SH_R11_REGNUM: 2378 case SIM_SH_R12_REGNUM: case SIM_SH_R13_REGNUM: case SIM_SH_R14_REGNUM: 2379 case SIM_SH_R15_REGNUM: 2380 val = saved_state.asregs.regs[rn]; 2381 break; 2382 case SIM_SH_PC_REGNUM: 2383 val = saved_state.asregs.pc; 2384 break; 2385 case SIM_SH_PR_REGNUM: 2386 val = PR; 2387 break; 2388 case SIM_SH_GBR_REGNUM: 2389 val = GBR; 2390 break; 2391 case SIM_SH_VBR_REGNUM: 2392 val = VBR; 2393 break; 2394 case SIM_SH_MACH_REGNUM: 2395 val = MACH; 2396 break; 2397 case SIM_SH_MACL_REGNUM: 2398 val = MACL; 2399 break; 2400 case SIM_SH_SR_REGNUM: 2401 val = GET_SR (); 2402 break; 2403 case SIM_SH_FPUL_REGNUM: 2404 val = FPUL; 2405 break; 2406 case SIM_SH_FPSCR_REGNUM: 2407 val = GET_FPSCR (); 2408 break; 2409 case SIM_SH_FR0_REGNUM: case SIM_SH_FR1_REGNUM: case SIM_SH_FR2_REGNUM: 2410 case SIM_SH_FR3_REGNUM: case SIM_SH_FR4_REGNUM: case SIM_SH_FR5_REGNUM: 2411 case SIM_SH_FR6_REGNUM: case SIM_SH_FR7_REGNUM: case SIM_SH_FR8_REGNUM: 2412 case SIM_SH_FR9_REGNUM: case SIM_SH_FR10_REGNUM: case SIM_SH_FR11_REGNUM: 2413 case SIM_SH_FR12_REGNUM: case SIM_SH_FR13_REGNUM: case SIM_SH_FR14_REGNUM: 2414 case SIM_SH_FR15_REGNUM: 2415 val = FI (rn - SIM_SH_FR0_REGNUM); 2416 break; 2417 case SIM_SH_DSR_REGNUM: 2418 val = DSR; 2419 break; 2420 case SIM_SH_A0G_REGNUM: 2421 val = SEXT (A0G); 2422 break; 2423 case SIM_SH_A0_REGNUM: 2424 val = A0; 2425 break; 2426 case SIM_SH_A1G_REGNUM: 2427 val = SEXT (A1G); 2428 break; 2429 case SIM_SH_A1_REGNUM: 2430 val = A1; 2431 break; 2432 case SIM_SH_M0_REGNUM: 2433 val = M0; 2434 break; 2435 case SIM_SH_M1_REGNUM: 2436 val = M1; 2437 break; 2438 case SIM_SH_X0_REGNUM: 2439 val = X0; 2440 break; 2441 case SIM_SH_X1_REGNUM: 2442 val = X1; 2443 break; 2444 case SIM_SH_Y0_REGNUM: 2445 val = Y0; 2446 break; 2447 case SIM_SH_Y1_REGNUM: 2448 val = Y1; 2449 break; 2450 case SIM_SH_MOD_REGNUM: 2451 val = MOD; 2452 break; 2453 case SIM_SH_RS_REGNUM: 2454 val = RS; 2455 break; 2456 case SIM_SH_RE_REGNUM: 2457 val = RE; 2458 break; 2459 case SIM_SH_SSR_REGNUM: 2460 val = SSR; 2461 break; 2462 case SIM_SH_SPC_REGNUM: 2463 val = SPC; 2464 break; 2465 /* The rn_bank idiosyncracies are not due to hardware differences, but to 2466 a weird aliasing naming scheme for sh3 / sh3e / sh4. */ 2467 case SIM_SH_R0_BANK0_REGNUM: case SIM_SH_R1_BANK0_REGNUM: 2468 case SIM_SH_R2_BANK0_REGNUM: case SIM_SH_R3_BANK0_REGNUM: 2469 case SIM_SH_R4_BANK0_REGNUM: case SIM_SH_R5_BANK0_REGNUM: 2470 case SIM_SH_R6_BANK0_REGNUM: case SIM_SH_R7_BANK0_REGNUM: 2471 if (saved_state.asregs.bfd_mach == bfd_mach_sh2a) 2472 { 2473 rn -= SIM_SH_R0_BANK0_REGNUM; 2474 val = saved_state.asregs.regstack[gdb_bank_number].regs[rn]; 2475 } 2476 else 2477 val = (SR_MD && SR_RB 2478 ? Rn_BANK (rn - SIM_SH_R0_BANK0_REGNUM) 2479 : saved_state.asregs.regs[rn - SIM_SH_R0_BANK0_REGNUM]); 2480 break; 2481 case SIM_SH_R0_BANK1_REGNUM: case SIM_SH_R1_BANK1_REGNUM: 2482 case SIM_SH_R2_BANK1_REGNUM: case SIM_SH_R3_BANK1_REGNUM: 2483 case SIM_SH_R4_BANK1_REGNUM: case SIM_SH_R5_BANK1_REGNUM: 2484 case SIM_SH_R6_BANK1_REGNUM: case SIM_SH_R7_BANK1_REGNUM: 2485 if (saved_state.asregs.bfd_mach == bfd_mach_sh2a) 2486 { 2487 rn -= SIM_SH_R0_BANK1_REGNUM; 2488 val = saved_state.asregs.regstack[gdb_bank_number].regs[rn + 8]; 2489 } 2490 else 2491 val = (! SR_MD || ! SR_RB 2492 ? Rn_BANK (rn - SIM_SH_R0_BANK1_REGNUM) 2493 : saved_state.asregs.regs[rn - SIM_SH_R0_BANK1_REGNUM]); 2494 break; 2495 case SIM_SH_R0_BANK_REGNUM: case SIM_SH_R1_BANK_REGNUM: 2496 case SIM_SH_R2_BANK_REGNUM: case SIM_SH_R3_BANK_REGNUM: 2497 case SIM_SH_R4_BANK_REGNUM: case SIM_SH_R5_BANK_REGNUM: 2498 case SIM_SH_R6_BANK_REGNUM: case SIM_SH_R7_BANK_REGNUM: 2499 val = Rn_BANK (rn - SIM_SH_R0_BANK_REGNUM); 2500 break; 2501 case SIM_SH_TBR_REGNUM: 2502 val = TBR; 2503 break; 2504 case SIM_SH_IBNR_REGNUM: 2505 val = IBNR; 2506 break; 2507 case SIM_SH_IBCR_REGNUM: 2508 val = IBCR; 2509 break; 2510 case SIM_SH_BANK_REGNUM: 2511 /* This is a pseudo-register maintained just for gdb. 2512 It tells us what register bank gdb would like to read/write. */ 2513 val = gdb_bank_number; 2514 break; 2515 case SIM_SH_BANK_MACL_REGNUM: 2516 val = saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_MACL]; 2517 break; 2518 case SIM_SH_BANK_GBR_REGNUM: 2519 val = saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_GBR]; 2520 break; 2521 case SIM_SH_BANK_PR_REGNUM: 2522 val = saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_PR]; 2523 break; 2524 case SIM_SH_BANK_IVN_REGNUM: 2525 val = saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_IVN]; 2526 break; 2527 case SIM_SH_BANK_MACH_REGNUM: 2528 val = saved_state.asregs.regstack[gdb_bank_number].regs[REGBANK_MACH]; 2529 break; 2530 default: 2531 return 0; 2532 } 2533 * (int *) memory = swap (val); 2534 return -1; 2535} 2536 2537int 2538sim_trace (sd) 2539 SIM_DESC sd; 2540{ 2541 tracing = 1; 2542 sim_resume (sd, 0, 0); 2543 tracing = 0; 2544 return 1; 2545} 2546 2547void 2548sim_stop_reason (sd, reason, sigrc) 2549 SIM_DESC sd; 2550 enum sim_stop *reason; 2551 int *sigrc; 2552{ 2553 /* The SH simulator uses SIGQUIT to indicate that the program has 2554 exited, so we must check for it here and translate it to exit. */ 2555 if (saved_state.asregs.exception == SIGQUIT) 2556 { 2557 *reason = sim_exited; 2558 *sigrc = saved_state.asregs.regs[5]; 2559 } 2560 else 2561 { 2562 *reason = sim_stopped; 2563 *sigrc = saved_state.asregs.exception; 2564 } 2565} 2566 2567void 2568sim_info (sd, verbose) 2569 SIM_DESC sd; 2570 int verbose; 2571{ 2572 double timetaken = 2573 (double) saved_state.asregs.ticks / (double) now_persec (); 2574 double virttime = saved_state.asregs.cycles / 36.0e6; 2575 2576 callback->printf_filtered (callback, "\n\n# instructions executed %10d\n", 2577 saved_state.asregs.insts); 2578 callback->printf_filtered (callback, "# cycles %10d\n", 2579 saved_state.asregs.cycles); 2580 callback->printf_filtered (callback, "# pipeline stalls %10d\n", 2581 saved_state.asregs.stalls); 2582 callback->printf_filtered (callback, "# misaligned load/store %10d\n", 2583 saved_state.asregs.memstalls); 2584 callback->printf_filtered (callback, "# real time taken %10.4f\n", 2585 timetaken); 2586 callback->printf_filtered (callback, "# virtual time taken %10.4f\n", 2587 virttime); 2588 callback->printf_filtered (callback, "# profiling size %10d\n", 2589 sim_profile_size); 2590 callback->printf_filtered (callback, "# profiling frequency %10d\n", 2591 saved_state.asregs.profile); 2592 callback->printf_filtered (callback, "# profile maxpc %10x\n", 2593 (1 << sim_profile_size) << PROFILE_SHIFT); 2594 2595 if (timetaken != 0) 2596 { 2597 callback->printf_filtered (callback, "# cycles/second %10d\n", 2598 (int) (saved_state.asregs.cycles / timetaken)); 2599 callback->printf_filtered (callback, "# simulation ratio %10.4f\n", 2600 virttime / timetaken); 2601 } 2602} 2603 2604void 2605sim_set_profile (n) 2606 int n; 2607{ 2608 saved_state.asregs.profile = n; 2609} 2610 2611void 2612sim_set_profile_size (n) 2613 int n; 2614{ 2615 sim_profile_size = n; 2616} 2617 2618SIM_DESC 2619sim_open (kind, cb, abfd, argv) 2620 SIM_OPEN_KIND kind; 2621 host_callback *cb; 2622 struct bfd *abfd; 2623 char **argv; 2624{ 2625 char **p; 2626 int endian_set = 0; 2627 int i; 2628 union 2629 { 2630 int i; 2631 short s[2]; 2632 char c[4]; 2633 } 2634 mem_word; 2635 2636 sim_kind = kind; 2637 myname = argv[0]; 2638 callback = cb; 2639 2640 for (p = argv + 1; *p != NULL; ++p) 2641 { 2642 if (strcmp (*p, "-E") == 0) 2643 { 2644 ++p; 2645 if (*p == NULL) 2646 { 2647 /* FIXME: This doesn't use stderr, but then the rest of the 2648 file doesn't either. */ 2649 callback->printf_filtered (callback, "Missing argument to `-E'.\n"); 2650 return 0; 2651 } 2652 target_little_endian = strcmp (*p, "big") != 0; 2653 endian_set = 1; 2654 } 2655 else if (isdigit (**p)) 2656 parse_and_set_memory_size (*p); 2657 } 2658 2659 if (abfd != NULL && ! endian_set) 2660 target_little_endian = ! bfd_big_endian (abfd); 2661 2662 if (abfd) 2663 init_dsp (abfd); 2664 2665 for (i = 4; (i -= 2) >= 0; ) 2666 mem_word.s[i >> 1] = i; 2667 global_endianw = mem_word.i >> (target_little_endian ? 0 : 16) & 0xffff; 2668 2669 for (i = 4; --i >= 0; ) 2670 mem_word.c[i] = i; 2671 endianb = mem_word.i >> (target_little_endian ? 0 : 24) & 0xff; 2672 2673 /* fudge our descriptor for now */ 2674 return (SIM_DESC) 1; 2675} 2676 2677static void 2678parse_and_set_memory_size (str) 2679 char *str; 2680{ 2681 int n; 2682 2683 n = strtol (str, NULL, 10); 2684 if (n > 0 && n <= 24) 2685 sim_memory_size = n; 2686 else 2687 callback->printf_filtered (callback, "Bad memory size %d; must be 1 to 24, inclusive\n", n); 2688} 2689 2690void 2691sim_close (sd, quitting) 2692 SIM_DESC sd; 2693 int quitting; 2694{ 2695 /* nothing to do */ 2696} 2697 2698SIM_RC 2699sim_load (sd, prog, abfd, from_tty) 2700 SIM_DESC sd; 2701 char *prog; 2702 bfd *abfd; 2703 int from_tty; 2704{ 2705 extern bfd *sim_load_file (); /* ??? Don't know where this should live. */ 2706 bfd *prog_bfd; 2707 2708 prog_bfd = sim_load_file (sd, myname, callback, prog, abfd, 2709 sim_kind == SIM_OPEN_DEBUG, 2710 0, sim_write); 2711 2712 /* Set the bfd machine type. */ 2713 if (prog_bfd) 2714 saved_state.asregs.bfd_mach = bfd_get_mach (prog_bfd); 2715 else if (abfd) 2716 saved_state.asregs.bfd_mach = bfd_get_mach (abfd); 2717 else 2718 saved_state.asregs.bfd_mach = 0; 2719 2720 if (prog_bfd == NULL) 2721 return SIM_RC_FAIL; 2722 if (abfd == NULL) 2723 bfd_close (prog_bfd); 2724 return SIM_RC_OK; 2725} 2726 2727SIM_RC 2728sim_create_inferior (sd, prog_bfd, argv, env) 2729 SIM_DESC sd; 2730 struct bfd *prog_bfd; 2731 char **argv; 2732 char **env; 2733{ 2734 /* Clear the registers. */ 2735 memset (&saved_state, 0, 2736 (char*) &saved_state.asregs.end_of_registers - (char*) &saved_state); 2737 2738 /* Set the PC. */ 2739 if (prog_bfd != NULL) 2740 saved_state.asregs.pc = bfd_get_start_address (prog_bfd); 2741 2742 /* Set the bfd machine type. */ 2743 if (prog_bfd != NULL) 2744 saved_state.asregs.bfd_mach = bfd_get_mach (prog_bfd); 2745 2746 /* Record the program's arguments. */ 2747 prog_argv = argv; 2748 2749 return SIM_RC_OK; 2750} 2751 2752void 2753sim_do_command (sd, cmd) 2754 SIM_DESC sd; 2755 char *cmd; 2756{ 2757 char *sms_cmd = "set-memory-size"; 2758 int cmdsize; 2759 2760 if (cmd == NULL || *cmd == '\0') 2761 { 2762 cmd = "help"; 2763 } 2764 2765 cmdsize = strlen (sms_cmd); 2766 if (strncmp (cmd, sms_cmd, cmdsize) == 0 2767 && strchr (" \t", cmd[cmdsize]) != NULL) 2768 { 2769 parse_and_set_memory_size (cmd + cmdsize + 1); 2770 } 2771 else if (strcmp (cmd, "help") == 0) 2772 { 2773 (callback->printf_filtered) (callback, 2774 "List of SH simulator commands:\n\n"); 2775 (callback->printf_filtered) (callback, "set-memory-size <n> -- Set the number of address bits to use\n"); 2776 (callback->printf_filtered) (callback, "\n"); 2777 } 2778 else 2779 { 2780 (callback->printf_filtered) (callback, "Error: \"%s\" is not a valid SH simulator command.\n", cmd); 2781 } 2782} 2783 2784void 2785sim_set_callbacks (p) 2786 host_callback *p; 2787{ 2788 callback = p; 2789} 2790