OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [insight/] [sim/] [z8k/] [support.c] - Blame information for rev 1775

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 578 markom
/* support routines for interpreted instructions
2
   Copyright (C) 1992, 1993 Free Software Foundation, Inc.
3
 
4
This file is part of Z8KSIM
5
 
6
Z8KSIM is free software; you can redistribute it and/or modify
7
it under the terms of the GNU General Public License as published by
8
the Free Software Foundation; either version 2, or (at your option)
9
any later version.
10
 
11
Z8KSIM is distributed in the hope that it will be useful,
12
but WITHOUT ANY WARRANTY; without even the implied warranty of
13
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
GNU General Public License for more details.
15
 
16
You should have received a copy of the GNU General Public License
17
along with Z8KZIM; if not, write to the Free Software
18
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
19
 
20
#include "config.h"
21
 
22
#include <ansidecl.h>
23
#include <signal.h>
24
#include <errno.h>
25
 
26
#include "tm.h"
27
#include "sim.h"
28
#include "mem.h"
29
#include <stdio.h>
30
#ifdef HAVE_TIME_H
31
#include <time.h>
32
#endif
33
#ifdef HAVE_SYS_TIMES_H
34
#include <sys/times.h>
35
#endif
36
#include <sys/types.h>
37
#include <sys/stat.h>
38
#include <sys/param.h>
39
#include "callback.h"
40
#include "remote-sim.h"
41
#include "syscall.h"
42
 
43
static int get_now PARAMS ((void));
44
static int now_persec PARAMS ((void));
45
static int put_long PARAMS ((sim_state_type * context, int ptr, int value));
46
static int put_short PARAMS ((sim_state_type * context, int ptr, int value));
47
 
48
int sim_z8001_mode;
49
 
50
static int
51
get_now ()
52
{
53
#ifdef HAVE_SYS_TIMES_H
54
  struct tms b;
55
 
56
  times (&b);
57
  return b.tms_utime + b.tms_stime;
58
#else
59
  return time (0);
60
#endif
61
}
62
 
63
static int
64
now_persec ()
65
{
66
  return 50;
67
}
68
 
69
 
70
/* #define LOG /* define this to print instruction use counts */
71
 
72
#ifdef __GNUC__
73
#define INLINE __inline__
74
#include "inlines.h"
75
#else
76
#include "inlines.h"
77
#endif
78
 
79
/* This holds the entire cpu context */
80
static sim_state_type the_state;
81
 
82
int
83
fail (context, dummy)
84
     sim_state_type *context;
85
     int dummy;
86
{
87
  context->exception = SIM_BAD_INST;
88
  return 1;
89
}
90
 
91
void
92
sfop_bad1 (context)
93
     sim_state_type *context;
94
{
95
  context->exception
96
    = SIM_BAD_INST;
97
}
98
 
99
void
100
bfop_bad1 (context)
101
     sim_state_type *context;
102
{
103
  context->exception
104
    = SIM_BAD_INST;
105
}
106
 
107
void
108
fop_bad (context)
109
     sim_state_type *context;
110
{
111
  context->exception =
112
    SIM_BAD_INST;
113
}
114
 
115
/* Table of bit counts for all byte values */
116
 
117
char the_parity[256] =
118
{
119
  0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4, 1, 2, 2, 3, 2, 3, 3,
120
  4, 2, 3, 3, 4, 3, 4, 4, 5, 1, 2, 2, 3, 2, 3, 3, 4, 2, 3, 3, 4, 3, 4,
121
  4, 5, 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, 1, 2, 2, 3, 2,
122
  3, 3, 4, 2, 3, 3, 4, 3, 4, 4, 5, 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5,
123
  4, 5, 5, 6, 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, 3, 4, 4,
124
  5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7, 1, 2, 2, 3, 2, 3, 3, 4, 2, 3,
125
  3, 4, 3, 4, 4, 5, 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, 2,
126
  3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5, 6, 3, 4, 4, 5, 4, 5, 5, 6,
127
  4, 5, 5, 6, 5, 6, 6, 7, 2, 3, 3, 4, 3, 4, 4, 5, 3, 4, 4, 5, 4, 5, 5,
128
  6, 3, 4, 4, 5, 4, 5, 5, 6, 4, 5, 5, 6, 5, 6, 6, 7, 3, 4, 4, 5, 4, 5,
129
  5, 6, 4, 5, 5, 6, 5, 6, 6, 7, 4, 5, 5, 6, 5, 6, 6, 7, 5, 6, 6, 7, 6,
130
  7, 7, 8};
131
 
132
 
133
int read ();
134
int write ();
135
int open ();
136
int close ();
137
int open ();
138
int close ();
139
 
140
int link ();
141
int fstat ();
142
 
143
static int
144
put_short (context, ptr, value)
145
     sim_state_type *context;
146
     int ptr;
147
     int value;
148
{
149
  put_word_mem_da (context, ptr, value);
150
  return ptr + 2;
151
}
152
 
153
static int
154
put_long (context, ptr, value)
155
     sim_state_type *context;
156
     int
157
       ptr;
158
     int value;
159
{
160
  put_long_mem_da (context, ptr, value);
161
  return ptr + 4;
162
}
163
 
164
#define aptr(x) ((sitoptr(x)) + (char *)(context->memory))
165
 
166
static int args[3];
167
static int arg_index;           /* Translate a z8k system call into a host system call */
168
void
169
support_call (context, sc)
170
     sim_state_type *context;
171
     int sc;
172
{
173
  extern int errno;
174
  int ret;
175
  int retnext = 0;
176
  int fd;
177
 
178
  int olderrno = errno;
179
  errno = 0;
180
  switch (sc)
181
    {
182
    case SYS_ARG:
183
      args[arg_index++] = context->regs[0].word << 16 | context->regs[1].word;
184
      break;
185
    case SYS_exit:
186
      context->exception = SIM_DONE;
187
      ret = args[0];
188
      arg_index = 0;
189
      break;
190
    case SYS_close:
191
      ret = close ((int) (args[0]));
192
      arg_index = 0;
193
      break;
194
    case SYS_creat:
195
      ret = creat (aptr (args[0]), args[1]);
196
      arg_index = 0;
197
      break;
198
    case SYS_isatty:
199
      ret = isatty (args[0]);
200
      arg_index = 0;
201
      break;
202
    case SYS_open:
203
      ret = open (aptr (args[0]), args[1], args[2]);
204
      arg_index = 0;
205
      break;
206
    case SYS_lseek:
207
      ret = lseek (args[0], (off_t) args[1], args[2]);
208
      arg_index = 0;
209
      break;
210
    case SYS_read:
211
      ret = read (args[0], aptr (args[1]), args[2]);
212
      arg_index = 0;
213
      break;
214
    case SYS_write:
215
      ret = write (args[0],aptr (args[1]), args[2]);
216
      arg_index = 0;
217
      break;
218
    case SYS_time:
219
      {
220
        int dst = args[0];
221
 
222
        ret = time (0);
223
        if (dst)
224
          {
225
            put_long_mem_da (context,
226
                             sitoptr (dst), ret);
227
          }
228
        retnext = ret;
229
        ret = retnext >> 16;
230
        arg_index = 0;
231
      }
232
      break;
233
    case SYS_fstat:
234
      {
235
        int buf;
236
        struct stat host_stat;
237
        fd = args[0];
238
        buf = sitoptr (args[1]);
239
        ret = fstat (fd, &host_stat);
240
        buf = put_short (context, buf, host_stat.st_dev);
241
        buf = put_short (context, buf, host_stat.st_ino);
242
        /* FIXME: Isn't mode_t 4 bytes?  */
243
        buf = put_short (context, buf, host_stat.st_mode);
244
        buf = put_short (context, buf, host_stat.st_nlink);
245
        buf = put_short (context, buf, host_stat.st_uid);
246
        buf = put_short (context, buf, host_stat.st_uid);
247
        buf = put_short (context, buf, host_stat.st_rdev);
248
        buf = put_long (context, buf, host_stat.st_size);
249
        buf = put_long (context, buf, host_stat.st_atime);
250
        arg_index = 0;
251
      } break;
252
    default:
253
    case SYS_link:
254
      context->exception = SIM_BAD_SYSCALL;
255
      arg_index = 0;
256
      break;
257
    }
258
  context->regs[2].word = ret;
259
  context->regs[3].word = retnext;
260
  context->regs[5].word = errno;
261
 
262
 
263
  /* support for the stdcall calling convention */
264
  context->regs[6].word = retnext;
265
  context->regs[7].word = ret;
266
 
267
  errno = olderrno;
268
}
269
 
270
#undef get_word_mem_da
271
 
272
int
273
get_word_mem_da (context, addr)
274
     sim_state_type *context;
275
     int addr;
276
{
277
  return (get_byte_mem_da (context, addr) << 8) | (get_byte_mem_da (context, addr + 1));
278
 
279
}
280
 
281
#undef get_word_reg
282
int
283
get_word_reg (context, reg) sim_state_type
284
* context;
285
     int reg;
286
{
287
  return context->regs[reg].word;
288
}
289
 
290
#ifdef LOG
291
int log[64 * 1024];
292
 
293
#endif
294
 
295
void
296
tm_store_register (regno, value)
297
     int regno;
298
     int value;
299
{
300
  switch
301
    (regno)
302
    {
303
    case REG_PC:
304
      the_state.sometimes_pc = value;
305
      break;
306
 
307
    default:
308
      put_word_reg (&the_state, regno, value);
309
    }
310
}
311
 
312
void
313
swap_long (buf, val)
314
     char *buf;
315
     int val;
316
{
317
  buf[0] = val >> 24;
318
  buf[1] = val >> 16;
319
  buf[2] = val >> 8;
320
  buf[3] = val >> 0;
321
}
322
 
323
void
324
swap_word (buf, val)
325
     char *buf;
326
     int val;
327
{
328
  buf[0] = val >> 8;
329
  buf[1] = val >> 0;
330
}
331
 
332
void
333
tm_fetch_register (regno, buf)
334
     int regno;
335
     char *buf;
336
{
337
  switch
338
    (regno)
339
    {
340
    case REG_CYCLES:
341
      swap_long (buf, the_state.cycles);
342
      break;
343
    case REG_INSTS:
344
      swap_long (buf, the_state.insts);
345
      break;
346
      case
347
    REG_TIME:
348
      swap_long (buf, the_state.ticks);
349
      break;
350
    case REG_PC:
351
      swap_long (buf, the_state.sometimes_pc);
352
      break;
353
    case REG_SP:
354
      {
355
        if (sim_z8001_mode)
356
          {
357
            swap_long (buf, get_long_reg (&the_state, 14));
358
          }
359
        else
360
          {
361
            swap_long (buf, get_word_reg (&the_state, 15));
362
          }
363
      }
364
      break;
365
      case
366
    REG_FP:
367
      {
368
        if (sim_z8001_mode)
369
          {
370
            swap_long (buf, get_long_reg
371
                       (&the_state, 10));
372
          }
373
        else
374
          {
375
            swap_long (buf,
376
                       get_word_reg (&the_state, 10));
377
          }
378
      }
379
      break;
380
    default:
381
      {
382
        swap_word (buf,
383
                   get_word_reg (&the_state, regno));
384
      }
385
    }
386
}
387
 
388
void
389
tm_resume (step)
390
     int step;
391
{
392
  int now = get_now ();
393
  struct op_info
394
   *p;
395
  int word;
396
  int pc;
397
  extern int (*(sfop_table[])) ();
398
  extern int (*(bfop_table[])) ();
399
  int (*((*table))) ();
400
  sim_state_type *context = &the_state;
401
 
402
  if (step)
403
    {
404
      context->exception = SIM_SINGLE_STEP;
405
    }
406
  else
407
    {
408
      context->exception = 0;
409
    }
410
 
411
  pc = context->sometimes_pc;
412
  if (sim_z8001_mode)
413
    {
414
      table = bfop_table;
415
      pc = MAP_PHYSICAL_TO_LOGICAL (pc);
416
    }
417
  else
418
    {
419
      table = sfop_table;
420
    }
421
 
422
 
423
  do
424
    {
425
      word = get_word_mem_da (context, pc);
426
      p = op_info_table + word;
427
 
428
#ifdef LOG
429
      log[word]++;
430
#endif
431
      pc = table[p->exec] (context, pc, word);
432
      context->insts++;
433
 
434
    }
435
  while (!context->exception);
436
 
437
 
438
 
439
  context->sometimes_pc = MAP_LOGICAL_TO_PHYSICAL (pc);
440
  context->ticks += get_now () - now;
441
}
442
 
443
int
444
tm_signal ()
445
{
446
  return the_state.exception;
447
}
448
 
449
void
450
tm_info_print (x)
451
     sim_state_type *x;
452
{
453
  double timetaken = (double) x->ticks / (double) now_persec ();
454
  double virttime = x->cycles / 4.0e6;
455
 
456
  printf ("instructions executed            : %9d\n", x->insts);
457
  printf ("cycles counted                   : %9d \n", x->cycles);
458
  printf ("cycles / inst                    : %9.1f \n", (double) x->cycles / (double) x->insts);
459
  printf ("virtual time taked (at 4 Mhz)    : %9.1f \n", virttime);
460
  printf ("real time taken                  : %9.1f \n", timetaken);
461
 
462
  if (timetaken)
463
    {
464
      printf ("virtual instructions per second  : %9.1f\n", x->insts / timetaken);
465
      printf ("emulation speed                  : %9.1f%%\n", virttime / timetaken * 100.0);
466
    }
467
#ifdef LOG
468
  {
469
    extern int quick[];
470
 
471
    for (i = 0; quick[i]; i++)
472
      {
473
        log[quick[i]] += 100000;
474
      }
475
  }
476
 
477
  for (i = 0; i < 64 * 1024; i++)
478
    {
479
      if (log[i])
480
        {
481
          printf ("                     /*%7d*/ 0x%x,\n", log[i], i);
482
        }
483
    }
484
#endif
485
 
486
}
487
 
488
int
489
sim_trace (sd)
490
     SIM_DESC sd;
491
{
492
  int i;
493
  char buffer[10];
494
  int r;
495
 
496
  printf ("\n");
497
  for (r = 0; r < 16; r++)
498
    {
499
      int m;
500
 
501
      printf ("r%2d", r);
502
      printf ("=%04x ", get_word_reg (&the_state,
503
                                      r));
504
      for (m = -4; m < 8; m++)
505
        {
506
          if (m == 0)
507
            printf (">");
508
          printf ("%04x ",
509
                  get_word_mem_da (&the_state, (0xfffe & get_word_reg (&the_state, r)) + m * 2));
510
        }
511
      printf ("\n");
512
    }
513
 
514
  printf ("\n");
515
  printf ("%9d %9d %08x ", the_state.cycles,
516
          the_state.insts, the_state.sometimes_pc);
517
 
518
  for (i = 0; i < 6; i++)
519
    {
520
      buffer[i] = get_byte_mem_da (&the_state,
521
                                   the_state.sometimes_pc + i);
522
    }
523
 
524
  print_insn_z8001 (the_state.sometimes_pc, buffer, stdout);
525
  printf
526
    ("\n");
527
  tm_resume (1);
528
  if (the_state.exception != SIM_SINGLE_STEP)
529
    return 1;
530
  return 0;
531
}
532
 
533
void
534
tm_state (x)
535
     sim_state_type *x;
536
{
537
  *x = the_state;
538
}
539
 
540
void
541
tm_exception (x)
542
     int x;
543
{
544
  the_state.exception = x;
545
}
546
 
547
int
548
tm_read_byte (x)
549
     int x;
550
{
551
  x &= 0x3f00ffff;
552
  return sim_read_byte (&the_state, x);
553
}
554
 
555
void
556
tm_write_byte (x, y)
557
     int x, y;
558
{
559
  x &= 0x3f00ffff;
560
  sim_write_byte (&the_state, x, y);
561
}
562
 
563
#define SIGN(x) ((x) & MASK)
564
normal_flags_32(context,d,sa,sb,sub)
565
sim_state_type *context;
566
unsigned int d;
567
unsigned int sa;
568
unsigned int sb;
569
unsigned int sub;
570
{
571
#undef MASK
572
#define MASK (1<<31)
573
  context->broken_flags = 0;
574
  if (sub)
575
    PSW_CARRY = sa < sb;
576
  else
577
    PSW_CARRY = d < sa;
578
  if (sub)
579
    PSW_OVERFLOW = (SIGN(sa) != SIGN(sb)) && (SIGN(d) == SIGN(sb));
580
  else
581
    PSW_OVERFLOW = (SIGN(sa) == SIGN(sb)) && (SIGN(d) != SIGN(sb));
582
 
583
  PSW_SIGN = ((int)d) <0;
584
  PSW_ZERO = d == 0;
585
}
586
 
587
normal_flags_16(context,d,sal,sbl,sub)
588
sim_state_type *context;
589
unsigned  int d;
590
unsigned  int sal;
591
unsigned  int sbl;
592
unsigned short int sub;
593
{
594
  unsigned short sa = sal;
595
  unsigned short sb = sbl;
596
#undef MASK
597
#define MASK (1<<15)
598
  context->broken_flags = 0;
599
  if (sub)
600
    PSW_CARRY = sal < sbl;
601
  else
602
    PSW_CARRY = (d & 0x10000) != 0;
603
 
604
  if (sub)
605
    PSW_OVERFLOW = (SIGN(sa) != SIGN(sb)) && (SIGN(d) == SIGN(sb));
606
  else
607
    PSW_OVERFLOW = (SIGN(sa) == SIGN(sb)) && (SIGN(d) != SIGN(sb));
608
 
609
  PSW_SIGN = ((short int)d) <0;
610
  PSW_ZERO = ((short)d) == 0;
611
}
612
 
613
normal_flags_8(context,d,sa,sb,sub)
614
sim_state_type *context;
615
unsigned char d;
616
unsigned char sa;
617
unsigned char sb;
618
unsigned char sub;
619
{
620
#undef MASK
621
#define MASK (1<<7)
622
  context->broken_flags = 0;
623
  if (sub)
624
    PSW_CARRY = sa < sb;
625
  else
626
    PSW_CARRY = d < sa;
627
  if (sub)
628
    PSW_OVERFLOW = (SIGN(sa) != SIGN(sb)) && (SIGN(d) == SIGN(sb));
629
  else
630
    PSW_OVERFLOW = (SIGN(sa) == SIGN(sb)) && (SIGN(d) != SIGN(sb));
631
  PSW_SIGN = ((char)d) <0;
632
  PSW_ZERO = d == 0;
633
}
634
 
635
 
636
static int
637
is_cond_true (context, c)
638
     sim_state_type *context;
639
     int c;
640
{
641
  switch (c)
642
    {
643
    case T:
644
      return 1;
645
    case F:
646
      return 0;                  /* F */
647
    case LE:
648
      return (PSW_ZERO | (PSW_SIGN ^ PSW_OVERFLOW)) & 1;        /*LE */
649
    case GT:
650
      return (~(PSW_ZERO | (PSW_SIGN ^ PSW_OVERFLOW))) & 1;     /*GT */
651
    case 0x5:
652
      return (PSW_SIGN & 1);    /* sign */
653
    case 0xd:
654
      return (~(PSW_SIGN)) & 1; /* not sign */
655
    case 0x3:
656
      return ((PSW_CARRY | PSW_ZERO) & 1);      /* ule*/
657
    case UGT:
658
      return ((~(PSW_CARRY | PSW_ZERO)) & 1);   /* ugt */
659
    case 0x4:
660
      return (PSW_OVERFLOW & 1);/* overflow */
661
    case 0xc:
662
      return (~(PSW_OVERFLOW)) & 1;     /* not overflow */
663
    case LT:
664
      return (PSW_SIGN ^ PSW_OVERFLOW) & 1;     /* LT */
665
    case GE:
666
      return (~(PSW_SIGN ^ PSW_OVERFLOW)) & 1;  /* GE */
667
    case EQ:
668
      return (PSW_ZERO) & 1;    /* zero */
669
    case NE:
670
      return ((~PSW_ZERO) & 1); /* not zero */
671
    case 0x7:
672
      return (PSW_CARRY) & 1;   /* carry */
673
    case 0xf:
674
      return (~PSW_CARRY) & 1;  /* not carry */
675
    default:
676
      abort ();
677
    }
678
}
679
 
680
int
681
COND (context, c)
682
     sim_state_type *context;
683
     int c;
684
{
685
  if (c == 8)
686
    return 1;
687
 
688
  /* We can calculate what the flags would have been by
689
     looking at the src and dst and size of the operation */
690
 
691
  if (context->broken_flags)
692
    {
693
      int slow = 0;
694
      int size;
695
      int dst;
696
      int srca;
697
      int srcb;
698
      int mask;
699
      int ans;
700
 
701
      /* see if we can short-cut the nasty flag calcs */
702
 
703
      switch (size = context->size)
704
        {
705
         default:
706
          abort();
707
          return 0;
708
        case 8:
709
          srca = (char) (context->srca);
710
          srcb = (char) (context->srcb);
711
          dst = (char) (context->dst);
712
          mask = 0xff;
713
          break;
714
        case 16:
715
          srca = (short) (context->srca);
716
          srcb = (short) (context->srcb);
717
          dst = (short) (context->dst);
718
          mask = 0xffff;
719
          break;
720
        case 32:
721
          srca = (long) (context->srca);
722
          srcb = (long) (context->srcb);
723
          dst = (long) (context->dst);
724
          mask = 0xffffffff;
725
          break;
726
        }
727
 
728
      switch (c)
729
        {
730
        case T:
731
          return 1;
732
        case F:
733
          return 0;
734
        case EQ:
735
          return !dst;
736
        case NE:
737
          return dst;
738
        case GT:
739
          ans = ((dst)) > 0;
740
          if (slow)
741
            {
742
              if (is_cond_true (context, c) != ans)
743
                abort ();
744
            }
745
          return ans;
746
        case LE:
747
          ans = ((dst)) <= 0;
748
          if (slow)
749
            {
750
              if (is_cond_true (context, c) != ans)
751
                abort ();
752
            }
753
          return ans;
754
        case GE:
755
          ans = ((dst)) >= 0;
756
          if (slow)
757
            {
758
              if (is_cond_true (context, c) != ans)
759
                abort ();
760
            }
761
          return ans;
762
        case LT:
763
          ans = ((dst)) < 0;
764
          if (slow)
765
            {
766
              if (is_cond_true (context, c) != ans)
767
                abort ();
768
            }
769
          return ans;
770
        default:
771
          break;
772
        }
773
 
774
      /* Can't fake it, we'll have to work out the flags the
775
         hard way */
776
 
777
      makeflags (context, mask);
778
    }
779
 
780
  /* don't know how to fake a test, inspect the flags
781
     the hard way */
782
 
783
  return is_cond_true (context, c);
784
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.