]> Git Repo - binutils.git/blob - gdb/remote-rdp.c
Remove ATTRIBUTE_UNUSED. Update (C).
[binutils.git] / gdb / remote-rdp.c
1 /* Remote debugging for the ARM RDP interface.
2
3    Copyright 1994, 1995, 1998, 1999, 2000, 2001, 2002 Free Software
4    Foundation, Inc.
5
6    This file is part of GDB.
7
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 2 of the License, or
11    (at your option) any later version.
12
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 59 Temple Place - Suite 330,
21    Boston, MA 02111-1307, USA.  
22
23
24  */
25
26
27 /* 
28    Much of this file (in particular the SWI stuff) is based on code by
29    David Taylor ([email protected]).
30
31    I hacked on and simplified it by removing a lot of sexy features he
32    had added, and some of the (unix specific) workarounds he'd done
33    for other GDB problems - which if they still exist should be fixed
34    in GDB, not in a remote-foo thing .  I also made it conform more to
35    the doc I have; which may be wrong.
36
37    Steve Chamberlain ([email protected]).
38  */
39
40
41 #include "defs.h"
42 #include "inferior.h"
43 #include "value.h"
44 #include "callback.h"
45 #include "command.h"
46 #include <ctype.h>
47 #include <fcntl.h>
48 #include "symfile.h"
49 #include "remote-utils.h"
50 #include "gdb_string.h"
51 #include "gdbcore.h"
52 #include "regcache.h"
53 #include "serial.h"
54
55 #ifdef HAVE_TIME_H
56 #include <time.h>
57 #endif
58
59 extern struct target_ops remote_rdp_ops;
60 static struct serial *io;
61 static host_callback *callback = &default_callback;
62
63 struct
64   {
65     int step_info;
66     int break_info;
67     int model_info;
68     int target_info;
69     int can_step;
70     char command_line[10];
71     int rdi_level;
72     int rdi_stopped_status;
73   }
74 ds;
75
76
77
78 /* Definitions for the RDP protocol. */
79
80 #define RDP_MOUTHFULL                   (1<<6)
81 #define FPU_COPRO_NUMBER                1
82
83 #define RDP_OPEN                        0
84 #define RDP_OPEN_TYPE_COLD              0
85 #define RDP_OPEN_TYPE_WARM              1
86 #define RDP_OPEN_TYPE_BAUDRATE          2
87
88 #define RDP_OPEN_BAUDRATE_9600          1
89 #define RDP_OPEN_BAUDRATE_19200         2
90 #define RDP_OPEN_BAUDRATE_38400         3
91
92 #define RDP_OPEN_TYPE_RETURN_SEX        (1<<3)
93
94 #define RDP_CLOSE                       1
95
96 #define RDP_MEM_READ                    2
97
98 #define RDP_MEM_WRITE                   3
99
100 #define RDP_CPU_READ                    4
101 #define RDP_CPU_WRITE                   5
102 #define RDP_CPU_READWRITE_MODE_CURRENT 255
103 #define RDP_CPU_READWRITE_MASK_PC       (1<<16)
104 #define RDP_CPU_READWRITE_MASK_CPSR     (1<<17)
105 #define RDP_CPU_READWRITE_MASK_SPSR     (1<<18)
106
107 #define RDP_COPRO_READ                  6
108 #define RDP_COPRO_WRITE                 7
109 #define RDP_FPU_READWRITE_MASK_FPS      (1<<8)
110
111 #define RDP_SET_BREAK                   0xa
112 #define RDP_SET_BREAK_TYPE_PC_EQUAL     0
113 #define RDP_SET_BREAK_TYPE_GET_HANDLE   (0x10)
114
115 #define RDP_CLEAR_BREAK                 0xb
116
117 #define RDP_EXEC                        0x10
118 #define RDP_EXEC_TYPE_SYNC              0
119
120 #define RDP_STEP                        0x11
121
122 #define RDP_INFO                        0x12
123 #define RDP_INFO_ABOUT_STEP             2
124 #define RDP_INFO_ABOUT_STEP_GT_1        1
125 #define RDP_INFO_ABOUT_STEP_TO_JMP      2
126 #define RDP_INFO_ABOUT_STEP_1           4
127 #define RDP_INFO_ABOUT_TARGET           0
128 #define RDP_INFO_ABOUT_BREAK            1
129 #define RDP_INFO_ABOUT_BREAK_COMP       1
130 #define RDP_INFO_ABOUT_BREAK_RANGE      2
131 #define RDP_INFO_ABOUT_BREAK_BYTE_READ  4
132 #define RDP_INFO_ABOUT_BREAK_HALFWORD_READ 8
133 #define RDP_INFO_ABOUT_BREAK_WORD_READ (1<<4)
134 #define RDP_INFO_ABOUT_BREAK_BYTE_WRITE (1<<5)
135 #define RDP_INFO_ABOUT_BREAK_HALFWORD_WRITE (1<<6)
136 #define RDP_INFO_ABOUT_BREAK_WORD_WRITE (1<<7)
137 #define RDP_INFO_ABOUT_BREAK_MASK       (1<<8)
138 #define RDP_INFO_ABOUT_BREAK_THREAD_BREAK (1<<9)
139 #define RDP_INFO_ABOUT_BREAK_THREAD_WATCH (1<<10)
140 #define RDP_INFO_ABOUT_BREAK_COND       (1<<11)
141 #define RDP_INFO_VECTOR_CATCH           (0x180)
142 #define RDP_INFO_ICEBREAKER             (7)
143 #define RDP_INFO_SET_CMDLINE            (0x300)
144
145 #define RDP_SELECT_CONFIG               (0x16)
146 #define RDI_ConfigCPU                   0
147 #define RDI_ConfigSystem                1
148 #define RDI_MatchAny                    0
149 #define RDI_MatchExactly                1
150 #define RDI_MatchNoEarlier              2
151
152 #define RDP_RESET                       0x7f
153
154 /* Returns from RDP */
155 #define RDP_RES_STOPPED                 0x20
156 #define RDP_RES_SWI                     0x21
157 #define RDP_RES_FATAL                   0x5e
158 #define RDP_RES_VALUE                   0x5f
159 #define RDP_RES_VALUE_LITTLE_ENDIAN     240
160 #define RDP_RES_VALUE_BIG_ENDIAN        241
161 #define RDP_RES_RESET                   0x7f
162 #define RDP_RES_AT_BREAKPOINT           143
163 #define RDP_RES_IDUNNO                  0xe6
164 #define RDP_OSOpReply                   0x13
165 #define RDP_OSOpWord                    2
166 #define RDP_OSOpNothing                 0
167
168 static int timeout = 2;
169
170 static char *commandline = NULL;
171
172 static int
173 remote_rdp_xfer_inferior_memory (CORE_ADDR memaddr, char *myaddr, int len,
174                                  int write, 
175                                  struct mem_attrib *attrib,
176                                  struct target_ops *target);
177
178
179 /* Stuff for talking to the serial layer. */
180
181 static unsigned char
182 get_byte (void)
183 {
184   int c = serial_readchar (io, timeout);
185
186   if (remote_debug)
187     fprintf_unfiltered (gdb_stdlog, "[%02x]\n", c);
188
189   if (c == SERIAL_TIMEOUT)
190     {
191       if (timeout == 0)
192         return (unsigned char) c;
193
194       error ("Timeout reading from remote_system");
195     }
196
197   return c;
198 }
199
200 /* Note that the target always speaks little-endian to us,
201    even if it's a big endian machine. */
202 static unsigned int
203 get_word (void)
204 {
205   unsigned int val = 0;
206   unsigned int c;
207   int n;
208   for (n = 0; n < 4; n++)
209     {
210       c = get_byte ();
211       val |= c << (n * 8);
212     }
213   return val;
214 }
215
216 static void
217 put_byte (char val)
218 {
219   if (remote_debug)
220     fprintf_unfiltered (gdb_stdlog, "(%02x)\n", val);
221   serial_write (io, &val, 1);
222 }
223
224 static void
225 put_word (int val)
226 {
227   /* We always send in little endian */
228   unsigned char b[4];
229   b[0] = val;
230   b[1] = val >> 8;
231   b[2] = val >> 16;
232   b[3] = val >> 24;
233
234   if (remote_debug)
235     fprintf_unfiltered (gdb_stdlog, "(%04x)", val);
236
237   serial_write (io, b, 4);
238 }
239
240
241
242 /* Stuff for talking to the RDP layer. */
243
244 /* This is a bit more fancy that need be so that it syncs even in nasty cases.
245
246    I'be been unable to make it reliably sync up with the change
247    baudrate open command.  It likes to sit and say it's been reset,
248    with no more action.  So I took all that code out.  I'd rather sync
249    reliably at 9600 than wait forever for a possible 19200 connection.
250
251  */
252 static void
253 rdp_init (int cold, int tty)
254 {
255   int sync = 0;
256   int type = cold ? RDP_OPEN_TYPE_COLD : RDP_OPEN_TYPE_WARM;
257   int baudtry = 9600;
258
259   time_t now = time (0);
260   time_t stop_time = now + 10;  /* Try and sync for 10 seconds, then give up */
261
262
263   while (time (0) < stop_time && !sync)
264     {
265       int restype;
266       QUIT;
267
268       serial_flush_input (io);
269       serial_flush_output (io);
270
271       if (tty)
272         printf_unfiltered ("Trying to connect at %d baud.\n", baudtry);
273
274       /*
275          ** It seems necessary to reset an EmbeddedICE to get it going.
276          ** This has the side benefit of displaying the startup banner.
277        */
278       if (cold)
279         {
280           put_byte (RDP_RESET);
281           while ((restype = serial_readchar (io, 1)) > 0)
282             {
283               switch (restype)
284                 {
285                 case SERIAL_TIMEOUT:
286                   break;
287                 case RDP_RESET:
288                   /* Sent at start of reset process: ignore */
289                   break;
290                 default:
291                   printf_unfiltered ("%c", isgraph (restype) ? restype : ' ');
292                   break;
293                 }
294             }
295
296           if (restype == 0)
297             {
298               /* Got end-of-banner mark */
299               printf_filtered ("\n");
300             }
301         }
302
303       put_byte (RDP_OPEN);
304
305       put_byte (type | RDP_OPEN_TYPE_RETURN_SEX);
306       put_word (0);
307
308       while (!sync && (restype = serial_readchar (io, 1)) > 0)
309         {
310           if (remote_debug)
311             fprintf_unfiltered (gdb_stdlog, "[%02x]\n", restype);
312
313           switch (restype)
314             {
315             case SERIAL_TIMEOUT:
316               break;
317
318             case RDP_RESET:
319               while ((restype = serial_readchar (io, 1)) == RDP_RESET)
320                 ;
321               do
322                 {
323                   printf_unfiltered ("%c", isgraph (restype) ? restype : ' ');
324                 }
325               while ((restype = serial_readchar (io, 1)) > 0);
326
327               if (tty)
328                 {
329                   printf_unfiltered ("\nThe board has sent notification that it was reset.\n");
330                   printf_unfiltered ("Waiting for it to settle down...\n");
331                 }
332               sleep (3);
333               if (tty)
334                 printf_unfiltered ("\nTrying again.\n");
335               cold = 0;
336               break;
337
338             default:
339               break;
340
341             case RDP_RES_VALUE:
342               {
343                 int resval = serial_readchar (io, 1);
344
345                 if (remote_debug)
346                   fprintf_unfiltered (gdb_stdlog, "[%02x]\n", resval);
347
348                 switch (resval)
349                   {
350                   case SERIAL_TIMEOUT:
351                     break;
352                   case RDP_RES_VALUE_LITTLE_ENDIAN:
353                     target_byte_order = BFD_ENDIAN_LITTLE;
354                     sync = 1;
355                     break;
356                   case RDP_RES_VALUE_BIG_ENDIAN:
357                     target_byte_order = BFD_ENDIAN_BIG;
358                     sync = 1;
359                     break;
360                   default:
361                     break;
362                   }
363               }
364             }
365         }
366     }
367
368   if (!sync)
369     {
370       error ("Couldn't reset the board, try pressing the reset button");
371     }
372 }
373
374
375 void
376 send_rdp (char *template,...)
377 {
378   char buf[200];
379   char *dst = buf;
380   va_list alist;
381   va_start (alist, template);
382
383   while (*template)
384     {
385       unsigned int val;
386       int *pi;
387       int *pstat;
388       char *pc;
389       int i;
390       switch (*template++)
391         {
392         case 'b':
393           val = va_arg (alist, int);
394           *dst++ = val;
395           break;
396         case 'w':
397           val = va_arg (alist, int);
398           *dst++ = val;
399           *dst++ = val >> 8;
400           *dst++ = val >> 16;
401           *dst++ = val >> 24;
402           break;
403         case 'S':
404           val = get_byte ();
405           if (val != RDP_RES_VALUE)
406             {
407               printf_unfiltered ("got bad res value of %d, %x\n", val, val);
408             }
409           break;
410         case 'V':
411           pstat = va_arg (alist, int *);
412           pi = va_arg (alist, int *);
413
414           *pstat = get_byte ();
415           /* Check the result was zero, if not read the syndrome */
416           if (*pstat)
417             {
418               *pi = get_word ();
419             }
420           break;
421         case 'Z':
422           /* Check the result code */
423           switch (get_byte ())
424             {
425             case 0:
426               /* Success */
427               break;
428             case 253:
429               /* Target can't do it; never mind */
430               printf_unfiltered ("RDP: Insufficient privilege\n");
431               return;
432             case 254:
433               /* Target can't do it; never mind */
434               printf_unfiltered ("RDP: Unimplemented message\n");
435               return;
436             case 255:
437               error ("Command garbled");
438               break;
439             default:
440               error ("Corrupt reply from target");
441               break;
442             }
443           break;
444         case 'W':
445           /* Read a word from the target */
446           pi = va_arg (alist, int *);
447           *pi = get_word ();
448           break;
449         case 'P':
450           /* Read in some bytes from the target. */
451           pc = va_arg (alist, char *);
452           val = va_arg (alist, int);
453           for (i = 0; i < val; i++)
454             {
455               pc[i] = get_byte ();
456             }
457           break;
458         case 'p':
459           /* send what's being pointed at */
460           pc = va_arg (alist, char *);
461           val = va_arg (alist, int);
462           dst = buf;
463           serial_write (io, pc, val);
464           break;
465         case '-':
466           /* Send whats in the queue */
467           if (dst != buf)
468             {
469               serial_write (io, buf, dst - buf);
470               dst = buf;
471             }
472           break;
473         case 'B':
474           pi = va_arg (alist, int *);
475           *pi = get_byte ();
476           break;
477         default:
478           internal_error (__FILE__, __LINE__, "failed internal consistency check");
479         }
480     }
481   va_end (alist);
482
483   if (dst != buf)
484     internal_error (__FILE__, __LINE__, "failed internal consistency check");
485 }
486
487
488 static int
489 rdp_write (CORE_ADDR memaddr, char *buf, int len)
490 {
491   int res;
492   int val;
493
494   send_rdp ("bww-p-SV", RDP_MEM_WRITE, memaddr, len, buf, len, &res, &val);
495
496   if (res)
497     {
498       return val;
499     }
500   return len;
501 }
502
503
504 static int
505 rdp_read (CORE_ADDR memaddr, char *buf, int len)
506 {
507   int res;
508   int val;
509   send_rdp ("bww-S-P-V",
510             RDP_MEM_READ, memaddr, len,
511             buf, len,
512             &res, &val);
513   if (res)
514     {
515       return val;
516     }
517   return len;
518 }
519
520 static void
521 rdp_fetch_one_register (int mask, char *buf)
522 {
523   int val;
524   send_rdp ("bbw-SWZ", RDP_CPU_READ, RDP_CPU_READWRITE_MODE_CURRENT, mask, &val);
525   store_signed_integer (buf, 4, val);
526 }
527
528 static void
529 rdp_fetch_one_fpu_register (int mask, char *buf)
530 {
531 #if 0
532   /* !!! Since the PIE board doesn't work as documented,
533      and it doesn't have FPU hardware anyway and since it
534      slows everything down, I've disabled this. */
535   int val;
536   if (mask == RDP_FPU_READWRITE_MASK_FPS)
537     {
538       /* this guy is only a word */
539       send_rdp ("bbw-SWZ", RDP_COPRO_READ, FPU_COPRO_NUMBER, mask, &val);
540       store_signed_integer (buf, 4, val);
541     }
542   else
543     {
544       /* There are 12 bytes long 
545          !! fixme about endianness 
546        */
547       int dummy;                /* I've seen these come back as four words !! */
548       send_rdp ("bbw-SWWWWZ", RDP_COPRO_READ, FPU_COPRO_NUMBER, mask, buf + 0, buf + 4, buf + 8, &dummy);
549     }
550 #endif
551   memset (buf, 0, MAX_REGISTER_RAW_SIZE);
552 }
553
554
555 static void
556 rdp_store_one_register (int mask, char *buf)
557 {
558   int val = extract_unsigned_integer (buf, 4);
559
560   send_rdp ("bbww-SZ",
561             RDP_CPU_WRITE, RDP_CPU_READWRITE_MODE_CURRENT, mask, val);
562 }
563
564
565 static void
566 rdp_store_one_fpu_register (int mask, char *buf)
567 {
568 #if 0
569   /* See comment in fetch_one_fpu_register */
570   if (mask == RDP_FPU_READWRITE_MASK_FPS)
571     {
572       int val = extract_unsigned_integer (buf, 4);
573       /* this guy is only a word */
574       send_rdp ("bbww-SZ", RDP_COPRO_WRITE,
575                 FPU_COPRO_NUMBER,
576                 mask, val);
577     }
578   else
579     {
580       /* There are 12 bytes long 
581          !! fixme about endianness 
582        */
583       int dummy = 0;
584       /* I've seen these come as four words, not the three advertized !! */
585       printf ("Sending mask %x\n", mask);
586       send_rdp ("bbwwwww-SZ",
587                 RDP_COPRO_WRITE,
588                 FPU_COPRO_NUMBER,
589                 mask,
590                 *(int *) (buf + 0),
591                 *(int *) (buf + 4),
592                 *(int *) (buf + 8),
593                 0);
594
595       printf ("done mask %x\n", mask);
596     }
597 #endif
598 }
599 \f
600
601 /* Convert between GDB requests and the RDP layer. */
602
603 static void
604 remote_rdp_fetch_register (int regno)
605 {
606   if (regno == -1)
607     {
608       for (regno = 0; regno < NUM_REGS; regno++)
609         remote_rdp_fetch_register (regno);
610     }
611   else
612     {
613       char buf[MAX_REGISTER_RAW_SIZE];
614       if (regno < 15)
615         rdp_fetch_one_register (1 << regno, buf);
616       else if (regno == PC_REGNUM)
617         rdp_fetch_one_register (RDP_CPU_READWRITE_MASK_PC, buf);
618       else if (regno == PS_REGNUM)
619         rdp_fetch_one_register (RDP_CPU_READWRITE_MASK_CPSR, buf);
620       else if (regno == FPS_REGNUM)
621         rdp_fetch_one_fpu_register (RDP_FPU_READWRITE_MASK_FPS, buf);
622       else if (regno >= F0_REGNUM && regno <= F7_REGNUM)
623         rdp_fetch_one_fpu_register (1 << (regno - F0_REGNUM), buf);
624       else
625         {
626           printf ("Help me with fetch reg %d\n", regno);
627         }
628       supply_register (regno, buf);
629     }
630 }
631
632
633 static void
634 remote_rdp_store_register (int regno)
635 {
636   if (regno == -1)
637     {
638       for (regno = 0; regno < NUM_REGS; regno++)
639         remote_rdp_store_register (regno);
640     }
641   else
642     {
643       char tmp[MAX_REGISTER_RAW_SIZE];
644       read_register_gen (regno, tmp);
645       if (regno < 15)
646         rdp_store_one_register (1 << regno, tmp);
647       else if (regno == PC_REGNUM)
648         rdp_store_one_register (RDP_CPU_READWRITE_MASK_PC, tmp);
649       else if (regno == PS_REGNUM)
650         rdp_store_one_register (RDP_CPU_READWRITE_MASK_CPSR, tmp);
651       else if (regno >= F0_REGNUM && regno <= F7_REGNUM)
652         rdp_store_one_fpu_register (1 << (regno - F0_REGNUM), tmp);
653       else
654         {
655           printf ("Help me with reg %d\n", regno);
656         }
657     }
658 }
659
660 static void
661 remote_rdp_kill (void)
662 {
663   callback->shutdown (callback);
664 }
665
666
667 static void
668 rdp_info (void)
669 {
670   send_rdp ("bw-S-W-Z", RDP_INFO, RDP_INFO_ABOUT_STEP,
671             &ds.step_info);
672   send_rdp ("bw-S-W-Z", RDP_INFO, RDP_INFO_ABOUT_BREAK,
673             &ds.break_info);
674   send_rdp ("bw-S-WW-Z", RDP_INFO, RDP_INFO_ABOUT_TARGET,
675             &ds.target_info,
676             &ds.model_info);
677
678   ds.can_step = ds.step_info & RDP_INFO_ABOUT_STEP_1;
679
680   ds.rdi_level = (ds.target_info >> 5) & 3;
681 }
682
683
684 static void
685 rdp_execute_start (void)
686 {
687   /* Start it off, but don't wait for it */
688   send_rdp ("bb-", RDP_EXEC, RDP_EXEC_TYPE_SYNC);
689 }
690
691
692 static void
693 rdp_set_command_line (char *command, char *args)
694 {
695   /*
696      ** We could use RDP_INFO_SET_CMDLINE to send this, but EmbeddedICE systems
697      ** don't implement that, and get all confused at the unexpected text.
698      ** Instead, just keep a copy, and send it when the target does a SWI_GetEnv
699    */
700
701   if (commandline != NULL)
702     xfree (commandline);
703
704   xasprintf (&commandline, "%s %s", command, args);
705 }
706
707 static void
708 rdp_catch_vectors (void)
709 {
710   /*
711      ** We want the target monitor to intercept the abort vectors
712      ** i.e. stop the program if any of these are used.
713    */
714   send_rdp ("bww-SZ", RDP_INFO, RDP_INFO_VECTOR_CATCH,
715   /*
716      ** Specify a bitmask including
717      **  the reset vector
718      **  the undefined instruction vector
719      **  the prefetch abort vector
720      **  the data abort vector
721      **  the address exception vector
722    */
723             (1 << 0) | (1 << 1) | (1 << 3) | (1 << 4) | (1 << 5)
724     );
725 }
726
727
728
729 #define a_byte 1
730 #define a_word 2
731 #define a_string 3
732
733
734 typedef struct
735 {
736   CORE_ADDR n;
737   const char *s;
738 }
739 argsin;
740
741 #define ABYTE 1
742 #define AWORD 2
743 #define ASTRING 3
744 #define ADDRLEN 4
745
746 #define SWI_WriteC                      0x0
747 #define SWI_Write0                      0x2
748 #define SWI_ReadC                       0x4
749 #define SWI_CLI                         0x5
750 #define SWI_GetEnv                      0x10
751 #define SWI_Exit                        0x11
752 #define SWI_EnterOS                     0x16
753
754 #define SWI_GetErrno                    0x60
755 #define SWI_Clock                       0x61
756
757 #define SWI_Time                        0x63
758 #define SWI_Remove                      0x64
759 #define SWI_Rename                      0x65
760 #define SWI_Open                        0x66
761
762 #define SWI_Close                       0x68
763 #define SWI_Write                       0x69
764 #define SWI_Read                        0x6a
765 #define SWI_Seek                        0x6b
766 #define SWI_Flen                        0x6c
767
768 #define SWI_IsTTY                       0x6e
769 #define SWI_TmpNam                      0x6f
770 #define SWI_InstallHandler              0x70
771 #define SWI_GenerateError               0x71
772
773
774 #ifndef O_BINARY
775 #define O_BINARY 0
776 #endif
777
778 static int translate_open_mode[] =
779 {
780   O_RDONLY,                     /* "r"   */
781   O_RDONLY + O_BINARY,          /* "rb"  */
782   O_RDWR,                       /* "r+"  */
783   O_RDWR + O_BINARY,            /* "r+b" */
784   O_WRONLY + O_CREAT + O_TRUNC, /* "w"   */
785   O_WRONLY + O_BINARY + O_CREAT + O_TRUNC,      /* "wb"  */
786   O_RDWR + O_CREAT + O_TRUNC,   /* "w+"  */
787   O_RDWR + O_BINARY + O_CREAT + O_TRUNC,        /* "w+b" */
788   O_WRONLY + O_APPEND + O_CREAT,        /* "a"   */
789   O_WRONLY + O_BINARY + O_APPEND + O_CREAT,     /* "ab"  */
790   O_RDWR + O_APPEND + O_CREAT,  /* "a+"  */
791   O_RDWR + O_BINARY + O_APPEND + O_CREAT        /* "a+b" */
792 };
793
794 static int
795 exec_swi (int swi, argsin *args)
796 {
797   int i;
798   char c;
799   switch (swi)
800     {
801     case SWI_WriteC:
802       callback->write_stdout (callback, &c, 1);
803       return 0;
804     case SWI_Write0:
805       for (i = 0; i < args->n; i++)
806         callback->write_stdout (callback, args->s, strlen (args->s));
807       return 0;
808     case SWI_ReadC:
809       callback->read_stdin (callback, &c, 1);
810       args->n = c;
811       return 1;
812     case SWI_CLI:
813       args->n = callback->system (callback, args->s);
814       return 1;
815     case SWI_GetErrno:
816       args->n = callback->get_errno (callback);
817       return 1;
818     case SWI_Time:
819       args->n = callback->time (callback, NULL);
820       return 1;
821
822     case SWI_Clock:
823       /* return number of centi-seconds... */
824       args->n =
825 #ifdef CLOCKS_PER_SEC
826         (CLOCKS_PER_SEC >= 100)
827         ? (clock () / (CLOCKS_PER_SEC / 100))
828         : ((clock () * 100) / CLOCKS_PER_SEC);
829 #else
830       /* presume unix... clock() returns microseconds */
831         clock () / 10000;
832 #endif
833       return 1;
834
835     case SWI_Remove:
836       args->n = callback->unlink (callback, args->s);
837       return 1;
838     case SWI_Rename:
839       args->n = callback->rename (callback, args[0].s, args[1].s);
840       return 1;
841
842     case SWI_Open:
843       /* Now we need to decode the Demon open mode */
844       i = translate_open_mode[args[1].n];
845
846       /* Filename ":tt" is special: it denotes stdin/out */
847       if (strcmp (args->s, ":tt") == 0)
848         {
849           if (i == O_RDONLY)    /* opening tty "r" */
850             args->n = 0 /* stdin */ ;
851           else
852             args->n = 1 /* stdout */ ;
853         }
854       else
855         args->n = callback->open (callback, args->s, i);
856       return 1;
857
858     case SWI_Close:
859       args->n = callback->close (callback, args->n);
860       return 1;
861
862     case SWI_Write:
863       /* Return the number of bytes *not* written */
864       args->n = args[1].n -
865         callback->write (callback, args[0].n, args[1].s, args[1].n);
866       return 1;
867
868     case SWI_Read:
869       {
870         char *copy = alloca (args[2].n);
871         int done = callback->read (callback, args[0].n, copy, args[2].n);
872         if (done > 0)
873           remote_rdp_xfer_inferior_memory (args[1].n, copy, done, 1, 0, 0);
874         args->n = args[2].n - done;
875         return 1;
876       }
877
878     case SWI_Seek:
879       /* Return non-zero on failure */
880       args->n = callback->lseek (callback, args[0].n, args[1].n, 0) < 0;
881       return 1;
882
883     case SWI_Flen:
884       {
885         long old = callback->lseek (callback, args->n, 0, SEEK_CUR);
886         args->n = callback->lseek (callback, args->n, 0, SEEK_END);
887         callback->lseek (callback, args->n, old, 0);
888         return 1;
889       }
890
891     case SWI_IsTTY:
892       args->n = callback->isatty (callback, args->n);
893       return 1;
894
895     case SWI_GetEnv:
896       if (commandline != NULL)
897         {
898           int len = strlen (commandline);
899           if (len > 255)
900             {
901               len = 255;
902               commandline[255] = '\0';
903             }
904           remote_rdp_xfer_inferior_memory (args[0].n,
905                                            commandline, len + 1, 1, 0, 0);
906         }
907       else
908         remote_rdp_xfer_inferior_memory (args[0].n, "", 1, 1, 0, 0);
909       return 1;
910
911     default:
912       return 0;
913     }
914 }
915
916
917 static void
918 handle_swi (void)
919 {
920   argsin args[3];
921   char *buf;
922   int len;
923   int count = 0;
924
925   int swino = get_word ();
926   int type = get_byte ();
927   while (type != 0)
928     {
929       switch (type & 0x3)
930         {
931         case ABYTE:
932           args[count].n = get_byte ();
933           break;
934
935         case AWORD:
936           args[count].n = get_word ();
937           break;
938
939         case ASTRING:
940           /* If the word is under 32 bytes it will be sent otherwise
941              an address to it is passed. Also: Special case of 255 */
942
943           len = get_byte ();
944           if (len > 32)
945             {
946               if (len == 255)
947                 {
948                   len = get_word ();
949                 }
950               buf = alloca (len);
951               remote_rdp_xfer_inferior_memory (get_word (),
952                                                buf,
953                                                len,
954                                                0,
955                                                0,
956                                                0);
957             }
958           else
959             {
960               int i;
961               buf = alloca (len + 1);
962               for (i = 0; i < len; i++)
963                 buf[i] = get_byte ();
964               buf[i] = 0;
965             }
966           args[count].n = len;
967           args[count].s = buf;
968           break;
969
970         default:
971           error ("Unimplemented SWI argument");
972         }
973
974       type = type >> 2;
975       count++;
976     }
977
978   if (exec_swi (swino, args))
979     {
980       /* We have two options here reply with either a byte or a word
981          which is stored in args[0].n. There is no harm in replying with
982          a word all the time, so thats what I do! */
983       send_rdp ("bbw-", RDP_OSOpReply, RDP_OSOpWord, args[0].n);
984     }
985   else
986     {
987       send_rdp ("bb-", RDP_OSOpReply, RDP_OSOpNothing);
988     }
989 }
990
991 static void
992 rdp_execute_finish (void)
993 {
994   int running = 1;
995
996   while (running)
997     {
998       int res;
999       res = serial_readchar (io, 1);
1000       while (res == SERIAL_TIMEOUT)
1001         {
1002           QUIT;
1003           printf_filtered ("Waiting for target..\n");
1004           res = serial_readchar (io, 1);
1005         }
1006
1007       switch (res)
1008         {
1009         case RDP_RES_SWI:
1010           handle_swi ();
1011           break;
1012         case RDP_RES_VALUE:
1013           send_rdp ("B", &ds.rdi_stopped_status);
1014           running = 0;
1015           break;
1016         case RDP_RESET:
1017           printf_filtered ("Target reset\n");
1018           running = 0;
1019           break;
1020         default:
1021           printf_filtered ("Ignoring %x\n", res);
1022           break;
1023         }
1024     }
1025 }
1026
1027
1028 static void
1029 rdp_execute (void)
1030 {
1031   rdp_execute_start ();
1032   rdp_execute_finish ();
1033 }
1034
1035 static int
1036 remote_rdp_insert_breakpoint (CORE_ADDR addr, char *save)
1037 {
1038   int res;
1039   if (ds.rdi_level > 0)
1040     {
1041       send_rdp ("bwb-SWB",
1042                 RDP_SET_BREAK,
1043                 addr,
1044                 RDP_SET_BREAK_TYPE_PC_EQUAL | RDP_SET_BREAK_TYPE_GET_HANDLE,
1045                 save,
1046                 &res);
1047     }
1048   else
1049     {
1050       send_rdp ("bwb-SB",
1051                 RDP_SET_BREAK,
1052                 addr,
1053                 RDP_SET_BREAK_TYPE_PC_EQUAL,
1054                 &res);
1055     }
1056   return res;
1057 }
1058
1059 static int
1060 remote_rdp_remove_breakpoint (CORE_ADDR addr, char *save)
1061 {
1062   int res;
1063   if (ds.rdi_level > 0)
1064     {
1065       send_rdp ("b-p-S-B",
1066                 RDP_CLEAR_BREAK,
1067                 save, 4,
1068                 &res);
1069     }
1070   else
1071     {
1072       send_rdp ("bw-S-B",
1073                 RDP_CLEAR_BREAK,
1074                 addr,
1075                 &res);
1076     }
1077   return res;
1078 }
1079
1080 static void
1081 rdp_step (void)
1082 {
1083   if (ds.can_step && 0)
1084     {
1085       /* The pie board can't do steps so I can't test this, and
1086          the other code will always work. */
1087       int status;
1088       send_rdp ("bbw-S-B",
1089                 RDP_STEP, 0, 1,
1090                 &status);
1091     }
1092   else
1093     {
1094       char handle[4];
1095       CORE_ADDR pc = read_register (PC_REGNUM);
1096       pc = arm_get_next_pc (pc);
1097       remote_rdp_insert_breakpoint (pc, handle);
1098       rdp_execute ();
1099       remote_rdp_remove_breakpoint (pc, handle);
1100     }
1101 }
1102
1103 static void
1104 remote_rdp_open (char *args, int from_tty)
1105 {
1106   int not_icebreaker;
1107
1108   if (!args)
1109     error_no_arg ("serial port device name");
1110
1111   baud_rate = 9600;
1112
1113   target_preopen (from_tty);
1114
1115   io = serial_open (args);
1116
1117   if (!io)
1118     perror_with_name (args);
1119
1120   serial_raw (io);
1121
1122   rdp_init (1, from_tty);
1123
1124
1125   if (from_tty)
1126     {
1127       printf_unfiltered ("Remote RDP debugging using %s at %d baud\n", args, baud_rate);
1128     }
1129
1130   rdp_info ();
1131
1132   /* Need to set up the vector interception state */
1133   rdp_catch_vectors ();
1134
1135   /*
1136      ** If it's an EmbeddedICE, we need to set the processor config.
1137      ** Assume we can always have ARM7TDI...
1138    */
1139   send_rdp ("bw-SB", RDP_INFO, RDP_INFO_ICEBREAKER, &not_icebreaker);
1140   if (!not_icebreaker)
1141     {
1142       const char *CPU = "ARM7TDI";
1143       int ICEversion;
1144       int len = strlen (CPU);
1145
1146       send_rdp ("bbbbw-p-SWZ",
1147                 RDP_SELECT_CONFIG,
1148                 RDI_ConfigCPU,  /* Aspect: set the CPU */
1149                 len,            /* The number of bytes in the name */
1150                 RDI_MatchAny,   /* We'll take whatever we get */
1151                 0,              /* We'll take whatever version's there */
1152                 CPU, len,
1153                 &ICEversion);
1154     }
1155
1156   /* command line initialised on 'run' */
1157
1158   push_target (&remote_rdp_ops);
1159
1160   callback->init (callback);
1161   flush_cached_frames ();
1162   registers_changed ();
1163   stop_pc = read_pc ();
1164   set_current_frame (create_new_frame (read_fp (), stop_pc));
1165   select_frame (get_current_frame (), 0);
1166   print_stack_frame (selected_frame, -1, 1);
1167 }
1168
1169
1170
1171 /* Close out all files and local state before this target loses control. */
1172
1173 static void
1174 remote_rdp_close (int quitting)
1175 {
1176   callback->shutdown (callback);
1177   if (io)
1178     serial_close (io);
1179   io = 0;
1180 }
1181
1182
1183 /* Resume execution of the target process.  STEP says whether to single-step
1184    or to run free; SIGGNAL is the signal value (e.g. SIGINT) to be given
1185    to the target, or zero for no signal.  */
1186
1187 static void
1188 remote_rdp_resume (ptid_t ptid, int step, enum target_signal siggnal)
1189 {
1190   if (step)
1191     rdp_step ();
1192   else
1193     rdp_execute ();
1194 }
1195
1196 /* Wait for inferior process to do something.  Return pid of child,
1197    or -1 in case of error; store status through argument pointer STATUS,
1198    just as `wait' would.  */
1199
1200 static ptid_t
1201 remote_rdp_wait (ptid_t ptid, struct target_waitstatus *status)
1202 {
1203   switch (ds.rdi_stopped_status)
1204     {
1205     default:
1206     case RDP_RES_RESET:
1207     case RDP_RES_SWI:
1208       status->kind = TARGET_WAITKIND_EXITED;
1209       status->value.integer = read_register (0);
1210       break;
1211     case RDP_RES_AT_BREAKPOINT:
1212       status->kind = TARGET_WAITKIND_STOPPED;
1213       /* The signal in sigrc is a host signal.  That probably
1214          should be fixed.  */
1215       status->value.sig = TARGET_SIGNAL_TRAP;
1216       break;
1217 #if 0
1218     case rdp_signalled:
1219       status->kind = TARGET_WAITKIND_SIGNALLED;
1220       /* The signal in sigrc is a host signal.  That probably
1221          should be fixed.  */
1222       status->value.sig = target_signal_from_host (sigrc);
1223       break;
1224 #endif
1225     }
1226
1227   return inferior_ptid;
1228 }
1229
1230 /* Get ready to modify the registers array.  On machines which store
1231    individual registers, this doesn't need to do anything.  On machines
1232    which store all the registers in one fell swoop, this makes sure
1233    that registers contains all the registers from the program being
1234    debugged.  */
1235
1236 static void
1237 remote_rdp_prepare_to_store (void)
1238 {
1239   /* Do nothing, since we can store individual regs */
1240 }
1241
1242 /* Transfer LEN bytes between GDB address MYADDR and target address
1243    MEMADDR.  If WRITE is non-zero, transfer them to the target,
1244    otherwise transfer them from the target.  TARGET is unused.
1245
1246    Returns the number of bytes transferred. */
1247
1248 static int
1249 remote_rdp_xfer_inferior_memory (CORE_ADDR memaddr, char *myaddr, int len,
1250                                  int write, struct mem_attrib *attrib,
1251                                  struct target_ops *target)
1252 {
1253   /* I infer from D Taylor's code that there's a limit on the amount
1254      we can transfer in one chunk.. */
1255   int done = 0;
1256   while (done < len)
1257     {
1258       int justdone;
1259       int thisbite = len - done;
1260       if (thisbite > RDP_MOUTHFULL)
1261         thisbite = RDP_MOUTHFULL;
1262
1263       QUIT;
1264
1265       if (write)
1266         {
1267           justdone = rdp_write (memaddr + done, myaddr + done, thisbite);
1268         }
1269       else
1270         {
1271           justdone = rdp_read (memaddr + done, myaddr + done, thisbite);
1272         }
1273
1274       done += justdone;
1275
1276       if (justdone != thisbite)
1277         break;
1278     }
1279   return done;
1280 }
1281
1282
1283
1284 struct yn
1285 {
1286   const char *name;
1287   int bit;
1288 };
1289 static struct yn stepinfo[] =
1290 {
1291   {"Step more than one instruction", RDP_INFO_ABOUT_STEP_GT_1},
1292   {"Step to jump", RDP_INFO_ABOUT_STEP_TO_JMP},
1293   {"Step one instruction", RDP_INFO_ABOUT_STEP_1},
1294   {0}
1295 };
1296
1297 static struct yn breakinfo[] =
1298 {
1299   {"comparison breakpoints supported", RDP_INFO_ABOUT_BREAK_COMP},
1300   {"range breakpoints supported", RDP_INFO_ABOUT_BREAK_RANGE},
1301   {"watchpoints for byte reads supported", RDP_INFO_ABOUT_BREAK_BYTE_READ},
1302   {"watchpoints for half-word reads supported", RDP_INFO_ABOUT_BREAK_HALFWORD_READ},
1303   {"watchpoints for word reads supported", RDP_INFO_ABOUT_BREAK_WORD_READ},
1304   {"watchpoints for byte writes supported", RDP_INFO_ABOUT_BREAK_BYTE_WRITE},
1305   {"watchpoints for half-word writes supported", RDP_INFO_ABOUT_BREAK_HALFWORD_WRITE},
1306   {"watchpoints for word writes supported", RDP_INFO_ABOUT_BREAK_WORD_WRITE},
1307   {"mask break/watch-points supported", RDP_INFO_ABOUT_BREAK_MASK},
1308 {"thread-specific breakpoints supported", RDP_INFO_ABOUT_BREAK_THREAD_BREAK},
1309 {"thread-specific watchpoints supported", RDP_INFO_ABOUT_BREAK_THREAD_WATCH},
1310   {"conditional breakpoints supported", RDP_INFO_ABOUT_BREAK_COND},
1311   {0}
1312 };
1313
1314
1315 static void
1316 dump_bits (struct yn *t, int info)
1317 {
1318   while (t->name)
1319     {
1320       printf_unfiltered ("  %-45s : %s\n", t->name, (info & t->bit) ? "Yes" : "No");
1321       t++;
1322     }
1323 }
1324
1325 static void
1326 remote_rdp_files_info (struct target_ops *target)
1327 {
1328   printf_filtered ("Target capabilities:\n");
1329   dump_bits (stepinfo, ds.step_info);
1330   dump_bits (breakinfo, ds.break_info);
1331   printf_unfiltered ("target level RDI %x\n", (ds.target_info >> 5) & 3);
1332 }
1333
1334
1335 static void
1336 remote_rdp_create_inferior (char *exec_file, char *allargs, char **env)
1337 {
1338   CORE_ADDR entry_point;
1339
1340   if (exec_file == 0 || exec_bfd == 0)
1341     error ("No executable file specified.");
1342
1343   entry_point = (CORE_ADDR) bfd_get_start_address (exec_bfd);
1344
1345   remote_rdp_kill ();
1346   remove_breakpoints ();
1347   init_wait_for_inferior ();
1348
1349   /* This gives us a chance to set up the command line */
1350   rdp_set_command_line (exec_file, allargs);
1351
1352   inferior_ptid = pid_to_ptid (42);
1353   insert_breakpoints ();        /* Needed to get correct instruction in cache */
1354
1355   /*
1356      ** RDP targets don't provide any facility to set the top of memory,
1357      ** so we don't bother to look for MEMSIZE in the environment.
1358    */
1359
1360   /* Let's go! */
1361   proceed (entry_point, TARGET_SIGNAL_DEFAULT, 0);
1362 }
1363
1364 /* Accept any stray run/attach commands */
1365 static int
1366 remote_rdp_can_run (void)
1367 {
1368   return 1;
1369 }
1370
1371 /* Attach doesn't need to do anything */
1372 static void
1373 remote_rdp_attach (char *args, int from_tty)
1374 {
1375   return;
1376 }
1377
1378 /* Define the target subroutine names */
1379
1380 struct target_ops remote_rdp_ops;
1381
1382 static void
1383 init_remote_rdp_ops (void)
1384 {
1385   remote_rdp_ops.to_shortname = "rdp";
1386   remote_rdp_ops.to_longname = "Remote Target using the RDProtocol";
1387   remote_rdp_ops.to_doc = "Use a remote ARM system which uses the ARM Remote Debugging Protocol";
1388   remote_rdp_ops.to_open = remote_rdp_open;
1389   remote_rdp_ops.to_close = remote_rdp_close;
1390   remote_rdp_ops.to_attach = remote_rdp_attach;
1391   remote_rdp_ops.to_post_attach = NULL;
1392   remote_rdp_ops.to_require_attach = NULL;
1393   remote_rdp_ops.to_detach = NULL;
1394   remote_rdp_ops.to_require_detach = NULL;
1395   remote_rdp_ops.to_resume = remote_rdp_resume;
1396   remote_rdp_ops.to_wait = remote_rdp_wait;
1397   remote_rdp_ops.to_post_wait = NULL;
1398   remote_rdp_ops.to_fetch_registers = remote_rdp_fetch_register;
1399   remote_rdp_ops.to_store_registers = remote_rdp_store_register;
1400   remote_rdp_ops.to_prepare_to_store = remote_rdp_prepare_to_store;
1401   remote_rdp_ops.to_xfer_memory = remote_rdp_xfer_inferior_memory;
1402   remote_rdp_ops.to_files_info = remote_rdp_files_info;
1403   remote_rdp_ops.to_insert_breakpoint = remote_rdp_insert_breakpoint;
1404   remote_rdp_ops.to_remove_breakpoint = remote_rdp_remove_breakpoint;
1405   remote_rdp_ops.to_terminal_init = NULL;
1406   remote_rdp_ops.to_terminal_inferior = NULL;
1407   remote_rdp_ops.to_terminal_ours_for_output = NULL;
1408   remote_rdp_ops.to_terminal_ours = NULL;
1409   remote_rdp_ops.to_terminal_info = NULL;
1410   remote_rdp_ops.to_kill = remote_rdp_kill;
1411   remote_rdp_ops.to_load = generic_load;
1412   remote_rdp_ops.to_lookup_symbol = NULL;
1413   remote_rdp_ops.to_create_inferior = remote_rdp_create_inferior;
1414   remote_rdp_ops.to_post_startup_inferior = NULL;
1415   remote_rdp_ops.to_acknowledge_created_inferior = NULL;
1416   remote_rdp_ops.to_clone_and_follow_inferior = NULL;
1417   remote_rdp_ops.to_post_follow_inferior_by_clone = NULL;
1418   remote_rdp_ops.to_insert_fork_catchpoint = NULL;
1419   remote_rdp_ops.to_remove_fork_catchpoint = NULL;
1420   remote_rdp_ops.to_insert_vfork_catchpoint = NULL;
1421   remote_rdp_ops.to_remove_vfork_catchpoint = NULL;
1422   remote_rdp_ops.to_has_forked = NULL;
1423   remote_rdp_ops.to_has_vforked = NULL;
1424   remote_rdp_ops.to_can_follow_vfork_prior_to_exec = NULL;
1425   remote_rdp_ops.to_post_follow_vfork = NULL;
1426   remote_rdp_ops.to_insert_exec_catchpoint = NULL;
1427   remote_rdp_ops.to_remove_exec_catchpoint = NULL;
1428   remote_rdp_ops.to_has_execd = NULL;
1429   remote_rdp_ops.to_reported_exec_events_per_exec_call = NULL;
1430   remote_rdp_ops.to_has_exited = NULL;
1431   remote_rdp_ops.to_mourn_inferior = generic_mourn_inferior;
1432   remote_rdp_ops.to_can_run = remote_rdp_can_run;
1433   remote_rdp_ops.to_notice_signals = 0;
1434   remote_rdp_ops.to_thread_alive = 0;
1435   remote_rdp_ops.to_stop = 0;
1436   remote_rdp_ops.to_pid_to_exec_file = NULL;
1437   remote_rdp_ops.to_stratum = process_stratum;
1438   remote_rdp_ops.DONT_USE = NULL;
1439   remote_rdp_ops.to_has_all_memory = 1;
1440   remote_rdp_ops.to_has_memory = 1;
1441   remote_rdp_ops.to_has_stack = 1;
1442   remote_rdp_ops.to_has_registers = 1;
1443   remote_rdp_ops.to_has_execution = 1;
1444   remote_rdp_ops.to_sections = NULL;
1445   remote_rdp_ops.to_sections_end = NULL;
1446   remote_rdp_ops.to_magic = OPS_MAGIC;
1447 }
1448
1449 void
1450 _initialize_remote_rdp (void)
1451 {
1452   init_remote_rdp_ops ();
1453   add_target (&remote_rdp_ops);
1454 }
This page took 0.103616 seconds and 4 git commands to generate.