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

Subversion Repositories or1k

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

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 139 chris
const char rcsrev[] = "$Revision: 1.19 $";
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 139 chris
  JTAGProxyBlockWriteMessage *msg_bwrite;
1065
  JTAGProxyBlockReadMessage msg_bread;
1066
  JTAGProxyBlockWriteResponse resp_bwrite;
1067
  JTAGProxyBlockReadResponse *resp_bread;
1068 127 chris
  char *buf;
1069
  unsigned long long data;
1070 139 chris
  int err = 0;
1071 127 chris
  uint32_t command,length;
1072 139 chris
  int len,i;
1073 127 chris
 
1074
  /* First, we must read the incomming command */
1075
  if(gdb_read(&command,sizeof(uint32_t)) < 0)
1076
    {
1077
      if(gdb_fd)
1078
        {
1079
          perror("gdb socket - 1");
1080
          close(gdb_fd);
1081
          gdb_fd = 0;
1082
        }
1083
      return;
1084
    }
1085
  if(gdb_read(&length,sizeof(uint32_t)) < 0)
1086
    {
1087
      if(gdb_fd)
1088
        {
1089
          perror("gdb socket - 2");
1090
          close(gdb_fd);
1091
          gdb_fd = 0;
1092
        }
1093
      return;
1094
    }
1095
  length = ntohl(length);
1096
 
1097
  /* Now, verify the protocol and implement the command */
1098
  switch(ntohl(command))
1099
    {
1100
    case JTAG_COMMAND_WRITE:
1101
      if(length != sizeof(msg_write) - 8)
1102
        {
1103
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1104
          return;
1105
        }
1106
      buf = (char*)&msg_write;
1107
      if(gdb_read(&buf[8],length) < 0)
1108
        {
1109
          if(gdb_fd)
1110
            {
1111
              perror("gdb socket - 3");
1112
              close(gdb_fd);
1113
              gdb_fd = 0;
1114
            }
1115
          return;
1116
        }
1117
      msg_write.address = ntohl(msg_write.address);
1118
      msg_write.data_H = ntohl(msg_write.data_H);
1119
      msg_write.data_L = ntohl(msg_write.data_L);
1120
      err = DebugSetRegister(msg_write.address,msg_write.data_L);
1121
      resp_write.status = htonl(err);
1122
      if(gdb_write(&resp_write,sizeof(resp_write)) < 0)
1123
        {
1124
          if(gdb_fd)
1125
            {
1126
              perror("gdb socket - 4");
1127
              close(gdb_fd);
1128
              gdb_fd = 0;
1129
            }
1130
          return;
1131
        }
1132
      break;
1133
    case JTAG_COMMAND_READ:
1134
      if(length != sizeof(msg_read) - 8)
1135
        {
1136
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1137
          return;
1138
        }
1139
      buf = (char*)&msg_read;
1140
      if(gdb_read(&buf[8],length) < 0)
1141
        {
1142
          if(gdb_fd)
1143
            {
1144
              perror("gdb socket - 5");
1145
              close(gdb_fd);
1146
              gdb_fd = 0;
1147
            }
1148
          return;
1149
        }
1150
      msg_read.address = ntohl(msg_read.address);
1151
      err = DebugGetRegister(msg_read.address,&resp_read.data_L);
1152
      resp_read.status = htonl(err);
1153
      resp_read.data_H = 0;
1154
      resp_read.data_L = htonl(resp_read.data_L);
1155
      if(gdb_write(&resp_read,sizeof(resp_read)) < 0)
1156
        {
1157
          if(gdb_fd)
1158
            {
1159
              perror("gdb socket - 6");
1160
              close(gdb_fd);
1161
              gdb_fd = 0;
1162
            }
1163
          return;
1164
        }
1165
      break;
1166 139 chris
    case JTAG_COMMAND_BLOCK_WRITE:
1167
      if(length < sizeof(JTAGProxyBlockWriteMessage)-8)
1168
        {
1169
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1170
          return;
1171
        }
1172
      if(!(buf = (char*)malloc(8+length)))
1173
        {
1174
          ProtocolClean(length,JTAG_PROXY_OUT_OF_MEMORY);
1175
          return;
1176
        }
1177
      msg_bwrite = (JTAGProxyBlockWriteMessage*)buf;
1178
      if(gdb_read(&buf[8],length) < 0)
1179
        {
1180
          if(gdb_fd)
1181
            {
1182
              perror("gdb socket - 5");
1183
              close(gdb_fd);
1184
              gdb_fd = 0;
1185
            }
1186
          free(buf);
1187
          return;
1188
        }
1189
      msg_bwrite->address = ntohl(msg_bwrite->address);
1190
      msg_bwrite->nRegisters = ntohl(msg_bwrite->nRegisters);
1191
      for(i=0;i<msg_bwrite->nRegisters;i++)
1192
        {
1193
          int t_err;
1194
 
1195
          msg_bwrite->data[i] = ntohl(msg_bwrite->data[i]);
1196
          t_err = DebugSetRegister(msg_bwrite->address+i,msg_bwrite->data[i]);
1197
          err = err ? err : t_err;
1198
        }
1199
      resp_bwrite.status = htonl(err);
1200
      free(buf);
1201
      buf = msg_bwrite = NULL;
1202
      if(gdb_write(&resp_bwrite,sizeof(resp_bwrite)) < 0)
1203
        {
1204
          if(gdb_fd)
1205
            {
1206
              perror("gdb socket - 4");
1207
              close(gdb_fd);
1208
              gdb_fd = 0;
1209
            }
1210
          return;
1211
        }
1212
      break;
1213
    case JTAG_COMMAND_BLOCK_READ:
1214
      if(length != sizeof(msg_bread) - 8)
1215
        {
1216
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1217
          return;
1218
        }
1219
      buf = (char*)&msg_bread;
1220
      if(gdb_read(&buf[8],length) < 0)
1221
        {
1222
          if(gdb_fd)
1223
            {
1224
              perror("gdb socket - 5");
1225
              close(gdb_fd);
1226
              gdb_fd = 0;
1227
            }
1228
          return;
1229
        }
1230
      msg_bread.address = ntohl(msg_bread.address);
1231
      msg_bread.nRegisters = ntohl(msg_bread.nRegisters);
1232
      len = sizeof(JTAGProxyBlockReadResponse) + 4*(msg_bread.nRegisters-1);
1233
      if(!(buf = (char*)malloc(len)))
1234
        {
1235
          ProtocolClean(0,JTAG_PROXY_OUT_OF_MEMORY);
1236
          return;
1237
        }
1238
      resp_bread = (JTAGProxyBlockReadResponse*)buf;
1239
      for(i=0;i<msg_bread.nRegisters;i++)
1240
        {
1241
          int t_err;
1242
 
1243
          t_err = DebugGetRegister(msg_bread.address+i,&resp_bread->data[i]);
1244
          resp_bread->data[i] = htonl(resp_bread->data[i]);
1245
          err = err ? err : t_err;
1246
        }
1247
      resp_bread->status = htonl(err);
1248
      resp_bread->nRegisters = htonl(msg_bread.nRegisters);
1249
      if(gdb_write(resp_bread,len) < 0)
1250
        {
1251
          if(gdb_fd)
1252
            {
1253
              perror("gdb socket - 6");
1254
              close(gdb_fd);
1255
              gdb_fd = 0;
1256
            }
1257
          free(buf);
1258
          return;
1259
        }
1260
      free(buf);
1261
      buf = resp_bread = NULL;
1262
      break;
1263 127 chris
    case JTAG_COMMAND_CHAIN:
1264
      if(length != sizeof(msg_chain) - 8)
1265
        {
1266
          ProtocolClean(length,JTAG_PROXY_PROTOCOL_ERROR);
1267
          return;
1268
        }
1269
      buf = (char*)&msg_chain;
1270
      if(gdb_read(&buf[8],sizeof(msg_chain)-8) < 0)
1271
        {
1272
          if(gdb_fd)
1273
            {
1274
              perror("gdb socket - 7");
1275
              close(gdb_fd);
1276
              gdb_fd = 0;
1277
            }
1278
          return;
1279
        }
1280
      msg_chain.chain = htonl(msg_chain.chain);
1281
      err = DebugSetChain(msg_chain.chain);
1282
      resp_chain.status = htonl(err);
1283
      if(gdb_write(&resp_chain,sizeof(resp_chain)) < 0)
1284
        {
1285
          if(gdb_fd)
1286
            {
1287
              perror("gdb socket - 8");
1288
              close(gdb_fd);
1289
              gdb_fd = 0;
1290
            }
1291
          return;
1292
        }
1293
      break;
1294
    default:
1295
      ProtocolClean(length,JTAG_PROXY_COMMAND_NOT_IMPLEMENTED);
1296
      break;
1297
    }
1298 123 markom
}
1299 127 chris
 
1300
void ProtocolClean(int length,int32_t err)
1301
{
1302
  char buf[4096];
1303
 
1304
  err = htonl(err);
1305
  if((gdb_read(buf,length) < 0) ||
1306
      (gdb_write(&err,sizeof(err)) < 0) && gdb_fd)
1307
    {
1308
      perror("gdb socket - 9");
1309
      close(gdb_fd);
1310
      gdb_fd = 0;
1311
    }
1312
}
1313
 
1314
static int gdb_write(void* buf,int len)
1315
{
1316
  int n;
1317
  char* w_buf = (char*)buf;
1318
  struct pollfd block;
1319
 
1320
  while(len)
1321
    {
1322
      if((n = write(gdb_fd,w_buf,len)) < 0)
1323
        {
1324
          switch(errno)
1325
            {
1326
            case EWOULDBLOCK: /* or EAGAIN */
1327
              /* We've been called on a descriptor marked
1328
                 for nonblocking I/O. We better simulate
1329
                 blocking behavior. */
1330
              block.fd = gdb_fd;
1331
              block.events = POLLOUT;
1332
              block.revents = 0;
1333
              poll(&block,1,-1);
1334
              continue;
1335
            case EINTR:
1336
              continue;
1337
            case EPIPE:
1338
              close(gdb_fd);
1339
              gdb_fd = 0;
1340
              return -1;
1341
            default:
1342
              return -1;
1343
            }
1344
        }
1345
      else
1346
        {
1347
          len -= n;
1348
          w_buf += n;
1349
        }
1350
    }
1351
  return 0;
1352
}
1353
 
1354
static int gdb_read(void* buf,int len)
1355
{
1356
  int n;
1357
  char* r_buf = (char*)buf;
1358
  struct pollfd block;
1359
 
1360
  while(len)
1361
    {
1362
      if((n = read(gdb_fd,r_buf,len)) < 0)
1363
        {
1364
          switch(errno)
1365
            {
1366
            case EWOULDBLOCK: /* or EAGAIN */
1367
              /* We've been called on a descriptor marked
1368
                 for nonblocking I/O. We better simulate
1369
                 blocking behavior. */
1370
              block.fd = gdb_fd;
1371
              block.events = POLLIN;
1372
              block.revents = 0;
1373
              poll(&block,1,-1);
1374
              continue;
1375
            case EINTR:
1376
              continue;
1377
            default:
1378
              return -1;
1379
            }
1380
        }
1381
      else if(n == 0)
1382
        {
1383
          close(gdb_fd);
1384
          gdb_fd = 0;
1385
          return -1;
1386
        }
1387
      else
1388
        {
1389
          len -= n;
1390
          r_buf += n;
1391
        }
1392
    }
1393
  return 0;
1394
}

powered by: WebSVN 2.1.0

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