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

Subversion Repositories or1k

[/] [or1k/] [tags/] [rel-0-3-0-rc2/] [or1ksim/] [toplevel.c] - Blame information for rev 1688

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

Line No. Rev Author Line
1 2 cvs
/* toplevel.c -- Top level simulator source file
2
   Copyright (C) 1999 Damjan Lampret, lampret@opencores.org
3
 
4
This file is part of OpenRISC 1000 Architectural Simulator.
5
 
6
This program 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 of the License, or
9
(at your option) any later version.
10
 
11
This program 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 this program; if not, write to the Free Software
18
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
19
 
20
/* Simulator commands. Help and version output. SIGINT processing.
21
Stdout redirection is specific to linux (I need to fix this). */
22
 
23 16 jrydberg
 
24 2 cvs
#include <stdio.h>
25
#include <ctype.h>
26
#include <string.h>
27
#include <stdlib.h>
28 46 lampret
#include <unistd.h>
29 2 cvs
#include <signal.h>
30
#include <stdarg.h>
31 123 markom
#include <fcntl.h>
32 728 markom
#include <limits.h>
33 1308 phoenix
#include <time.h>
34 2 cvs
 
35 1350 nogj
#include "config.h"
36
 
37
#ifdef HAVE_INTTYPES_H
38
#include <inttypes.h>
39
#endif
40
 
41
#include "port.h"
42 2 cvs
#include "arch.h"
43
#include "parse.h"
44
#include "abstract.h"
45 261 markom
#include "labels.h"
46 69 lampret
#include "sim-config.h"
47 1432 nogj
#include "opcode/or32.h"
48 103 lampret
#include "spr_defs.h"
49 1432 nogj
#include "execute.h"
50 518 markom
#include "sprs.h"
51 304 markom
#include "vapi.h"
52 479 markom
#include "gdbcomm.h"
53
#include "debug_unit.h"
54 28 lampret
#include "coff.h"
55 728 markom
#include "sched.h"
56 632 ivang
#include "profiler.h"
57
#include "mprofiler.h"
58 1308 phoenix
#include "pm.h"
59
#include "pic.h"
60
#include "stats.h"
61
#include "immu.h"
62
#include "dmmu.h"
63
#include "dcache_model.h"
64
#include "icache_model.h"
65
#include "branch_predict.h"
66
#include "dumpverilog.h"
67
#include "trace.h"
68
#include "cuc.h"
69 1557 nogj
#include "tick.h"
70 1688 nogj
#include "debug.h"
71 632 ivang
 
72 1688 nogj
DECLARE_DEBUG_CHANNEL(sched);
73
 
74 1645 nogj
const char *or1ksim_ver = "0.2.0";
75 2 cvs
 
76 344 markom
inline void debug(int level, const char *format, ...)
77 2 cvs
{
78 7 jrydberg
  char *p;
79
  va_list ap;
80 2 cvs
 
81 344 markom
  if (config.sim.debug >= level) {
82 69 lampret
    if ((p = malloc(1000)) == NULL)
83
      return;
84
    va_start(ap, format);
85
    (void) vsnprintf(p, 1000, format, ap);
86
    va_end(ap);
87 997 markom
    PRINTF("%s", p);
88 69 lampret
    fflush(stdout);
89
    free(p);
90
  } else {
91
#if DEBUG
92 7 jrydberg
  if ((p = malloc(1000)) == NULL)
93
    return;
94
  va_start(ap, format);
95
  (void) vsnprintf(p, 1000, format, ap);
96
  va_end(ap);
97 997 markom
  PRINTF("%s\n", p);
98 7 jrydberg
  fflush(stdout);
99
  free(p);
100 2 cvs
#endif
101 69 lampret
  }
102 2 cvs
}
103
 
104 304 markom
void ctrl_c(signum)
105 7 jrydberg
     int signum;
106 2 cvs
{
107 1480 nogj
  /* Incase the user pressed ctrl+c twice without the sim reacting kill it.
108
   * This is incase the sim locks up in a high level routine, without executeing
109
   * any (or) code */
110 1593 nogj
  if(runtime.sim.iprompt && !runtime.sim.iprompt_run)
111 1480 nogj
    sim_done();
112 551 markom
  runtime.sim.iprompt = 1;
113 7 jrydberg
  signal(SIGINT, ctrl_c);
114 2 cvs
}
115
 
116 1471 nogj
/* Periodically checks runtime.sim.iprompt to see if ctrl_c has been pressed */
117
void check_int(void *dat)
118 2 cvs
{
119 1471 nogj
  if(runtime.sim.iprompt) {
120
    set_stall_state (0);
121
    handle_sim_command();
122
  }
123
  SCHED_ADD(check_int, NULL, CHECK_INT_TIME);
124
}
125
 
126 1360 nogj
struct sim_reset_hook {
127
  void *dat;
128
  void (*reset_hook)(void *);
129
  struct sim_reset_hook *next;
130
};
131 21 cmchen
 
132 1550 nogj
static struct sim_reset_hook *sim_reset_hooks = NULL;
133 1360 nogj
 
134
/* Registers a new reset hook, called when sim_reset below is called */
135
void reg_sim_reset(void (*reset_hook)(void *), void *dat)
136
{
137
  struct sim_reset_hook *new = malloc(sizeof(struct sim_reset_hook));
138
 
139
  if(!new) {
140
    fprintf(stderr, "reg_sim_reset: Out-of-memory\n");
141
    exit(1);
142
  }
143
 
144
  new->dat = dat;
145
  new->reset_hook = reset_hook;
146
  new->next = sim_reset_hooks;
147
  sim_reset_hooks = new;
148
}
149
 
150 479 markom
/* Resets all subunits */
151 1353 nogj
void sim_reset (void)
152 479 markom
{
153 1360 nogj
  struct sim_reset_hook *cur_reset = sim_reset_hooks;
154
 
155 1390 nogj
  /* We absolutely MUST reset the scheduler first */
156
  sched_reset();
157 1360 nogj
 
158
  while(cur_reset) {
159
    cur_reset->reset_hook(cur_reset->dat);
160
    cur_reset = cur_reset->next;
161
  }
162
 
163 479 markom
  tick_reset();
164
  pm_reset();
165
  pic_reset();
166
  du_reset ();
167 1452 nogj
 
168 1471 nogj
  /* Make sure that runtime.sim.iprompt is the first thing to get checked */
169 1486 nogj
  SCHED_ADD(check_int, NULL, 1);
170 1471 nogj
 
171 1452 nogj
  /* FIXME: Lame-ass way to get runtime.sim.mem_cycles not going into overly
172
   * negative numbers.  This happens because parse.c uses setsim_mem32 to load
173
   * the program but set_mem32 calls dc_simulate_write, which inturn calls
174
   * setsim_mem32.  This mess of memory statistics needs to be sorted out for
175
   * good one day */
176
  runtime.sim.mem_cycles = 0;
177 557 markom
  cpu_reset();
178 479 markom
}
179
 
180 304 markom
/* Initalizes all devices and sim */
181 1486 nogj
void sim_init (void)
182 2 cvs
{
183 269 markom
  init_labels();
184
  init_breakpoints();
185 361 markom
  initstats();
186
  build_automata();
187 1390 nogj
 
188 1452 nogj
#if DYNAMIC_EXECUTION
189
  /* Note: This must be called before the scheduler is used */
190
  init_dyn_recomp();
191
#endif
192
 
193 1390 nogj
  sched_init();
194 361 markom
 
195 305 markom
  if (config.sim.profile) {
196 361 markom
    runtime.sim.fprof = fopen(config.sim.prof_fn, "wt+");
197
    if(!runtime.sim.fprof) {
198 551 markom
      fprintf(stderr, "ERROR: Problems opening profile file.\n");
199
      exit (1);
200 173 markom
    } else
201 897 markom
      fprintf(runtime.sim.fprof, "+00000000 FFFFFFFF FFFFFFFF [outside_functions]\n");
202 173 markom
  }
203 294 markom
 
204 547 markom
  if (config.sim.mprofile) {
205
    runtime.sim.fmprof = fopen(config.sim.mprof_fn, "wb+");
206
    if(!runtime.sim.fmprof) {
207 551 markom
      fprintf(stderr, "ERROR: Problems opening memory profile file.\n");
208
      exit (1);
209 547 markom
    }
210
  }
211
 
212 294 markom
  if (config.sim.exe_log) {
213 361 markom
    runtime.sim.fexe_log = fopen(config.sim.exe_log_fn, "wt+");
214
    if(!runtime.sim.fexe_log) {
215 997 markom
      PRINTF("ERROR: Problems opening exe_log file.\n");
216 551 markom
      exit (1);
217 294 markom
    }
218
  }
219 263 markom
 
220 361 markom
  if(runtime.sim.filename) {
221
    unsigned long endaddr = 0xFFFFFFFF;
222
    endaddr = loadcode(runtime.sim.filename, 0, 0); /* MM170901 always load at address zero.  */
223
    if (endaddr == -1) {
224
      fprintf(stderr, "Problems loading boot code.\n");
225
      exit(1);
226
    }
227
  }
228 551 markom
 
229 361 markom
  /* Disable gdb debugging, if debug module is not available.  */
230
  if (config.debug.gdb_enabled && !config.debug.enabled) {
231
    config.debug.gdb_enabled = 0;
232
    if (config.sim.verbose)
233
      fprintf (stderr, "WARNING: Debug module not enabled, cannot start gdb.\n");
234
  }
235 551 markom
 
236 550 markom
  if (config.debug.gdb_enabled)
237 479 markom
    gdbcomm_init ();
238 551 markom
 
239 361 markom
  /* Enable dependency stats, if we want to do history analisis */
240 394 markom
  if (config.sim.history && !config.cpu.dependstats) {
241
    config.cpu.dependstats = 1;
242 361 markom
    if (config.sim.verbose)
243 394 markom
      fprintf (stderr, "WARNING: dependstats stats must be enabled to do history analisis.\n");
244 361 markom
  }
245 551 markom
 
246 361 markom
  /* Debug forces verbose */
247
  if (config.sim.debug && !config.sim.verbose) {
248
    config.sim.verbose = 1;
249
    fprintf (stderr, "WARNING: verbose turned on.\n");
250
  }
251
 
252
  /* Start VAPI before device initialization.  */
253
  if (config.vapi.enabled) {
254 551 markom
    runtime.vapi.enabled = 1;
255 361 markom
    vapi_init ();
256
    if (config.sim.verbose)
257 997 markom
      PRINTF ("VAPI started, waiting for clients.\n");
258 361 markom
  }
259 538 markom
 
260 479 markom
  sim_reset ();
261 424 markom
 
262 361 markom
  /* Wait till all test are connected.  */
263 551 markom
  if (runtime.vapi.enabled) {
264 361 markom
    int numu = vapi_num_unconnected (0);
265
    if (numu) {
266 997 markom
      PRINTF ("\nWaiting for VAPI tests with ids:\n");
267 361 markom
      vapi_num_unconnected (1);
268 997 markom
      PRINTF ("\n");
269 1308 phoenix
      while ((numu = vapi_num_unconnected (0))) {
270 361 markom
        vapi_check ();
271 997 markom
        PRINTF ("\rStill waiting for %i VAPI test(s) to connect.       ", numu);
272 361 markom
        usleep (100);
273
      }
274 997 markom
      PRINTF ("\n");
275 361 markom
    }
276 997 markom
    PRINTF ("All devices connected                         \n");
277 361 markom
  }
278
  /* simulator is initialized */
279
  runtime.sim.init = 0;
280 304 markom
}
281 7 jrydberg
 
282 304 markom
/* Cleanup */
283 1446 nogj
void sim_done (void)
284 304 markom
{
285
  if (config.sim.profile) {
286 1350 nogj
    fprintf(runtime.sim.fprof,"-%08llX FFFFFFFF\n", runtime.sim.cycles);
287 361 markom
    fclose(runtime.sim.fprof);
288 304 markom
  }
289 547 markom
 
290 847 markom
  if (config.sim.mprofile) fclose(runtime.sim.fmprof);
291 361 markom
  if (config.sim.exe_log)   fclose(runtime.sim.fexe_log);
292 551 markom
  if (runtime.vapi.enabled)  vapi_done ();
293 426 markom
  done_memory_table ();
294 304 markom
  exit(0);
295
}
296
 
297 728 markom
/* Executes jobs in time queue */
298 1452 nogj
#if !(DYNAMIC_EXECUTION)
299
static inline
300
#endif
301
void do_scheduler (void)
302 728 markom
{
303 1390 nogj
  struct sched_entry *tmp;
304 632 ivang
 
305 728 markom
  /* Execute all jobs till now */
306
  do {
307 1390 nogj
    tmp = scheduler.job_queue;
308
    scheduler.job_queue = tmp->next;
309
    tmp->next = scheduler.free_job_queue;
310
    scheduler.free_job_queue = tmp;
311
 
312 1607 nogj
    scheduler.job_queue->time += tmp->time;
313
 
314 1452 nogj
    TRACE_(sched)("Setting to-go cycles to %"PRIi32" at %lli\n",
315
                  scheduler.job_queue->time, runtime.sim.cycles);
316
 
317 1390 nogj
    tmp->func (tmp->param);
318
  } while (scheduler.job_queue->time <= 0);
319 728 markom
}
320 632 ivang
 
321 1471 nogj
void recalc_do_stats(void)
322
{
323
  extern int do_stats;
324 1550 nogj
  do_stats = config.cpu.superscalar || config.cpu.dependstats ||
325
             config.sim.history || config.sim.exe_log;
326 1471 nogj
}
327
 
328 728 markom
/* Main function */
329 304 markom
int main(argc, argv)
330
     int argc;
331
     char *argv[];
332
{
333 361 markom
  srand(getpid());
334
  init_defconfig();
335 1358 nogj
  reg_config_secs();
336 361 markom
  if (parse_args(argc, argv)) {
337 997 markom
    PRINTF("Usage: %s [options] <filename>\n", argv[0]);
338
    PRINTF("Options:\n");
339
    PRINTF(" -v                   version and copyright note\n");
340
    PRINTF(" -i                   enable interactive command prompt\n");
341
    PRINTF(" --nosrv              do not launch JTAG proxy server\n"); /* (CZ) */
342
    PRINTF(" --srv <n>            launch JTAG proxy server on port <n>; [random]\n"); /* (CZ) */
343
    PRINTF(" -f or --file         load script file [sim.cfg]\n");
344 1548 nogj
    PRINTF(" -d <debug config>    Enable debug channels\n");
345 997 markom
    PRINTF(" --enable-profile     enable profiling.\n");
346
    PRINTF(" --enable-mprofile    enable memory profiling.\n");
347
    PRINTF("\nor   : %s ", argv[0]);
348 847 markom
    mp_help ();
349 997 markom
    PRINTF("\nor   : %s ", argv[0]);
350 847 markom
    prof_help ();
351 361 markom
    exit(-1);
352
  }
353 304 markom
 
354
  /* Read configuration file.  */
355 361 markom
  if (!runtime.sim.script_file_specified)
356
    read_script_file ("sim.cfg");
357 883 markom
 
358
  /* Overide parameters with command line ones */
359
  if (runtime.simcmd.profile) config.sim.profile = 1;
360
  if (runtime.simcmd.mprofile) config.sim.mprofile = 1;
361
 
362 424 markom
  if (!runtime.sim.script_file_specified && config.sim.verbose)
363
    fprintf (stderr, "WARNING: No config file read, assuming default configuration.\n");
364 304 markom
  print_config();
365
  signal(SIGINT, ctrl_c);
366 335 markom
 
367 1353 nogj
  runtime.sim.hush = 1;
368 1471 nogj
  recalc_do_stats();
369 1353 nogj
 
370 1471 nogj
  sim_init ();
371
 
372 361 markom
  while(1) {
373 1471 nogj
    long long time_start = runtime.sim.cycles;
374
    if (config.debug.enabled) {
375
      du_clock(); // reset watchpoints
376
      while (runtime.cpu.stalled) {
377
        if(config.debug.gdb_enabled) {
378
          BlockJTAG();
379
          HandleServerSocket(false);
380
        } else {
381
          fprintf (stderr, "WARNING: CPU stalled and gdb connection not enabled.\n");
382
          /* Dump the user into interactive mode.  From there he can decide what
383
           * to do. */
384
          handle_sim_command();
385
          sim_done();
386 557 markom
        }
387 1471 nogj
        if(runtime.sim.iprompt)
388
          handle_sim_command();
389 479 markom
      }
390 1471 nogj
    }
391 127 chris
 
392 1471 nogj
    /* Each cycle has counter of mem_cycles; this value is joined with cycles
393
       at the end of the cycle; no sim originated memory accesses should be
394
       performed inbetween. */
395
    runtime.sim.mem_cycles = 0;
396 1506 nogj
    if (!config.pm.enabled ||
397
        !(cpu_state.sprs[SPR_PMR] & (SPR_PMR_DME | SPR_PMR_SME)))
398 1471 nogj
      if (cpu_clock ())
399
        /* A breakpoint has been hit, drop to interactive mode */
400
        handle_sim_command();
401 304 markom
 
402 1471 nogj
    if (config.vapi.enabled && runtime.vapi.enabled) vapi_check();
403
    if (config.debug.gdb_enabled) HandleServerSocket(false); /* block & check_stdin = false */
404
    if(config.debug.enabled)
405 1506 nogj
      if (cpu_state.sprs[SPR_DMR1] & SPR_DMR1_ST) set_stall_state (1);
406 557 markom
 
407 1471 nogj
    runtime.sim.cycles += runtime.sim.mem_cycles;
408
    scheduler.job_queue->time -= runtime.sim.cycles - time_start;
409
    if (scheduler.job_queue->time <= 0) do_scheduler ();
410 361 markom
  }
411
  sim_done();
412 2 cvs
}

powered by: WebSVN 2.1.0

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