* interp.c (BUSERROR): New macro.
[deliverable/binutils-gdb.git] / sim / sh / interp.c
CommitLineData
594266fc
SC
1/* Simulator for the Hitachi 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*/
fe031f82 20
631f6b24 21#include <signal.h>
90fe361f 22#include "sysdep.h"
594266fc
SC
23#include <sys/times.h>
24#include <sys/param.h>
631f6b24 25#include "bfd.h"
fe031f82
DE
26#include "remote-sim.h"
27#include "../../newlib/libc/sys/sh/sys/syscall.h"
594266fc
SC
28#define O_RECOMPILE 85
29#define DEFINE_TABLE
4d0be1f5 30/*#define ACE_FAST*/
594266fc
SC
31#define DISASSEMBLER_TABLE
32
33#define SBIT(x) ((x)&sbit)
90fe361f
SC
34#define R0 saved_state.asregs.regs[0]
35#define Rn saved_state.asregs.regs[n]
36#define Rm saved_state.asregs.regs[m]
37#define UR0 (unsigned int)(saved_state.asregs.regs[0])
38#define UR (unsigned int)R
39#define UR (unsigned int)R
40#define SR0 saved_state.asregs.regs[0]
41#define GBR saved_state.asregs.gbr
42#define VBR saved_state.asregs.vbr
43#define MACH saved_state.asregs.mach
44#define MACL saved_state.asregs.macl
45#define M saved_state.asregs.sr.bits.m
46#define Q saved_state.asregs.sr.bits.q
594266fc 47
594266fc
SC
48#define GET_SR() (saved_state.asregs.sr.bits.t = T, saved_state.asregs.sr.word)
49#define SET_SR(x) {saved_state.asregs.sr.word = (x); T =saved_state.asregs.sr.bits.t;}
50
51#define PC pc
52#define C cycles
53
4d0be1f5
SC
54int
55fail ()
fe031f82 56{
4d0be1f5 57 abort ();
fe031f82
DE
58
59}
60
4d0be1f5
SC
61#define BUSERROR(addr, mask) \
62 if (addr & ~mask) { saved_state.asregs.exception = SIGBUS;}
fe031f82
DE
63
64/* Define this to enable register lifetime checking.
4d0be1f5 65 The compiler generates "add #0,rn" insns to mark registers as invalid,
fe031f82
DE
66 the simulator uses this info to call fail if it finds a ref to an invalid
67 register before a def
4d0be1f5 68
fe031f82
DE
69 #define PARANOID
70*/
71
72#ifdef PARANOID
73int valid[16];
74#define CREF(x) if(!valid[x]) fail();
75#define CDEF(x) valid[x] = 1;
76#define UNDEF(x) valid[x] = 0;
77#else
78#define CREF(x)
79#define CDEF(x)
80#define UNDEF(x)
81#endif
82
4d0be1f5
SC
83#ifdef __GNUC__
84#define INLINE inline
90fe361f 85#else
4d0be1f5 86#define INLINE
fe031f82 87#endif
90fe361f 88
4d0be1f5
SC
89/* These variables are at file scope so that functions other than
90 sim_resume can use the fetch/store macros */
90fe361f 91
4d0be1f5 92static int little_endian;
90fe361f 93
4d0be1f5
SC
94#if 1
95static int maskl = ~0;
96static int maskw = ~0;
97#endif
98typedef union
99{
90fe361f 100
4d0be1f5
SC
101 struct
102 {
90fe361f 103
4d0be1f5
SC
104 int regs[16];
105 int pc;
106 int pr;
90fe361f 107
4d0be1f5
SC
108 int gbr;
109 int vbr;
110 int mach;
111 int macl;
112
113
114 union
115 {
116 struct
117 {
118 unsigned int d0:22;
119 unsigned int m:1;
120 unsigned int q:1;
121 unsigned int i:4;
122 unsigned int d1:2;
123 unsigned int s:1;
124 unsigned int t:1;
125 }
126 bits;
127 int word;
128 }
129 sr;
130 int ticks;
131 int stalls;
132 int cycles;
133 int insts;
134
135
136 int prevlock;
137 int thislock;
138 int exception;
139 int msize;
140#define PROFILE_FREQ 1
141#define PROFILE_SHIFT 2
142 int profile;
143 unsigned short *profile_hist;
144 unsigned char *memory;
145
146 }
147 asregs;
148 int asints[28];
149
150} saved_state_type;
151saved_state_type saved_state;
152
153static void INLINE
154wlat_little (memory, x, value, maskl)
155 unsigned char *memory;
156{
157 int v = value;
158 unsigned char *p = memory + ((x) & maskl);
159 BUSERROR(x, maskl);
160 p[3] = v >> 24;
161 p[2] = v >> 16;
162 p[1] = v >> 8;
163 p[0] = v;
164}
165
166static void INLINE
167wwat_little (memory, x, value, maskw)
168 unsigned char *memory;
169{
170 int v = value;
171 unsigned char *p = memory + ((x) & maskw);
172 BUSERROR(x, maskw);
173
174 p[1] = v >> 8;
175 p[0] = v;
176}
177
178
179static void INLINE
180wbat_any (memory, x, value, maskb)
181 unsigned char *memory;
182{
183 unsigned char *p = memory + (x & maskb);
184 if (x > 0x5000000)
185 IOMEM (x, 1, value);
186 BUSERROR(x, maskb);
187
188 p[0] = value;
189}
90fe361f 190
90fe361f
SC
191
192
4d0be1f5
SC
193static void INLINE
194wlat_big (memory, x, value, maskl)
195 unsigned char *memory;
196{
197 int v = value;
198 unsigned char *p = memory + ((x) & maskl);
199 BUSERROR(x, maskl);
200
201 p[0] = v >> 24;
202 p[1] = v >> 16;
203 p[2] = v >> 8;
204 p[3] = v;
205}
206
207static void INLINE
208wwat_big (memory, x, value, maskw)
209 unsigned char *memory;
210{
211 int v = value;
212 unsigned char *p = memory + ((x) & maskw);
213 BUSERROR(x, maskw);
214
215 p[0] = v >> 8;
216 p[1] = v;
217}
218
219
220static void INLINE
221wbat_big (memory, x, value, maskb)
222 unsigned char *memory;
223{
224 unsigned char *p = memory + (x & maskb);
225 BUSERROR(x, maskb);
226
227 if (x > 0x5000000)
228 IOMEM (x, 1, value);
229 p[0] = value;
230}
231
232
233
234/* Read functions */
235static int INLINE
236rlat_little (memory, x, maskl)
237 unsigned char *memory;
238{
239 unsigned char *p = memory + ((x) & maskl);
240 BUSERROR(x, maskl);
241
242 return (p[3] << 24) | (p[2] << 16) | (p[1] << 8) | p[0];
243
244}
245
246static int INLINE
247rwat_little (memory, x, maskw)
248 unsigned char *memory;
249{
250 unsigned char *p = memory + ((x) & maskw);
251 BUSERROR(x, maskw);
252
253 return (p[1] << 8) | p[0];
254}
255
256static int INLINE
257rbat_any (memory, x, maskb)
258 unsigned char *memory;
259{
260 unsigned char *p = memory + ((x) & maskb);
261 BUSERROR(x, maskb);
262
263 return p[0];
264}
265
266static int INLINE
267rlat_big (memory, x, maskl)
268 unsigned char *memory;
269{
270 unsigned char *p = memory + ((x) & maskl);
271 BUSERROR(x, maskl);
272
273 return (p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3];
274
275}
276
277static int INLINE
278rwat_big (memory, x, maskw)
279 unsigned char *memory;
280{
281 unsigned char *p = memory + ((x) & maskw);
282 BUSERROR(x, maskw);
283
284 return (p[0] << 8) | p[1];
285}
286
287
288#define RWAT(x) (little_endian ? rwat_little(memory, x, maskw): rwat_big(memory, x, maskw))
289#define RLAT(x) (little_endian ? rlat_little(memory, x, maskl): rlat_big(memory, x, maskl))
290#define RBAT(x) (rbat_any (memory, x, maskb))
291#define WWAT(x,v) (little_endian ? wwat_little(memory, x, v, maskw): wwat_big(memory, x, v, maskw))
292#define WLAT(x,v) (little_endian ? wlat_little(memory, x, v, maskl): wlat_big(memory, x, v, maskl))
293#define WBAT(x,v) (wbat_any (memory, x, v, maskb))
294
295#define RUWAT(x) (RWAT(x) & 0xffff)
296#define RSWAT(x) ((short)(RWAT(x)))
297#define RSBAT(x) (SEXT(RBAT(x)))
90fe361f
SC
298
299#define SEXT(x) (((x&0xff) ^ (~0x7f))+0x80)
300#define SEXTW(y) ((int)((short)y))
301
302#define SL(TEMPPC) iword= RUWAT(TEMPPC); goto top;
303
304
fe031f82
DE
305int empty[16];
306
90fe361f
SC
307#define L(x) thislock = x;
308#define TL(x) if ((x) == prevlock) stalls++;
309#define TB(x,y) if ((x) == prevlock || (y)==prevlock) stalls++;
fe031f82
DE
310
311#ifdef __GO32__
90fe361f 312int sim_memory_size = 19;
fe031f82
DE
313#else
314int sim_memory_size = 24;
315#endif
316
90fe361f
SC
317static int sim_profile_size = 17;
318static int nsamples;
631f6b24 319
4d0be1f5
SC
320#undef TB
321#define TB(x,y)
594266fc 322
4d0be1f5
SC
323#define SMR1 (0x05FFFEC8) /* Channel 1 serial mode register */
324#define BRR1 (0x05FFFEC9) /* Channel 1 bit rate register */
325#define SCR1 (0x05FFFECA) /* Channel 1 serial control register */
326#define TDR1 (0x05FFFECB) /* Channel 1 transmit data register */
327#define SSR1 (0x05FFFECC) /* Channel 1 serial status register */
328#define RDR1 (0x05FFFECD) /* Channel 1 receive data register */
594266fc 329
4d0be1f5
SC
330#define SCI_RDRF 0x40 /* Recieve data register full */
331#define SCI_TDRE 0x80 /* Transmit data register empty */
594266fc 332
4d0be1f5
SC
333static int
334IOMEM (addr, write, value)
335 int addr;
336 int write;
337 int value;
338{
339 static int io;
340 static char ssr1;
341 int x;
342 static char lastchar;
594266fc 343
4d0be1f5
SC
344 if (write)
345 {
346 switch (addr)
594266fc 347 {
4d0be1f5
SC
348 case TDR1:
349 if (value != '\r')
594266fc 350 {
4d0be1f5
SC
351 putchar (value);
352 fflush (stdout);
594266fc 353 }
4d0be1f5
SC
354 break;
355 }
356 }
357 else
358 {
359 switch (addr)
360 {
361 case RDR1:
362 return getchar ();
594266fc 363 }
594266fc 364 }
594266fc
SC
365}
366
4d0be1f5 367
594266fc 368
594266fc
SC
369static int
370get_now ()
371{
4d0be1f5 372 return time ((long *) 0);
594266fc
SC
373}
374
375static int
376now_persec ()
377{
631f6b24 378 return 1;
90fe361f
SC
379}
380
381
382
383static FILE *profile_file;
384
4d0be1f5
SC
385static void
386swap (memory, n)
387 unsigned char *memory;
90fe361f 388 int n;
fdc506e6 389{
4d0be1f5 390 WLAT (0, n);
90fe361f 391}
4d0be1f5
SC
392static void
393swap16 (memory, n)
394 unsigned char *memory;
90fe361f 395 int n;
fdc506e6 396{
4d0be1f5 397 WWAT (0, n);
594266fc
SC
398}
399
90fe361f 400static void
fdc506e6 401swapout (n)
90fe361f
SC
402 int n;
403{
fdc506e6 404 if (profile_file)
90fe361f
SC
405 {
406 char b[4];
fdc506e6
SC
407 swap (b, n);
408 fwrite (b, 4, 1, profile_file);
90fe361f 409 }
fdc506e6 410}
90fe361f
SC
411
412static void
fdc506e6 413swapout16 (n)
90fe361f
SC
414 int n;
415{
416 char b[4];
fdc506e6
SC
417 swap16 (b, n);
418 fwrite (b, 2, 1, profile_file);
419}
90fe361f
SC
420
421
422/* Turn a pointer in a register into a pointer into real memory. */
423
424static char *
425ptr (x)
426 int x;
427{
fdc506e6 428 return (char *) (x + saved_state.asregs.memory);
90fe361f
SC
429}
430
fe031f82
DE
431
432/* Simulate a monitor trap, put the result into r0 and errno into r1 */
90fe361f 433static void
4d0be1f5 434trap (i, regs, memory, maskl, maskw, little_endian)
90fe361f 435 int i;
594266fc 436 int *regs;
4d0be1f5 437 unsigned char *memory;
594266fc
SC
438{
439 switch (i)
440 {
441 case 1:
442 printf ("%c", regs[0]);
443 break;
444 case 2:
445 saved_state.asregs.exception = SIGQUIT;
446 break;
4d0be1f5
SC
447#if 0
448 case 8:
449 trap8 (ptr (regs[4]));
450 break;
451 case 9:
452 trap9 (ptr (regs[4]));
453 break;
454 case 10:
455 trap10 ();
456 break;
457 case 11:
458 regs[0] = trap11 ();
459 break;
460 case 12:
461 regs[0] = trap12 ();
462 break;
463#endif
90fe361f
SC
464 case 3:
465 {
466 extern int errno;
467 int perrno = errno;
468 errno = 0;
469
470 switch (regs[4])
471 {
4d0be1f5 472
fe031f82 473#ifndef __GO32__
fe031f82 474
4d0be1f5
SC
475 case SYS_fork:
476 regs[0] = fork ();
477 break;
fe031f82 478 case SYS_execve:
4d0be1f5 479 regs[0] = execve (ptr (regs[5]), ptr (regs[6]), ptr (regs[7]));
fe031f82
DE
480 break;
481 case SYS_execv:
4d0be1f5 482 regs[0] = execv (ptr (regs[5]), ptr (regs[6]));
fe031f82
DE
483 break;
484 case SYS_pipe:
485 {
4d0be1f5 486 char *buf;
fe031f82
DE
487 int host_fd[2];
488
4d0be1f5 489 buf = ptr (regs[5]);
fe031f82 490
4d0be1f5 491 regs[0] = pipe (host_fd);
fe031f82 492
4d0be1f5
SC
493 WLAT (buf, host_fd[0]);
494 buf += 4;
495 WLAT (buf, host_fd[1]);
fe031f82
DE
496 }
497 break;
498
4d0be1f5
SC
499 case SYS_wait:
500 regs[0] = wait (ptr (regs[5]));
fe031f82
DE
501 break;
502#endif
4d0be1f5 503
fe031f82
DE
504 case SYS_read:
505 regs[0] = read (regs[5], ptr (regs[6]), regs[7]);
90fe361f 506 break;
fe031f82
DE
507 case SYS_write:
508 regs[0] = write (regs[5], ptr (regs[6]), regs[7]);
90fe361f 509 break;
fe031f82
DE
510 case SYS_lseek:
511 regs[0] = lseek (regs[5], regs[6], regs[7]);
90fe361f 512 break;
fe031f82
DE
513 case SYS_close:
514 regs[0] = close (regs[5]);
90fe361f 515 break;
fe031f82
DE
516 case SYS_open:
517 regs[0] = open (ptr (regs[5]), regs[6]);
90fe361f 518 break;
fe031f82 519 case SYS_exit:
4d0be1f5
SC
520 /* EXIT - caller can look in r5 to work out the
521 reason */
631f6b24 522 saved_state.asregs.exception = SIGQUIT;
631f6b24 523 break;
4d0be1f5
SC
524
525 case SYS_stat: /* added at hmsi */
fe031f82 526 /* stat system call */
4d0be1f5 527 {
fe031f82
DE
528 struct stat host_stat;
529 char *buf;
530
4d0be1f5
SC
531 regs[0] = stat (ptr (regs[5]), &host_stat);
532
533 buf = ptr (regs[6]);
534
535 WWAT (buf, host_stat.st_dev);
536 buf += 2;
537 WWAT (buf, host_stat.st_ino);
538 buf += 2;
539 WLAT (buf, host_stat.st_mode);
540 buf += 4;
541 WWAT (buf, host_stat.st_nlink);
542 buf += 2;
543 WWAT (buf, host_stat.st_uid);
544 buf += 2;
545 WWAT (buf, host_stat.st_gid);
546 buf += 2;
547 WWAT (buf, host_stat.st_rdev);
548 buf += 2;
549 WLAT (buf, host_stat.st_size);
550 buf += 4;
551 WLAT (buf, host_stat.st_atime);
552 buf += 4;
553 WLAT (buf, 0);
554 buf += 4;
555 WLAT (buf, host_stat.st_mtime);
556 buf += 4;
557 WLAT (buf, 0);
558 buf += 4;
559 WLAT (buf, host_stat.st_ctime);
560 buf += 4;
561 WLAT (buf, 0);
562 buf += 4;
563 WLAT (buf, 0);
564 buf += 4;
565 WLAT (buf, 0);
566 buf += 4;
567 }
568 break;
fe031f82 569
4d0be1f5
SC
570 case SYS_chown:
571 regs[0] = chown (ptr (regs[5]), regs[6], regs[7]);
fe031f82
DE
572 break;
573 case SYS_chmod:
4d0be1f5
SC
574 regs[0] = chmod (ptr (regs[5]), regs[6]);
575 break;
576 case SYS_utime:
577 regs[0] = utime (ptr (regs[5]), ptr (regs[6]));
fe031f82 578 break;
90fe361f
SC
579 default:
580 abort ();
581 }
fe031f82 582 regs[1] = errno;
90fe361f
SC
583 errno = perrno;
584 }
585
586 break;
587
4d0be1f5 588 case 0xc3:
594266fc 589 case 255:
631f6b24 590 saved_state.asregs.exception = SIGTRAP;
594266fc
SC
591 break;
592 }
593
594}
595void
596control_c (sig, code, scp, addr)
597 int sig;
598 int code;
599 char *scp;
600 char *addr;
601{
602 saved_state.asregs.exception = SIGINT;
603}
604
605
fdc506e6 606static int
90fe361f 607div1 (R, iRn2, iRn1, T)
594266fc 608 int *R;
90fe361f
SC
609 int iRn1;
610 int iRn2;
594266fc
SC
611 int T;
612{
613 unsigned long tmp0;
614 unsigned char old_q, tmp1;
90fe361f 615
594266fc 616 old_q = Q;
90fe361f
SC
617 Q = (unsigned char) ((0x80000000 & R[iRn1]) != 0);
618 R[iRn1] <<= 1;
619 R[iRn1] |= (unsigned long) T;
620
621 switch (old_q)
594266fc 622 {
fdc506e6 623 case 0:
90fe361f 624 switch (M)
fdc506e6
SC
625 {
626 case 0:
627 tmp0 = R[iRn1];
628 R[iRn1] -= R[iRn2];
629 tmp1 = (R[iRn1] > tmp0);
630 switch (Q)
631 {
632 case 0:
633 Q = tmp1;
634 break;
635 case 1:
636 Q = (unsigned char) (tmp1 == 0);
637 break;
638 }
639 break;
640 case 1:
641 tmp0 = R[iRn1];
642 R[iRn1] += R[iRn2];
643 tmp1 = (R[iRn1] < tmp0);
644 switch (Q)
645 {
646 case 0:
647 Q = (unsigned char) (tmp1 == 0);
648 break;
649 case 1:
650 Q = tmp1;
651 break;
652 }
653 break;
654 }
594266fc
SC
655 break;
656 case 1:
657 switch (M)
658 {
fdc506e6 659 case 0:
90fe361f
SC
660 tmp0 = R[iRn1];
661 R[iRn1] += R[iRn2];
662 tmp1 = (R[iRn1] < tmp0);
663 switch (Q)
664 {
665 case 0:
666 Q = tmp1;
667 break;
668 case 1:
669 Q = (unsigned char) (tmp1 == 0);
fdc506e6 670 break;
90fe361f 671 }
594266fc 672 break;
fdc506e6 673 case 1:
90fe361f
SC
674 tmp0 = R[iRn1];
675 R[iRn1] -= R[iRn2];
676 tmp1 = (R[iRn1] > tmp0);
677 switch (Q)
678 {
679 case 0:
680 Q = (unsigned char) (tmp1 == 0);
681 break;
682 case 1:
683 Q = tmp1;
684 break;
685 }
594266fc
SC
686 break;
687 }
688 break;
90fe361f
SC
689 }
690 T = (Q == M);
691 return T;
692}
693
90fe361f 694
4d0be1f5 695static void
fdc506e6
SC
696dmul (sign, rm, rn)
697 int sign;
698 unsigned int rm;
699 unsigned int rn;
700{
701 unsigned long RnL, RnH;
702 unsigned long RmL, RmH;
703 unsigned long temp0, temp1, temp2, temp3;
704 unsigned long Res2, Res1, Res0;
90fe361f 705
594266fc 706
fdc506e6 707 if (!sign)
90fe361f 708 {
594266fc 709
fdc506e6
SC
710 RnL = rn & 0xffff;
711 RnH = (rn >> 16) & 0xffff;
712 RmL = rm & 0xffff;
713 RmH = (rm >> 16) & 0xffff;
714 temp0 = RmL * RnL;
715 temp1 = RmH * RnL;
716 temp2 = RmL * RnH;
717 temp3 = RmH * RnH;
718 Res2 = 0;
719 Res1 = temp1 + temp2;
720 if (Res1 < temp1)
721 Res2 += 0x00010000;
722 temp1 = (Res1 << 16) & 0xffff0000;
723 Res0 = temp0 + temp1;
724 if (Res0 < temp0)
725 Res2 += 1;
726 Res2 += ((Res1 >> 16) & 0xffff) + temp3;
727 MACH = Res2;
728 MACL = Res0;
594266fc 729
90fe361f 730 }
fdc506e6
SC
731
732 else
90fe361f 733 {
4d0be1f5
SC
734#ifdef __GNUC__
735 long long res;
736 long long a = rn;
737 long long b = rm;
738 res = a * b;
739 MACH = res >> 32;
740 MACL = res & 0xffffffff;
741#else
fdc506e6 742 abort ();
4d0be1f5 743#endif
90fe361f 744 }
fdc506e6 745
594266fc
SC
746}
747
fdc506e6 748
90fe361f
SC
749/* Set the memory size to the power of two provided. */
750
751void
752sim_size (power)
753 int power;
754
755{
756 saved_state.asregs.msize = 1 << power;
757
fdc506e6 758 sim_memory_size = power;
90fe361f
SC
759
760
761 if (saved_state.asregs.memory)
762 {
763 free (saved_state.asregs.memory);
764 }
765
766 saved_state.asregs.memory =
767 (unsigned char *) calloc (64, saved_state.asregs.msize / 64);
768
769 if (!saved_state.asregs.memory)
770 {
771 fprintf (stderr,
4d0be1f5 772 "Not enough VM for simulation of %d bytes of RAM\n",
90fe361f
SC
773 saved_state.asregs.msize);
774
775 saved_state.asregs.msize = 1;
fdc506e6 776 saved_state.asregs.memory = (unsigned char *) calloc (1, 1);
90fe361f
SC
777 }
778}
779
780
4d0be1f5
SC
781extern int target_byte_order;
782
783static void
784set_static_little_endian(x)
785int x;
786{
787 little_endian = x;
788}
90fe361f 789
fdc506e6 790static
90fe361f
SC
791void
792init_pointers ()
793{
4d0be1f5
SC
794 register int little_endian = target_byte_order == 1234;
795 set_static_little_endian (little_endian);
90fe361f
SC
796 if (saved_state.asregs.msize != 1 << sim_memory_size)
797 {
798 sim_size (sim_memory_size);
799 }
800
801 if (saved_state.asregs.profile && !profile_file)
802 {
fdc506e6 803 profile_file = fopen ("gmon.out", "wb");
90fe361f 804 /* Seek to where to put the call arc data */
fdc506e6 805 nsamples = (1 << sim_profile_size);
90fe361f 806
fdc506e6
SC
807 fseek (profile_file, nsamples * 2 + 12, 0);
808
809 if (!profile_file)
90fe361f 810 {
fdc506e6 811 fprintf (stderr, "Can't open gmon.out\n");
90fe361f 812 }
fdc506e6 813 else
90fe361f
SC
814 {
815 saved_state.asregs.profile_hist =
fdc506e6 816 (unsigned short *) calloc (64, (nsamples * sizeof (short) / 64));
90fe361f
SC
817 }
818 }
819}
820
821static void
fdc506e6 822dump_profile ()
90fe361f 823{
fdc506e6 824 unsigned int minpc;
90fe361f
SC
825 unsigned int maxpc;
826 unsigned short *p;
827
828 int thisshift;
fdc506e6 829
90fe361f
SC
830 unsigned short *first;
831
832 int i;
833 p = saved_state.asregs.profile_hist;
fdc506e6
SC
834 minpc = 0;
835 maxpc = (1 << sim_profile_size);
836
837 fseek (profile_file, 0L, 0);
838 swapout (minpc << PROFILE_SHIFT);
839 swapout (maxpc << PROFILE_SHIFT);
840 swapout (nsamples * 2 + 12);
841 for (i = 0; i < nsamples; i++)
842 swapout16 (saved_state.asregs.profile_hist[i]);
843
90fe361f
SC
844}
845
4d0be1f5 846static int
fdc506e6 847gotcall (from, to)
90fe361f
SC
848 int from;
849 int to;
850{
fdc506e6
SC
851 swapout (from);
852 swapout (to);
853 swapout (1);
90fe361f
SC
854}
855
856#define MMASKB ((saved_state.asregs.msize -1) & ~0)
fe031f82 857
4d0be1f5 858
90fe361f 859void
fe031f82
DE
860sim_resume (step, siggnal)
861 int step, siggnal;
594266fc 862{
fdc506e6 863 register unsigned int pc;
90fe361f
SC
864 register int cycles = 0;
865 register int stalls = 0;
866 register int insts = 0;
867 register int prevlock;
fdc506e6
SC
868 register int thislock;
869 register unsigned int doprofile;
4d0be1f5
SC
870#ifdef __GO32__
871 register int pollcount = 0;
872#endif
873 register int little_endian = target_byte_order == 1234;
874
90fe361f 875
594266fc
SC
876 int tick_start = get_now ();
877 void (*prev) ();
878 extern unsigned char sh_jump_table0[];
879
880 register unsigned char *jump_table = sh_jump_table0;
881
882 register int *R = &(saved_state.asregs.regs[0]);
883 register int T;
884 register int PR;
885
90fe361f
SC
886 register int maskb = ((saved_state.asregs.msize - 1) & ~0);
887 register int maskw = ((saved_state.asregs.msize - 1) & ~1);
888 register int maskl = ((saved_state.asregs.msize - 1) & ~3);
4d0be1f5 889 register unsigned char *memory;
90fe361f
SC
890 register unsigned int sbit = (1 << 31);
891
594266fc
SC
892 prev = signal (SIGINT, control_c);
893
fdc506e6
SC
894 init_pointers ();
895
631f6b24
DE
896 memory = saved_state.asregs.memory;
897
594266fc
SC
898 if (step)
899 {
900 saved_state.asregs.exception = SIGTRAP;
901 }
902 else
903 {
904 saved_state.asregs.exception = 0;
905 }
906
907 pc = saved_state.asregs.pc;
908 PR = saved_state.asregs.pr;
909 T = saved_state.asregs.sr.bits.t;
90fe361f
SC
910 prevlock = saved_state.asregs.prevlock;
911 thislock = saved_state.asregs.thislock;
912 doprofile = saved_state.asregs.profile;
913
914 /* If profiling not enabled, disable it by asking for
915 profiles infrequently. */
fdc506e6 916 if (doprofile == 0)
90fe361f 917 doprofile = ~0;
fdc506e6 918
594266fc
SC
919 do
920 {
fdc506e6
SC
921 register unsigned int iword = RUWAT (pc);
922 register unsigned int ult;
4d0be1f5 923#ifndef ACE_FAST
594266fc 924 insts++;
4d0be1f5 925#endif
594266fc
SC
926 top:
927
928#include "code.c"
929
90fe361f 930
594266fc 931 pc += 2;
4d0be1f5
SC
932
933#ifdef __GO32__
934 pollcount++;
935 if (pollcount > 1000)
936 {
937 pollcount = 0;
938 if (kbhit()) {
939 int k = getkey();
940 if (k == 1)
941 saved_state.asregs.exception = SIGINT;
942
943 }
944 }
945#endif
946
947#ifndef ACE_FAST
90fe361f
SC
948 prevlock = thislock;
949 thislock = 30;
594266fc 950 cycles++;
90fe361f
SC
951
952 if (cycles >= doprofile)
953 {
4d0be1f5 954
90fe361f
SC
955 saved_state.asregs.cycles += doprofile;
956 cycles -= doprofile;
fdc506e6 957 if (saved_state.asregs.profile_hist)
90fe361f
SC
958 {
959 int n = pc >> PROFILE_SHIFT;
fdc506e6 960 if (n < nsamples)
90fe361f
SC
961 {
962 int i = saved_state.asregs.profile_hist[n];
963 if (i < 65000)
fdc506e6 964 saved_state.asregs.profile_hist[n] = i + 1;
90fe361f 965 }
fdc506e6 966
90fe361f
SC
967 }
968 }
4d0be1f5 969#endif
594266fc
SC
970 }
971 while (!saved_state.asregs.exception);
972
4d0be1f5
SC
973 if (saved_state.asregs.exception == SIGILL
974 || saved_state.asregs.exception == SIGBUS
975 || (saved_state.asregs.exception == SIGTRAP && !step))
594266fc 976 {
90fe361f 977 pc -= 2;
594266fc 978 }
90fe361f 979
594266fc
SC
980 saved_state.asregs.ticks += get_now () - tick_start;
981 saved_state.asregs.cycles += cycles;
90fe361f 982 saved_state.asregs.stalls += stalls;
594266fc
SC
983 saved_state.asregs.insts += insts;
984 saved_state.asregs.pc = pc;
985 saved_state.asregs.sr.bits.t = T;
986 saved_state.asregs.pr = PR;
987
90fe361f
SC
988 saved_state.asregs.prevlock = prevlock;
989 saved_state.asregs.thislock = thislock;
990
991
992 if (profile_file)
993 {
fdc506e6 994 dump_profile ();
90fe361f 995 }
fdc506e6 996
594266fc
SC
997 signal (SIGINT, prev);
998}
999
1000
1001
90fe361f 1002
631f6b24 1003int
594266fc 1004sim_write (addr, buffer, size)
fe031f82 1005 SIM_ADDR addr;
594266fc
SC
1006 unsigned char *buffer;
1007 int size;
1008{
1009 int i;
1010 init_pointers ();
1011
1012 for (i = 0; i < size; i++)
1013 {
1014 saved_state.asregs.memory[MMASKB & (addr + i)] = buffer[i];
1015 }
fe031f82 1016 return size;
594266fc
SC
1017}
1018
631f6b24 1019int
594266fc 1020sim_read (addr, buffer, size)
fe031f82
DE
1021 SIM_ADDR addr;
1022 unsigned char *buffer;
594266fc
SC
1023 int size;
1024{
1025 int i;
1026
1027 init_pointers ();
1028
1029 for (i = 0; i < size; i++)
1030 {
1031 buffer[i] = saved_state.asregs.memory[MMASKB & (addr + i)];
1032 }
fe031f82 1033 return size;
594266fc
SC
1034}
1035
1036
90fe361f 1037void
4d0be1f5 1038sim_store_register (rn, memory)
594266fc 1039 int rn;
4d0be1f5 1040 unsigned char *memory;
594266fc 1041{
4d0be1f5
SC
1042 init_pointers();
1043 saved_state.asregs.regs[rn]=RLAT(0);
594266fc
SC
1044}
1045
90fe361f 1046void
4d0be1f5 1047sim_fetch_register (rn, memory)
594266fc 1048 int rn;
4d0be1f5 1049 unsigned char *memory;
594266fc 1050{
4d0be1f5
SC
1051 init_pointers();
1052 WLAT (0, saved_state.asregs.regs[rn]);
594266fc
SC
1053}
1054
90fe361f 1055
594266fc
SC
1056int
1057sim_trace ()
1058{
594266fc 1059 return 0;
594266fc
SC
1060}
1061
fe031f82
DE
1062void
1063sim_stop_reason (reason, sigrc)
1064 enum sim_stop *reason;
631f6b24 1065 int *sigrc;
594266fc 1066{
fe031f82 1067 *reason = sim_stopped;
631f6b24 1068 *sigrc = saved_state.asregs.exception;
594266fc
SC
1069}
1070
1071
90fe361f 1072void
fe031f82
DE
1073sim_info (verbose)
1074 int verbose;
594266fc
SC
1075{
1076 double timetaken = (double) saved_state.asregs.ticks / (double) now_persec ();
90fe361f
SC
1077 double virttime = saved_state.asregs.cycles / 36.0e6;
1078
fe031f82
DE
1079 printf_filtered ("\n\n# instructions executed %10d\n", saved_state.asregs.insts);
1080 printf_filtered ("# cycles %10d\n", saved_state.asregs.cycles);
1081 printf_filtered ("# pipeline stalls %10d\n", saved_state.asregs.stalls);
1082 printf_filtered ("# real time taken %10.4f\n", timetaken);
1083 printf_filtered ("# virtual time taken %10.4f\n", virttime);
1084 printf_filtered ("# profiling size %10d\n", sim_profile_size);
1085 printf_filtered ("# profiling frequency %10d\n", saved_state.asregs.profile);
1086 printf_filtered ("# profile maxpc %10x\n", (1 << sim_profile_size) << PROFILE_SHIFT);
fdc506e6
SC
1087
1088 if (timetaken != 0)
90fe361f 1089 {
fe031f82
DE
1090 printf_filtered ("# cycles/second %10d\n", (int) (saved_state.asregs.cycles / timetaken));
1091 printf_filtered ("# simulation ratio %10.4f\n", virttime / timetaken);
90fe361f 1092 }
594266fc
SC
1093}
1094
90fe361f
SC
1095
1096void
fdc506e6 1097sim_set_profile (n)
631f6b24 1098 int n;
594266fc 1099{
90fe361f
SC
1100 saved_state.asregs.profile = n;
1101}
1102
1103void
fdc506e6 1104sim_set_profile_size (n)
631f6b24 1105 int n;
90fe361f
SC
1106{
1107 sim_profile_size = n;
594266fc 1108}
631f6b24
DE
1109
1110
1111void
fe031f82
DE
1112sim_open (name)
1113 char *name;
631f6b24 1114{
fe031f82
DE
1115 /* nothing to do */
1116}
631f6b24 1117
fe031f82
DE
1118void
1119sim_close (quitting)
1120 int quitting;
1121{
1122 /* nothing to do */
631f6b24
DE
1123}
1124
1125int
fe031f82
DE
1126sim_load (prog, from_tty)
1127 char *prog;
1128 int from_tty;
631f6b24 1129{
fe031f82
DE
1130 /* Return nonzero so GDB will handle it. */
1131 return 1;
631f6b24 1132}
fe031f82
DE
1133
1134void
1135sim_create_inferior (start_address, argv, env)
1136 SIM_ADDR start_address;
1137 char **argv;
1138 char **env;
631f6b24 1139{
fe031f82 1140 saved_state.asregs.pc = start_address;
631f6b24
DE
1141}
1142
fe031f82
DE
1143void
1144sim_kill ()
1145{
1146 /* nothing to do */
1147}
This page took 0.134202 seconds and 4 git commands to generate.