]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - sim/sh/interp.c
e9313c76cbd5a2912ae3554c904a7d51658fa9b0
[thirdparty/binutils-gdb.git] / sim / sh / interp.c
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
82 extern unsigned short sh_jump_table[], sh_dsp_table[0x1000], ppi_table[];
83
84 int 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
94 typedef struct
95 {
96 int regs[20];
97 } regstacktype;
98
99 typedef 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
196 saved_state_type saved_state;
197
198 struct 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
203 static int target_little_endian;
204 static int global_endianw, endianb;
205 static int target_dsp;
206 static int host_little_endian;
207 static char **prog_argv;
208
209 static int maskw = 0;
210 static int maskl = 0;
211
212 static SIM_OPEN_KIND sim_kind;
213 static char *myname;
214 static 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) \
291 do { \
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) \
301 do { \
302 IBNR = (IBNR & 0xfe00) | (EXP & 0x1f); \
303 } while (0)
304 #define SET_ME(EXP) \
305 do { \
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. */
334 static int
335 count_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
347 static void
348 set_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) \
367 do { \
368 set_fpscr1 (x); \
369 } while (0)
370
371 #define DSR (saved_state.asregs.sregs.named.fpscr)
372
373 int
374 fail ()
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
388 void
389 raise_exception (x)
390 int x;
391 {
392 RAISE_EXCEPTION (x);
393 }
394
395 void
396 raise_buserror ()
397 {
398 raise_exception (SIGBUS);
399 }
400
401 #define PROCESS_SPECIAL_ADDRESS(addr, endian, ptr, bits_written, \
402 forbidden_addr_bits, data, retval) \
403 do { \
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
466 int 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
476 static void parse_and_set_memory_size PARAMS ((char *str));
477 static int IOMEM PARAMS ((int addr, int write, int value));
478 static struct loop_bounds get_loop_bounds PARAMS ((int, int, unsigned char *,
479 unsigned char *, int, int));
480 static void process_wlat_addr PARAMS ((int, int));
481 static void process_wwat_addr PARAMS ((int, int));
482 static void process_wbat_addr PARAMS ((int, int));
483 static int process_rlat_addr PARAMS ((int));
484 static int process_rwat_addr PARAMS ((int));
485 static int process_rbat_addr PARAMS ((int));
486 static void INLINE wlat_fast PARAMS ((unsigned char *, int, int, int));
487 static void INLINE wwat_fast PARAMS ((unsigned char *, int, int, int, int));
488 static void INLINE wbat_fast PARAMS ((unsigned char *, int, int, int));
489 static int INLINE rlat_fast PARAMS ((unsigned char *, int, int));
490 static int INLINE rwat_fast PARAMS ((unsigned char *, int, int, int));
491 static int INLINE rbat_fast PARAMS ((unsigned char *, int, int));
492
493 static host_callback *callback;
494
495
496
497 /* Floating point registers */
498
499 #define DR(n) (get_dr (n))
500 static double
501 get_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))
521 static void
522 set_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
616 static void
617 set_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
637 static void INLINE
638 wlat_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
647 static void INLINE
648 wwat_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
657 static void INLINE
658 wbat_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
669 static int INLINE
670 rlat_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
679 static int INLINE
680 rwat_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
690 static int INLINE
691 riat_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
699 static int INLINE
700 rbat_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)))
723 static int
724 do_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)))
742 static int
743 do_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
760 static void
761 process_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
771 static void
772 process_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
782 static void
783 process_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
793 static int
794 process_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
803 static int
804 process_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
813 static int
814 process_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
842 static 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) \
846 do { \
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 += ((((long) 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__)
874 int sim_memory_size = 19;
875 #else
876 int sim_memory_size = 24;
877 #endif
878
879 static int sim_profile_size = 17;
880 static 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
895 static int
896 IOMEM (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
925 static int
926 get_now ()
927 {
928 return time ((long *) 0);
929 }
930
931 static int
932 now_persec ()
933 {
934 return 1;
935 }
936
937 static FILE *profile_file;
938
939 static unsigned INLINE
940 swap (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
949 static unsigned short INLINE
950 swap16 (n)
951 unsigned short n;
952 {
953 if (endianb)
954 n = n << 8 | (n & 0xff00) >> 8;
955 return n;
956 }
957
958 static void
959 swapout (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
970 static void
971 swapout16 (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
981 static char *
982 ptr (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.) */
992 static int
993 strswaplen (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
1007 static void
1008 strnswap (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
1031 static int
1032 trap (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
1264 void
1265 control_c (sig, code, scp, addr)
1266 int sig;
1267 int code;
1268 char *scp;
1269 char *addr;
1270 {
1271 raise_exception (SIGINT);
1272 }
1273
1274 static int
1275 div1 (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
1363 static void
1364 dmul (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
1404 static void
1405 macw (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
1442 static void
1443 macl (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
1487 enum {
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. */
1512 void
1513 do_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. */
1579 void
1580 do_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 }
1621 float
1622 fsca_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
1643 float
1644 fsrra_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
1679 static struct loop_bounds
1680 get_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
1696 static struct loop_bounds
1697 get_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
1735 static 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
1743 void *
1744 mcalloc (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
1762 void
1763 sim_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
1790 static void
1791 init_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
1884 static void
1885 init_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
1916 static void
1917 dump_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
1937 static void
1938 gotcall (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
1949 int
1950 sim_stop (sd)
1951 SIM_DESC sd;
1952 {
1953 raise_exception (SIGINT);
1954 return 1;
1955 }
1956
1957 void
1958 sim_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
2140 int
2141 sim_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
2158 int
2159 sim_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
2176 static int gdb_bank_number;
2177 enum {
2178 REGBANK_MACH = 15,
2179 REGBANK_IVN = 16,
2180 REGBANK_PR = 17,
2181 REGBANK_GBR = 18,
2182 REGBANK_MACL = 19
2183 };
2184
2185 int
2186 sim_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 length;
2360 }
2361
2362 int
2363 sim_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 length;
2535 }
2536
2537 int
2538 sim_trace (sd)
2539 SIM_DESC sd;
2540 {
2541 tracing = 1;
2542 sim_resume (sd, 0, 0);
2543 tracing = 0;
2544 return 1;
2545 }
2546
2547 void
2548 sim_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
2567 void
2568 sim_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
2604 void
2605 sim_set_profile (n)
2606 int n;
2607 {
2608 saved_state.asregs.profile = n;
2609 }
2610
2611 void
2612 sim_set_profile_size (n)
2613 int n;
2614 {
2615 sim_profile_size = n;
2616 }
2617
2618 SIM_DESC
2619 sim_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
2677 static void
2678 parse_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
2690 void
2691 sim_close (sd, quitting)
2692 SIM_DESC sd;
2693 int quitting;
2694 {
2695 /* nothing to do */
2696 }
2697
2698 SIM_RC
2699 sim_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
2727 SIM_RC
2728 sim_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
2752 void
2753 sim_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
2784 void
2785 sim_set_callbacks (p)
2786 host_callback *p;
2787 {
2788 callback = p;
2789 }
2790
2791 char **
2792 sim_complete_command (SIM_DESC sd, char *text, char *word)
2793 {
2794 return NULL;
2795 }