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

Subversion Repositories or1k

[/] [or1k/] [tags/] [tn_m001/] [or1ksim/] [toplevel.c] - Blame information for rev 138

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
#include "config.h"
24
 
25 2 cvs
#include <stdio.h>
26
#include <ctype.h>
27
#include <string.h>
28
#include <stdlib.h>
29 46 lampret
#include <unistd.h>
30 2 cvs
#include <signal.h>
31
#include <stdarg.h>
32 123 markom
/* Added by CZ 24/05/01 */
33
#include <sys/stat.h>
34
#include <sys/types.h>
35
#include <sys/socket.h>
36
#include <netinet/in.h>
37
#include <sys/select.h>
38
#include <sys/poll.h>
39
#include <fcntl.h>
40
#include <netdb.h>
41
#include <netinet/tcp.h>
42 127 chris
#include <inttypes.h>
43 2 cvs
 
44 16 jrydberg
#ifdef HAVE_LIBREADLINE
45 7 jrydberg
#include <readline/readline.h>
46
#include <readline/history.h>
47 16 jrydberg
#endif /* HAVE_LIBREADLINE */
48 7 jrydberg
 
49 2 cvs
#include "arch.h"
50
#include "parse.h"
51
#include "abstract.h"
52
#include "trace.h"
53
#include "execute.h"
54 69 lampret
#include "sim-config.h"
55 103 lampret
#include "spr_defs.h"
56 2 cvs
 
57 28 lampret
#include "coff.h"
58
 
59 123 markom
/* Added by CZ 24/05/01 */
60 127 chris
#include "gdb.h"
61 123 markom
#include <signal.h>
62
#include <errno.h>
63
typedef enum {
64
  false = 0,
65
  true = 1,
66
} Boolean;
67
unsigned int serverIP = 0;
68
unsigned int serverPort = 0;
69
unsigned int server_fd = 0;
70
unsigned int gdb_fd = 0;
71
void HandleServerSocket(Boolean);
72
void JTAGRequest(void);
73
void GDBRequest(void);
74 127 chris
void ProtocolClean(int,int32_t);
75
static int gdb_read(void*,int);
76
static int gdb_write(void*,int);
77
void BlockJTAG(void);
78
 
79 123 markom
int GlobalMode = 0;   /* Start off in the orginal mode */
80
 
81 2 cvs
/* CVS revision number. */
82 138 markom
const char rcsrev[] = "$Revision: 1.18 $";
83 2 cvs
 
84
/* Continuos run versus single step tracing switch. */
85
int cont_run;
86
 
87
/* History of execution */
88
int histexec[HISTEXEC_LEN];
89
 
90 7 jrydberg
char *sim_commands [] = {
91
  "q",
92
  "t",
93
  "help",
94 21 cmchen
  "de",
95 7 jrydberg
  "dm",
96
  "run",
97
  "pr",
98
  "pm",
99
  "pc",
100 18 lampret
  "reset",
101
  "break",
102 7 jrydberg
  "hist",
103
  "stats",
104
  "info",
105
  "r",
106 54 lampret
  "dv",
107 7 jrydberg
 
108
};
109
 
110 2 cvs
void debug(const char *format, ...)
111
{
112 7 jrydberg
  char *p;
113
  va_list ap;
114 2 cvs
 
115 69 lampret
  if (config.simdebug) {
116
    if ((p = malloc(1000)) == NULL)
117
      return;
118
    va_start(ap, format);
119
    (void) vsnprintf(p, 1000, format, ap);
120
    va_end(ap);
121
    printf("%s\n", p);
122
    fflush(stdout);
123
    free(p);
124
  } else {
125
#if DEBUG
126 7 jrydberg
  if ((p = malloc(1000)) == NULL)
127
    return;
128
  va_start(ap, format);
129
  (void) vsnprintf(p, 1000, format, ap);
130
  va_end(ap);
131
  printf("%s\n", p);
132
  fflush(stdout);
133
  free(p);
134 2 cvs
#endif
135 69 lampret
  }
136 7 jrydberg
  return;
137 2 cvs
}
138
 
139 30 lampret
/* Strip whitespace from the start and end of STRING.  Return a pointer
140
   into STRING. */
141
#ifndef whitespace
142
#define whitespace(a)   ((a) == '\t' ? 1 : ((a) == ' '? 1 : 0))
143
#endif
144
 
145
char *
146
stripwhite (string)
147
     char *string;
148
{
149
  register char *s, *t;
150
 
151
  for (s = string; whitespace (*s); s++)
152
    ;
153
 
154
  if (*s == 0)
155
    return (s);
156
 
157
  t = s + strlen (s) - 1;
158
  while (t > s && whitespace (*t))
159
    t--;
160
  *++t = '\0';
161
 
162
  return s;
163
}
164
 
165 7 jrydberg
void
166
ctrl_c(signum)
167
     int signum;
168 2 cvs
{
169
        cont_run = 1;
170 123 markom
        config.iprompt = 1;
171 7 jrydberg
  signal(SIGINT, ctrl_c);
172 2 cvs
}
173
 
174 7 jrydberg
void
175
version()
176 2 cvs
{
177 7 jrydberg
        printf ("\n");
178 18 lampret
        printf ("OpenRISC 1000 (OR16+OR32) Architectural Simulator, %s\n", rcsrev);
179
        printf ("Copyright (C) 1999 Damjan Lampret, lampret@opencores.org\n");
180
        printf ("Copyright (C) 2000 Damjan Lampret, lampret@opencores.org\n");
181 21 cmchen
        printf ("                   Jimmy Chen-Min Chen, jimmy@ee.nctu.edu.tw\n");
182 18 lampret
        printf ("                   Johan Rydberg, johan.rydberg@insight.se\n");
183 7 jrydberg
        printf ("Visit http://www.opencores.org for more information about ");
184
        printf ("OpenRISC 1000 and\nother open source cores.\n\n");
185
        printf ("This software comes with ABSOLUTELY NO WARRANTY; for ");
186
        printf ("details see COPYING.\nThis is free software, and you ");
187
        printf ("are welcome to redistribute it under certain\nconditions; ");
188
        printf ("for details see COPYING.\n");
189 2 cvs
}
190
 
191 7 jrydberg
void
192
help()
193 2 cvs
{
194
        printf("q                        - quit simulator\n");
195
        printf("r                        - display all registers\n");
196
        printf("t                        - execute next instruction\n");
197
        printf("run <cycles> [<hush>]    - execute <cycles> instructions, no reg dump if hush\n");
198
        printf("pr <r> <value>           - patch register <r> with <value>\n");
199
        printf("dm <fromaddr> [<toaddr>] - display memory from <fromaddr> to <toaddr>\n");
200 21 cmchen
        printf("de                       - debug insn memory\n");
201 2 cvs
        printf("pm <addr> <value>        - patch memory location <addr> with <value>\n");
202
        printf("pc <value>               - patch PC register with <value>\n");
203 18 lampret
        printf("break <addr>             - toggle breakpoint at address <addr>\n");
204
        printf("reset                    - simulator reset\n");
205 2 cvs
        printf("hist                     - execution history\n");
206 6 lampret
        printf("stats <num|clear>        - execution statistics num or clear it.\n");
207
        printf("info                     - configuration info (caches etc.)\n");
208 54 lampret
        printf("dv <fromaddr> [<toaddr>] [<modname>] - dumps memory as verilog (use redirect)\n");
209 86 lampret
        printf("dh <fromaddr> [<toaddr>] - dumps memory as hex code (use redirect)\n");
210 2 cvs
        printf("<cmd> > <filename>       - redirect simulator stdout to <filename> (and not emulated printf)\n");
211 69 lampret
        printf("debug                    - toggles simulator debug mode\n");
212 2 cvs
        printf("help                     - available commands (this list)\n");
213
}
214
 
215 21 cmchen
void debugmem();
216
 
217 7 jrydberg
main(argc, argv)
218
     int argc;
219
     char *argv[];
220 2 cvs
{
221 7 jrydberg
        char *linestr;
222 16 jrydberg
        char item1[500], b2[500];
223 2 cvs
        char *redirstr;
224
        int hush;
225 123 markom
        unsigned long endaddr = 0xFFFFFFFF;
226
        int first_prompt = 1;
227
 
228 103 lampret
        srand(getpid());
229
        init_defconfig();
230 123 markom
        if (parse_args(argc, argv)) {
231 103 lampret
                printf("Usage: %s [options] <filename>\n", argv[0]);
232
                printf("Options:\n");
233
                printf(" -v: version and copyright note\n");
234
                printf(" -i: enable interactive command prompt\n");
235
                printf(" -bpb: disable branch prediction buffer analysis\n");
236
                printf(" -btic: disable branch prediction target insn cache analysis\n");
237
                printf(" -hazards: disable dependency hazards analysis\n");
238
                printf(" -history: disable instruction stream history analysis\n");
239
                printf(" -superscalar: disable superscalar analysis\n");
240 123 markom
                printf(" -fast: disable BPB, BTIC, SLP, dependency hazards, history"
241
                       " analysis etc.\n");
242 103 lampret
                printf(" -upr <n>: set UPR to n\n");
243
                printf(" -ver <n>: set VR[VER] to n\n");
244
                printf(" -rev <n>: set VR[REV] to n\n");
245 123 markom
                printf(" -loadmem[@<n>] <filename>: load memory with file, "
246
                       "optionally at address <n>\n"); /* (CZ) */
247
                printf(" -nosrv: do not launch JTAG proxy server\n"); /* (CZ) */
248
                printf(" -srv <n>: launch JTAG proxy server on port <n>\n"); /* (CZ) */
249
                printf(" -initmem <n | random>: initialize memory to value "
250
                       "<n> or random\n"); /* (CZ) */
251 103 lampret
                exit(-1);
252
        }
253 7 jrydberg
 
254 16 jrydberg
#ifdef HAVE_LIBREADLINE
255 7 jrydberg
  initialize_readline ();       /* Bind our completer. */
256 16 jrydberg
#endif  
257 123 markom
 
258
  if(!config.inhibit_server)
259
    {
260
      serverPort = config.server_port;
261
      if(server_fd = GetServerSocket("or1ksim","tcp",serverPort))
262
        printf("JTAG Proxy server started on port %d\n",serverPort);
263
    }
264 16 jrydberg
 
265 103 lampret
        print_config();
266 2 cvs
        signal(SIGINT, ctrl_c);
267
        initstats();
268 138 markom
        build_automata();
269 123 markom
 
270
        /* Modified by CZ on 24/05/01 ... if a filename is
271
           specified, behave as the simulator always has. This way,
272
           no existing test suites should be broken. If a filename
273
           is not specified, default to the new style behavior. Let
274
           the simulator start up and execute garbage, the same way
275
           a real CPU would. This should maximize the reality of
276
           the capabilities. In this mode, we will expect that
277
           someone will attach to us over the JTAG Proxy interface
278
           and begin debugging that way. */
279
 
280
        if(config.filename)
281
          {
282
            endaddr = loadcode(config.filename, MEMORY_START, 0);
283
            if (endaddr == -1) {
284
              printf("Problems loading boot code.\n");
285
              exit(1);
286
            }
287
          }
288
        else
289
          {
290
            if(config.random_mem)
291
              {
292
                int n = 0;
293
                int len = sizeof(mem);
294
                unsigned int* mptr = (unsigned int*)mem;
295
                unsigned int val = 0;
296
                int seed = time(NULL);
297
 
298
                srandom(seed);
299
                /* Print out the seed just in case we ever need to debug */
300
                printf("Seeding random generator with value %d\n",seed);
301
 
302
                for(n=0;n<len;n+=sizeof(unsigned int))
303
                  {
304
                    val = random();
305
                    if(random() > RAND_MAX/2)
306
                      val |= 0x80000000;
307
                    *mptr++ = val;
308
                  }
309
              }
310
            else if(config.pattern_mem)
311
              {
312
                int n = 0;
313
                int len = sizeof(mem);
314
                unsigned int* mptr = (unsigned int*)mem;
315
 
316
                for(n=0;n<len;n+=sizeof(unsigned int))
317
                  *mptr++ = config.pattern_mem;
318
              }
319
            else
320
              memset(mem,0,sizeof(mem));
321
 
322
            if(config.memory)
323
              {
324
                MemoryBlock* block = config.memory;
325
 
326
                while(block)
327
                  {
328
                    int fd = open(block->file,O_RDONLY);
329
                    int len,i;
330
                    struct stat buf;
331
                    char *mptr = (char*)mem;
332
                    char buffer[8192];
333
 
334
                    if(fd < 0)
335
                      {
336
                        perror(block->file);
337
                        exit(1);
338
                      }
339
                    if(fstat(fd,&buf) < 0)
340
                      {
341
                        char sTemp[256];
342
 
343
                        sprintf(sTemp,"stat(\"%s\")",block->file);
344
                        perror(sTemp);
345
                        exit(1);
346
                      }
347
                    if(!S_ISREG(buf.st_mode))
348
                      {
349
                        fprintf(stderr,"File \"%s\" is not a regular file.\n",
350
                                block->file);
351
                        exit(1);
352
                      }
353
 
354
                    len = buf.st_size;
355
                    mptr += block->address;
356
                    for(i=0;i<len;)
357
                      {
358
                        int n = read(fd,buffer,sizeof(buffer));
359
 
360
                        switch(n)
361
                          {
362
                          case -1:
363
                            if(errno == EINTR)
364
                              continue;
365
                            perror(block->file);
366
                            exit(1);
367
                          case 0:
368
                            fprintf(stderr,"File \"%s\": premature end of file.\n",
369
                                    block->file);
370
                            exit(1);
371
                          default:
372
                            memcpy(mptr,buffer,n);
373
                            i+= n;
374
                            break;
375
                          }
376
                      }
377
                    close(fd);
378
                  }
379
              }
380
          }
381
        GlobalMode = config.filename == NULL; /* Old mode = 0, New mode = 1 */
382
 
383 30 lampret
        uart_reset();
384 92 lampret
        tick_reset();
385 103 lampret
        pm_reset();
386
        pic_reset();
387 2 cvs
        reset();
388 123 markom
        if(!GlobalMode)  /* Only in old mode */
389 138 markom
          set_reg32(3, endaddr);
390 7 jrydberg
 
391 103 lampret
        while(1) {
392
                if (config.iprompt) {
393 123 markom
                  if(server_fd)
394
                    {
395
                      printf ("(sim) ");
396
                      fflush(stdout);
397
                      HandleServerSocket(true);  /* block & check_stdin = true */
398
                    }
399 16 jrydberg
#ifdef HAVE_LIBREADLINE
400 123 markom
                  /* Must disable readline in new mode. It isn't compatible
401
                     with non blocking environments */
402
                  if(!server_fd)
403
                    linestr = readline("(sim) ");
404
                  else
405
                    linestr = fgets(b2, sizeof b2, stdin);
406 16 jrydberg
#else
407 123 markom
                  if(!server_fd)
408
                    printf ("(sim) ");
409
                  linestr = fgets(b2, sizeof b2, stdin);
410 16 jrydberg
#endif
411 103 lampret
                } else
412
                        strcpy(linestr = b2, "run 100000000 hush");
413 7 jrydberg
 
414 103 lampret
                if (!linestr)
415
                        break;
416
                linestr = stripwhite (linestr);
417 7 jrydberg
 
418 16 jrydberg
#ifdef HAVE_LIBREADLINE
419 123 markom
                /* Readline only works in the old mode */
420
                if(!server_fd)
421
                  {
422
                    if (strlen(linestr) == 0) {
423
                      char *l = repeat_last_command ();
424
 
425
                      if (l) {
426
                        free (linestr);
427
                        linestr = l;
428
                      }
429
                    }
430
 
431
                    if (*linestr) {
432
                      add_history (linestr);
433
                    }
434
                  }
435 16 jrydberg
#endif /* HAVE_LIBREADLINE */
436 2 cvs
 
437 103 lampret
                if (redirstr = strstr(linestr, ">")) {
438
                        *redirstr = '\0';
439
                        strtoken(&redirstr[1], item1, 1);
440
                        freopen(item1, "w+", stdout);
441
                }
442 2 cvs
 
443
                strtoken(linestr, item1, 1);
444
                if (strcmp(item1, "q") == 0)     /* quit */
445
                        exit(0);
446
                else
447
                if (strcmp(item1, "help") == 0)  /* help */
448
                        help();
449
                else
450
                if (strcmp(item1, "t") == 0) {   /* trace */
451
                        cont_run = 1;
452
                } else
453
                if (strcmp(item1, "dm") == 0) {  /* dump memory */
454
                        char item2[20];
455
                        char item3[20];
456
                        static int from = 0, to = 0;
457
 
458
                        strtoken(linestr, item2, 2);
459
                        strtoken(linestr, item3, 3);
460
 
461
                        if (strlen(item2)) {
462
                                if (item2[0] == '_')
463
                                        from = eval_label(item2);
464
                                else
465
                                        from = strtoul(item2, NULL, 0);
466
                                to = from + 0x40;
467
                        }
468
                        if (strlen(item3))
469
                                to = strtoul(item3, NULL, 0);
470
                        dumpmemory(from, to);
471 54 lampret
                        printf("\n");
472 2 cvs
                } else
473 54 lampret
                if (strcmp(item1, "dv") == 0) {/* dump memory as verilog*/
474
                        char item2[20];
475
                        char item3[20];
476
                        char item4[20];
477
                        static int from = 0, to = 0;
478
 
479
                        strtoken(linestr, item2, 2);
480
                        strtoken(linestr, item3, 3);
481
                        strtoken(linestr, item4, 4);
482
 
483
                        if (strlen(item2)) {
484
                                if (item2[0] == '_')
485
                                        from = eval_label(item2);
486
                                else
487
                                        from = strtoul(item2, NULL, 0);
488
                                to = from + 0x40;
489
                        }
490
                        if (strlen(item3))
491
                                to = strtoul(item3, NULL, 0);
492
                        if (!strlen(item4))
493
                                strcpy(item4, "or1k_mem");
494
                        dumpverilog(item4, from, to);
495
                        printf("\n");
496
                } else
497 86 lampret
                if (strcmp(item1, "dh") == 0) {/* dump memory as hex*/
498
                        char item2[20];
499
                        char item3[20];
500
                        static int from = 0, to = 0;
501
 
502
                        strtoken(linestr, item2, 2);
503
                        strtoken(linestr, item3, 3);
504
 
505
                        if (strlen(item2)) {
506
                                if (item2[0] == '_')
507
                                        from = eval_label(item2);
508
                                else
509
                                        from = strtoul(item2, NULL, 0);
510
                                to = from + 0x40;
511
                        }
512
                        if (strlen(item3))
513
                                to = strtoul(item3, NULL, 0);
514
                        dumphex(from, to);
515
                        printf("\n");
516
                } else
517 2 cvs
                if (strcmp(item1, "pm") == 0) {  /* patch memory */
518
                        char item2[20];
519
                        char item3[20];
520
                        static int addr = 0;
521 123 markom
                        int breakpoint = 0;
522
 
523 2 cvs
                        strtoken(linestr, item2, 2);
524
                        strtoken(linestr, item3, 3);
525
                        if (strlen(item2))
526
                                if (item2[0] == '_')
527
                                        addr = eval_label(item2);
528
                                else
529
                                        addr = strtoul(item2, NULL, 0);
530 123 markom
                        set_mem32(addr, strtoul(item3, NULL, 0), &breakpoint);
531 2 cvs
                } else
532
                if (strcmp(item1, "pr") == 0) {  /* patch regs */
533
                        char item2[20];
534
                        char item3[20];
535
 
536
                        strtoken(linestr, item2, 2);
537
                        strtoken(linestr, item3, 3);
538 138 markom
                        set_reg32(strtoul(item2, NULL,0), strtoul(item3, NULL, 0));
539 2 cvs
                } else
540
                if (strcmp(item1, "pc") == 0) {  /* patch PC */
541
                        char item2[20];
542
 
543
                        strtoken(linestr, item2, 2);
544 86 lampret
                        pcnext = strtoul(item2, NULL, 0);
545 2 cvs
                } else
546 7 jrydberg
                if (strcmp(item1, "break") == 0) {       /* set/clear breakpoint */
547 2 cvs
                        char item2[20];
548
 
549
                        strtoken(linestr, item2, 2);
550
                        set_insnbrkpoint(strtoul(item2, NULL, 0));
551
                } else
552
                if (strcmp(item1, "r") == 0) {   /* dump regs */
553
                        dumpreg();
554
                } else
555 21 cmchen
                if (strcmp(item1, "de") == 0) {  /* reset simulator */
556
                        debugmem();
557
                } else
558 18 lampret
                if (strcmp(item1, "reset") == 0) {       /* reset simulator */
559 30 lampret
                        uart_reset();
560 92 lampret
                        tick_reset();
561 103 lampret
                        pm_reset();
562
                        pic_reset();
563 123 markom
                        reset(); /* Old or new mode */
564 18 lampret
                } else
565 69 lampret
                if (strcmp(item1, "debug") == 0) {       /* debug mode */
566
                        config.simdebug ^= 1;
567
                } else
568 2 cvs
                if (strcmp(item1, "hist") == 0) {        /* dump history */
569
                        int i;
570
                        for(i = HISTEXEC_LEN; i; i--)
571
                                dumpmemory(histexec[i - 1], histexec[i - 1] + 4);
572 46 lampret
                        printf("\n");
573 2 cvs
                } else
574
                if (strcmp(item1, "run") == 0) { /* run */
575
                        char item2[20];
576
                        char item3[20];
577
 
578
                        strtoken(linestr, item2, 2);
579
                        strtoken(linestr, item3, 3);
580
                        if (strcmp(item3, "hush") == 0)
581
                                hush = 1;
582
                        else
583
                                hush = 0;
584
                        cont_run = strtoul(item2, NULL, 0);
585
                } else
586
                if (strcmp(item1, "stats") == 0) { /* stats */
587 6 lampret
                        char item2[20];
588
                        int i = 0;
589
 
590
                        strtoken(linestr, item2, 2);
591
                        if (strcmp(item2, "clear") == 0) {
592
                                initstats();
593
                                printf("Cleared.\n");
594
                        } else {
595
                                i = strtoul(item2, NULL, 0);
596
                                printstats(i);
597
                        }
598
                } else
599
                if (strcmp(item1, "info") == 0) { /* configuration info */
600 78 lampret
                        itlb_status(-1);
601
                        dtlb_status(-1);
602 6 lampret
                        bpb_info();
603
                        btic_info();
604
                        ic_info();
605
                        dc_info();
606 30 lampret
                        uart_status();
607
                        sprs_status();
608 7 jrydberg
                } else {
609 103 lampret
                        printf("%s: Unknown command.\n", linestr);
610
                }
611
 
612 138 markom
                /* MM: 'run -1' means endless execution.  */
613
                while(cont_run != 0) {
614 123 markom
                  extern int cycle_delay;  /* Added by CZ 27/05/01. Set during exception. */
615 127 chris
                  extern int cpu_stalled;  /* CZ from debug_interface */
616 123 markom
 
617 127 chris
                  if(cpu_stalled)
618
                    {
619
                      BlockJTAG();
620
                      HandleServerSocket(false);
621
                      continue;
622
                    }
623
 
624 103 lampret
                        if (!getsprbits(SPR_PMR, SPR_PMR_DME | SPR_PMR_SME)) {
625 123 markom
                          if(cycle_delay <= 0)
626
                            {
627
                              cont_run--;
628
                              if(fetch()) {
629
                                cont_run = 0; /* memory breakpoint encountered */
630
                                break;
631
                              }
632
                              decode_execute(&iqueue[0]);
633
                              update_pc();
634
                              analysis();
635
                              if (!hush)
636
                                dumpreg();
637
                            }
638
                          else
639
                            cycle_delay--;
640
 
641
                          pic_clock();
642
                          dc_clock();
643
                          ic_clock();
644 103 lampret
                        }
645
                        if (!getsprbits(SPR_PMR, SPR_PMR_SME))
646 123 markom
                          tick_clock();
647 103 lampret
                        pm_clock();
648 30 lampret
                        uart_clock();
649 123 markom
                        HandleServerSocket(false); /* block & check_stdin = false */
650 2 cvs
                }
651
                hush = 0;
652
                fflush(stdout);
653
                freopen("/dev/fd/0", "w+", stdout);
654
 
655 123 markom
                if (!config.iprompt && !GlobalMode)     /* non-interactive quit in old mode */
656 103 lampret
                        exit(0);
657
 
658 16 jrydberg
#ifdef HAVE_LIBREADLINE
659 103 lampret
                if (linestr)
660
                        free (linestr);
661 16 jrydberg
#endif
662 7 jrydberg
 
663 2 cvs
        }
664
        exit(0);
665
}
666 7 jrydberg
 
667 16 jrydberg
#ifdef HAVE_LIBREADLINE
668 7 jrydberg
char *command_generator ();
669
char **sim_completion ();
670
 
671
/* Tell the GNU readline library how to complete.  We want to try to complete
672
   on command names if this is the first word in the line, or on filenames
673
   if not. */
674
void initialize_readline ()
675
{
676
  /* Allow conditional parsing of the ~/.inputrc file. */
677
  rl_readline_name = "or1ksim";
678
 
679
  /* Tell the completer that we want a crack first. */
680
  rl_attempted_completion_function = (CPPFunction *)sim_completion;
681
}
682
 
683
/* Attempt to complete on the contents of TEXT.  START and END bound the
684
   region of rl_line_buffer that contains the word to complete.  TEXT is
685
   the word to complete.  We can use the entire contents of rl_line_buffer
686
   in case we want to do some simple parsing.  Return the array of matches,
687
   or NULL if there aren't any. */
688
char **
689
sim_completion (text, start, end)
690
     char *text;
691
     int start, end;
692
{
693
  char **matches;
694
 
695
  matches = (char **)NULL;
696
 
697
  /* If this word is at the start of the line, then it is a command
698
     to complete.  Otherwise it is the name of a file in the current
699
     directory. */
700
  if (start == 0)
701
    matches = completion_matches (text, command_generator);
702
 
703
  return (matches);
704
}
705
 
706
/* Generator function for command completion.  STATE lets us know whether
707
   to start from scratch; without any state (i.e. STATE == 0), then we
708
   start at the top of the list. */
709
char *
710
command_generator (text, state)
711
     char *text;
712
     int state;
713
{
714
  static int list_index, len;
715
  char *name;
716
 
717
  /* If this is a new word to complete, initialize now.  This includes
718
     saving the length of TEXT for efficiency, and initializing the index
719
     variable to 0. */
720
  if (!state)
721
    {
722
      list_index = 0;
723
      len = strlen (text);
724
    }
725
 
726
  /* Return the next name which partially matches from the command list. */
727
  while (name = sim_commands[list_index])
728
    {
729
      list_index++;
730
 
731
      if (strncmp (name, text, len) == 0)
732
        return (dupstr(name));
733
    }
734
 
735
  /* If no names matched, then return NULL. */
736
  return ((char *)NULL);
737
}
738
 
739
char *
740
dupstr (s)
741
     char *s;
742
{
743
  char *r;
744
 
745
  r = xmalloc (strlen (s) + 1);
746
  strcpy (r, s);
747
  return (r);
748
}
749
 
750
/* Repeats the last command.  */
751
char *
752
repeat_last_command ()
753
{
754
  int offset = where_history ();
755
  HIST_ENTRY *hist;
756
 
757
  if (hist = history_get (offset))
758
    {
759
      return dupstr (hist->line);
760
    }
761
  return 0;
762
}
763 16 jrydberg
 
764
#endif
765
 
766 138 markom
extern char *disassembled;
767 21 cmchen
void debugmem() {
768 138 markom
  int i;
769
  printf("starting to dump mem...\n");
770
  for(i=0; i<500; i++) {
771
    printf("i=%x :: ", i);
772
    if (mem[i].label)
773
      printf("label: %s |", mem[i].label->name);
774
    {
775
      unsigned int _insn;
776
      _insn = ((unsigned long)mem[i].data << 24);
777
      _insn |= ((unsigned long)mem[i + 1].data << 16);
778
      _insn |= ((unsigned long)mem[i + 2].data << 8);
779
      _insn |= ((unsigned long)mem[i + 3].data);
780
      iqueue[0].insn_index = insn_decode(_insn);
781
      iqueue[0].insn = _insn;
782
      disassemble_insn (_insn);
783
      printf("%s\n", disassembled);
784
    }
785
  }
786 21 cmchen
}
787 123 markom
 
788 127 chris
static int tcp_level = 0;
789
 
790 123 markom
/* Added by CZ 24/05/01 */
791
int GetServerSocket(const char* name,const char* proto,int port)
792
{
793
  struct servent *service;
794
  struct protoent *protocol;
795
  struct sockaddr_in sa;
796
  struct hostent *hp;
797
  int sockfd;
798
  char myname[256];
799
  int flags;
800
  char sTemp[256];
801
 
802
  /* First, get the protocol number of TCP */
803
  if(!(protocol = getprotobyname(proto)))
804
    {
805
      sprintf(sTemp,"Unable to load protocol \"%s\"",proto);
806
      perror(sTemp);
807
      return 0;
808
    }
809 127 chris
  tcp_level = protocol->p_proto; /* Save for later */
810
 
811 123 markom
  /* If we weren't passed a non standard port, get the port
812
     from the services directory. */
813
  if(!port)
814
    {
815
      if(service = getservbyname(name,protocol->p_name))
816
        port = ntohs(service->s_port);
817
    }
818
 
819
  /* Create the socket using the TCP protocol */
820
  if((sockfd = socket(PF_INET,SOCK_STREAM,protocol->p_proto)) < 0)
821
    {
822
      perror("Unable to create socket");
823
      return 0;
824
    }
825
 
826
  flags = 1;
827
  if(setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR,(const char*)&flags,sizeof(int))
828
 < 0)
829
    {
830
      sprintf(sTemp,"Can not set SO_REUSEADDR option on socket %d",sockfd);
831
      perror(sTemp);
832
      close(sockfd);
833
      return 0;
834
    }
835
 
836
  /* The server should also be non blocking. Get the current flags. */
837
  if(fcntl(sockfd,F_GETFL,&flags) < 0)
838
    {
839
      sprintf(sTemp,"Unable to get flags for socket %d",sockfd);
840
      perror(sTemp);
841
      close(sockfd);
842
      return 0;
843
    }
844
 
845
  /* Set the nonblocking flag */
846
  if(fcntl(sockfd,F_SETFL, flags | O_NONBLOCK) < 0)
847
    {
848
      sprintf(sTemp,"Unable to set flags for socket %d to value 0x%08x",
849
              sockfd,flags | O_NONBLOCK);
850
      perror(sTemp);
851
      close(sockfd);
852
      return 0;
853
    }
854
 
855
  /* Find out what our address is */
856
  memset(&sa,0,sizeof(struct sockaddr_in));
857
  gethostname(myname,sizeof(myname));
858
  if(!(hp = gethostbyname(myname)))
859
    {
860
      perror("Unable to read hostname");
861
      close(sockfd);
862
      return 0;
863
    }
864
 
865
  /* Bind our socket to the appropriate address */
866
  sa.sin_family = hp->h_addrtype;
867
  sa.sin_port = htons(port);
868
  if(bind(sockfd,(struct sockaddr*)&sa,sizeof(struct sockaddr_in)) < 0)
869
    {
870
      sprintf(sTemp,"Unable to bind socket %d to port %d",sockfd,port);
871
      perror(sTemp);
872
      close(sockfd);
873
      return 0;
874
    }
875
  serverIP = sa.sin_addr.s_addr;
876
  flags = sizeof(struct sockaddr_in);
877
  if(getsockname(sockfd,(struct sockaddr*)&sa,&flags) < 0)
878
    {
879
      sprintf(sTemp,"Unable to get socket information for socket %d",sockfd);
880
      perror(sTemp);
881
      close(sockfd);
882
      return 0;
883
    }
884
  serverPort = ntohs(sa.sin_port);
885
 
886
  /* Set the backlog to 1 connections */
887
  if(listen(sockfd,1) < 0)
888
    {
889
      sprintf(sTemp,"Unable to set backlog on socket %d to %d",sockfd,1);
890
      perror(sTemp);
891
      close(sockfd);
892
      return 0;
893
    }
894
 
895
  return sockfd;
896
}
897
 
898 127 chris
void BlockJTAG()
899 123 markom
{
900
  struct pollfd fds[2];
901
  int n = 0;
902 127 chris
 
903
  fds[n].fd = server_fd;
904
  fds[n].events = POLLIN;
905
  fds[n++].revents = 0;
906
  if(gdb_fd)
907
    {
908
      fds[n].fd = gdb_fd;
909
      fds[n].events = POLLIN;
910
      fds[n++].revents = 0;
911
    }
912
  poll(fds,n,-1);
913
}
914
 
915
void HandleServerSocket(Boolean block)
916
{
917
  struct pollfd fds[3];
918
  int n = 0;
919 123 markom
  int timeout = block ? -1 : 0;
920
  int server_index = -1;
921
  int gdb_index = -1;
922
  Boolean data_on_stdin = false;
923
  int o_serv_fd = server_fd;
924
 
925
  if(!o_serv_fd && !gdb_fd)
926
    return;
927
 
928
  if(o_serv_fd)
929
    {
930
      fds[n].fd = o_serv_fd;
931
      fds[n].events = POLLIN;
932
      fds[n++].revents = 0;
933
    }
934
  if(gdb_fd)
935
    {
936
      fds[n].fd = gdb_fd;
937
      fds[n].events = POLLIN;
938
      fds[n++].revents = 0;
939
    }
940
  if(block)
941
    {
942
      fds[n].fd = 0;
943
      fds[n].events = POLLIN;
944
      fds[n++].revents = 0;
945
    }
946
 
947
  while(!data_on_stdin)
948
    {
949
      switch(poll(fds,n,timeout))
950
        {
951
        case -1:
952
          if(errno == EINTR)
953
            continue;
954
          perror("poll");
955
          server_fd = 0;
956
          break;
957
        case 0: /* Nothing interesting going on */
958
          data_on_stdin = true; /* Can only get here if nonblocking */
959
          break;
960
        default:
961 127 chris
          /* Make sure to handle the gdb port first! */
962 123 markom
          if((fds[0].revents && (gdb_fd && !o_serv_fd) ||
963
              fds[1].revents && (server_fd && gdb_fd)))
964
            {
965
              int revents = o_serv_fd ? fds[1].revents : fds[0].revents;
966
 
967
              if(revents & POLLIN)
968
                GDBRequest();
969
              else /* Error Occurred */
970
                {
971
                  fprintf(stderr,"Received flags 0x%08x on gdb socket. Shutting down.\n",revents);
972
                  close(gdb_fd);
973
                  gdb_fd = 0;
974
                }
975
            }
976 127 chris
          if(fds[0].revents && o_serv_fd)
977
            {
978
              if(fds[0].revents & POLLIN)
979
                JTAGRequest();
980
              else /* Error Occurred */
981
                {
982
                  fprintf(stderr,"Received flags 0x%08x on server. Shutting down.\n",fds[0].revents);
983
                  close(o_serv_fd);
984
                  server_fd = 0;
985
                  serverPort = 0;
986
                  serverIP = 0;
987
                }
988
            }
989 123 markom
          if(fds[2].revents || (fds[1].revents && !gdb_fd))
990
            data_on_stdin = true;
991
          break;
992
        } /* End of switch statement */
993
    } /* End of while statement */
994
}
995
 
996
void JTAGRequest()
997
{
998
  struct sockaddr_in sa;
999
  struct sockaddr* addr = (struct sockaddr*)&sa;
1000
  int n = sizeof(struct sockaddr_in);
1001
  int fd = accept(server_fd,addr,&n);
1002
  int on_off = 0; /* Turn off Nagel's algorithm on the socket */
1003
  int flags;
1004
  char sTemp[256];
1005
 
1006
  if(fd < 0)
1007
    {
1008
      /* This is valid, because a connection could have started,
1009
         and then terminated due to a protocol error or user
1010
         initiation before the accept could take place. */
1011
      if(errno != EWOULDBLOCK && errno != EAGAIN)
1012
        {
1013
          perror("accept");
1014
          close(server_fd);
1015
          server_fd = 0;
1016
          serverPort = 0;
1017
          serverIP = 0;
1018
        }
1019
      return;
1020
    }
1021
 
1022
  if(gdb_fd)
1023
    {
1024
      close(fd);
1025
      return;
1026
    }
1027
 
1028
  if(fcntl(fd,F_GETFL,&flags) < 0)
1029
    {
1030
      sprintf(sTemp,"Unable to get flags for gdb socket %d",fd);
1031
      perror(sTemp);
1032
      close(fd);
1033
      return;
1034
    }
1035
 
1036
  if(fcntl(fd,F_SETFL, flags | O_NONBLOCK) < 0)
1037
    {
1038
      sprintf(sTemp,"Unable to set flags for gdb socket %d to value 0x%08x",
1039
              fd,flags | O_NONBLOCK);
1040
      perror(sTemp);
1041
      close(fd);
1042
      return;
1043
    }
1044
 
1045 127 chris
  if(setsockopt(fd,tcp_level,TCP_NODELAY,&on_off,sizeof(int)) < 0)
1046 123 markom
    {
1047
      sprintf(sTemp,"Unable to disable Nagel's algorithm for socket %d.\nsetsockopt",fd);
1048
      perror(sTemp);
1049
      close(fd);
1050
      return;
1051
    }
1052
 
1053
  gdb_fd = fd;
1054
}
1055
 
1056
void GDBRequest()
1057
{
1058 127 chris
  JTAGProxyWriteMessage msg_write;
1059
  JTAGProxyReadMessage msg_read;
1060
  JTAGProxyChainMessage msg_chain;
1061
  JTAGProxyWriteResponse resp_write;
1062
  JTAGProxyReadResponse resp_read;
1063
  JTAGProxyChainResponse resp_chain;
1064
  char *buf;
1065
  unsigned long long data;
1066
  int err;
1067
  uint32_t command,length;
1068
 
1069
  /* First, we must read the incomming command */
1070
  if(gdb_read(&command,sizeof(uint32_t)) < 0)
1071
    {
1072
      if(gdb_fd)
1073
        {
1074
          perror("gdb socket - 1");
1075
          close(gdb_fd);
1076
          gdb_fd = 0;
1077
        }
1078
      return;
1079
    }
1080
  if(gdb_read(&length,sizeof(uint32_t)) < 0)
1081
    {
1082
      if(gdb_fd)
1083
        {
1084
          perror("gdb socket - 2");
1085
          close(gdb_fd);
1086
          gdb_fd = 0;
1087
        }
1088
      return;
1089
    }
1090
  length = ntohl(length);
1091
 
1092
  /* Now, verify the protocol and implement the command */
1093
  switch(ntohl(command))
1094
    {
1095
    case JTAG_COMMAND_WRITE:
1096
      if(length != sizeof(msg_write) - 8)
1097
        {
1098
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1099
          return;
1100
        }
1101
      buf = (char*)&msg_write;
1102
      if(gdb_read(&buf[8],length) < 0)
1103
        {
1104
          if(gdb_fd)
1105
            {
1106
              perror("gdb socket - 3");
1107
              close(gdb_fd);
1108
              gdb_fd = 0;
1109
            }
1110
          return;
1111
        }
1112
      msg_write.address = ntohl(msg_write.address);
1113
      msg_write.data_H = ntohl(msg_write.data_H);
1114
      msg_write.data_L = ntohl(msg_write.data_L);
1115
      err = DebugSetRegister(msg_write.address,msg_write.data_L);
1116
      resp_write.status = htonl(err);
1117
      if(gdb_write(&resp_write,sizeof(resp_write)) < 0)
1118
        {
1119
          if(gdb_fd)
1120
            {
1121
              perror("gdb socket - 4");
1122
              close(gdb_fd);
1123
              gdb_fd = 0;
1124
            }
1125
          return;
1126
        }
1127
      break;
1128
    case JTAG_COMMAND_READ:
1129
      if(length != sizeof(msg_read) - 8)
1130
        {
1131
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1132
          return;
1133
        }
1134
      buf = (char*)&msg_read;
1135
      if(gdb_read(&buf[8],length) < 0)
1136
        {
1137
          if(gdb_fd)
1138
            {
1139
              perror("gdb socket - 5");
1140
              close(gdb_fd);
1141
              gdb_fd = 0;
1142
            }
1143
          return;
1144
        }
1145
      msg_read.address = ntohl(msg_read.address);
1146
      err = DebugGetRegister(msg_read.address,&resp_read.data_L);
1147
      resp_read.status = htonl(err);
1148
      resp_read.data_H = 0;
1149
      resp_read.data_L = htonl(resp_read.data_L);
1150
      if(gdb_write(&resp_read,sizeof(resp_read)) < 0)
1151
        {
1152
          if(gdb_fd)
1153
            {
1154
              perror("gdb socket - 6");
1155
              close(gdb_fd);
1156
              gdb_fd = 0;
1157
            }
1158
          return;
1159
        }
1160
      break;
1161
    case JTAG_COMMAND_CHAIN:
1162
      if(length != sizeof(msg_chain) - 8)
1163
        {
1164
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1165
          return;
1166
        }
1167
      buf = (char*)&msg_chain;
1168
      if(gdb_read(&buf[8],sizeof(msg_chain)-8) < 0)
1169
        {
1170
          if(gdb_fd)
1171
            {
1172
              perror("gdb socket - 7");
1173
              close(gdb_fd);
1174
              gdb_fd = 0;
1175
            }
1176
          return;
1177
        }
1178
      msg_chain.chain = htonl(msg_chain.chain);
1179
      err = DebugSetChain(msg_chain.chain);
1180
      resp_chain.status = htonl(err);
1181
      if(gdb_write(&resp_chain,sizeof(resp_chain)) < 0)
1182
        {
1183
          if(gdb_fd)
1184
            {
1185
              perror("gdb socket - 8");
1186
              close(gdb_fd);
1187
              gdb_fd = 0;
1188
            }
1189
          return;
1190
        }
1191
      break;
1192
    default:
1193
      ProtocolClean(length,JTAG_PROXY_COMMAND_NOT_IMPLEMENTED);
1194
      break;
1195
    }
1196 123 markom
}
1197 127 chris
 
1198
void ProtocolClean(int length,int32_t err)
1199
{
1200
  char buf[4096];
1201
 
1202
  err = htonl(err);
1203
  if((gdb_read(buf,length) < 0) ||
1204
      (gdb_write(&err,sizeof(err)) < 0) && gdb_fd)
1205
    {
1206
      perror("gdb socket - 9");
1207
      close(gdb_fd);
1208
      gdb_fd = 0;
1209
    }
1210
}
1211
 
1212
static int gdb_write(void* buf,int len)
1213
{
1214
  int n;
1215
  char* w_buf = (char*)buf;
1216
  struct pollfd block;
1217
 
1218
  while(len)
1219
    {
1220
      if((n = write(gdb_fd,w_buf,len)) < 0)
1221
        {
1222
          switch(errno)
1223
            {
1224
            case EWOULDBLOCK: /* or EAGAIN */
1225
              /* We've been called on a descriptor marked
1226
                 for nonblocking I/O. We better simulate
1227
                 blocking behavior. */
1228
              block.fd = gdb_fd;
1229
              block.events = POLLOUT;
1230
              block.revents = 0;
1231
              poll(&block,1,-1);
1232
              continue;
1233
            case EINTR:
1234
              continue;
1235
            case EPIPE:
1236
              close(gdb_fd);
1237
              gdb_fd = 0;
1238
              return -1;
1239
            default:
1240
              return -1;
1241
            }
1242
        }
1243
      else
1244
        {
1245
          len -= n;
1246
          w_buf += n;
1247
        }
1248
    }
1249
  return 0;
1250
}
1251
 
1252
static int gdb_read(void* buf,int len)
1253
{
1254
  int n;
1255
  char* r_buf = (char*)buf;
1256
  struct pollfd block;
1257
 
1258
  while(len)
1259
    {
1260
      if((n = read(gdb_fd,r_buf,len)) < 0)
1261
        {
1262
          switch(errno)
1263
            {
1264
            case EWOULDBLOCK: /* or EAGAIN */
1265
              /* We've been called on a descriptor marked
1266
                 for nonblocking I/O. We better simulate
1267
                 blocking behavior. */
1268
              block.fd = gdb_fd;
1269
              block.events = POLLIN;
1270
              block.revents = 0;
1271
              poll(&block,1,-1);
1272
              continue;
1273
            case EINTR:
1274
              continue;
1275
            default:
1276
              return -1;
1277
            }
1278
        }
1279
      else if(n == 0)
1280
        {
1281
          close(gdb_fd);
1282
          gdb_fd = 0;
1283
          return -1;
1284
        }
1285
      else
1286
        {
1287
          len -= n;
1288
          r_buf += n;
1289
        }
1290
    }
1291
  return 0;
1292
}

powered by: WebSVN 2.1.0

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