xref: /openbsd-src/gnu/usr.bin/binutils/gdb/remote-rdp.c (revision b2ea75c1b17e1a9a339660e7ed45cd24946b230e)
1 /* Remote debugging for the ARM RDP interface.
2    Copyright 1994, 1995 Free Software Foundation, Inc.
3 
4    This file is part of GDB.
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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19 
20 
21  */
22 
23 
24 /*
25    Much of this file (in particular the SWI stuff) is based on code by
26    David Taylor (djt1000@uk.ac.cam.hermes).
27 
28    I hacked on and simplified it by removing a lot of sexy features he
29    had added, and some of the (unix specific) workarounds he'd done
30    for other GDB problems - which if they still exist should be fixed
31    in GDB, not in a remote-foo thing .  I also made it conform more to
32    the doc I have; which may be wrong.
33 
34    Steve Chamberlain (sac@cygnus.com).
35  */
36 
37 
38 #include "defs.h"
39 #include "inferior.h"
40 #include "wait.h"
41 #include "value.h"
42 #include "callback.h"
43 #include "command.h"
44 #ifdef ANSI_PROTOTYPES
45 #include <stdarg.h>
46 #else
47 #include <varargs.h>
48 #endif
49 #include <ctype.h>
50 #include <fcntl.h>
51 #include "symfile.h"
52 #include "remote-utils.h"
53 #include "gdb_string.h"
54 #ifdef HAVE_UNISTD_H
55 #include <unistd.h>
56 #endif
57 
58 
59 extern struct target_ops remote_rdp_ops;
60 static serial_t 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 
142 #define RDP_RESET 			0x7f
143 
144 /* Returns from RDP */
145 #define RDP_RES_STOPPED 		0x20
146 #define RDP_RES_SWI 			0x21
147 #define RDP_RES_FATAL 			0x5e
148 #define RDP_RES_VALUE 			0x5f
149 #define RDP_RES_VALUE_LITTLE_ENDIAN     240
150 #define RDP_RES_VALUE_BIG_ENDIAN 	241
151 #define RDP_RES_RESET			0x7f
152 #define RDP_RES_AT_BREAKPOINT    	143
153 #define RDP_RES_IDUNNO			0xe6
154 #define RDP_OSOpReply           	0x13
155 #define RDP_OSOpWord            	2
156 #define RDP_OSOpNothing         	0
157 
158 static int timeout = 2;
159 
160 static int
161 remote_rdp_xfer_inferior_memory PARAMS ((CORE_ADDR memaddr,
162 					 char *myaddr,
163 					 int len,
164 					 int write,
165 					 struct target_ops * target));
166 
167 
168 /* Stuff for talking to the serial layer. */
169 
170 static unsigned char
171 get_byte ()
172 {
173   int c = SERIAL_READCHAR (io, timeout);
174 
175   if (remote_debug)
176     printf ("[%02x]\n", c);
177 
178   if (c == SERIAL_TIMEOUT)
179     {
180       if (timeout == 0)
181 	return (unsigned char) c;
182 
183       error ("Timeout reading from remote_system");
184     }
185 
186   return c;
187 }
188 
189 /* Note that the target always speaks little-endian to us,
190    even if it's a big endian machine. */
191 static unsigned int
192 get_word ()
193 {
194   unsigned int val = 0;
195   unsigned int c;
196   int n;
197   for (n = 0; n < 4; n++)
198     {
199       c = get_byte ();
200       val |= c << (n * 8);
201     }
202   return val;
203 }
204 
205 static void
206 put_byte (val)
207      char val;
208 {
209   if (remote_debug)
210     printf ("(%02x)\n", val);
211   SERIAL_WRITE (io, &val, 1);
212 }
213 
214 static void
215 put_word (val)
216      int val;
217 {
218   /* We always send in little endian */
219   unsigned char b[4];
220   b[0] = val;
221   b[1] = val >> 8;
222   b[2] = val >> 16;
223   b[3] = val >> 24;
224 
225   if (remote_debug)
226     printf ("(%04x)", val);
227 
228   SERIAL_WRITE (io, b, 4);
229 }
230 
231 
232 
233 /* Stuff for talking to the RDP layer. */
234 
235 /* This is a bit more fancy that need be so that it syncs even in nasty cases.
236 
237    I'be been unable to make it reliably sync up with the change
238    baudrate open command.  It likes to sit and say it's been reset,
239    with no more action.  So I took all that code out.  I'd rather sync
240    reliably at 9600 than wait forever for a possible 19200 connection.
241 
242  */
243 static void
244 rdp_init (cold, tty)
245      int cold;
246      int tty;
247 {
248   int sync = 0;
249   int type = cold ? RDP_OPEN_TYPE_COLD : RDP_OPEN_TYPE_WARM;
250   int baudtry = 9600;
251 
252   time_t now = time (0);
253   time_t stop_time = now + 10;	/* Try and sync for 10 seconds, then give up */
254 
255 
256   while (time (0) < stop_time && !sync)
257     {
258       int restype;
259       QUIT;
260 
261       SERIAL_FLUSH_INPUT (io);
262       SERIAL_FLUSH_OUTPUT (io);
263 
264       if (tty)
265 	printf_unfiltered ("Trying to connect at %d baud.\n", baudtry);
266       put_byte (RDP_OPEN);
267 
268       put_byte (type | RDP_OPEN_TYPE_RETURN_SEX);
269       put_word (0);
270 
271       while (!sync && (restype = SERIAL_READCHAR (io, 1)) > 0)
272 	{
273 	  if (remote_debug)
274 	    printf_unfiltered ("[%02x]\n", restype);
275 
276 	  switch (restype)
277 	    {
278 	    case SERIAL_TIMEOUT:
279 	      break;
280 	    case RDP_RESET:
281 	      while ((restype = SERIAL_READCHAR (io, 1)) == RDP_RESET)
282 		;
283 	      while ((restype = SERIAL_READCHAR (io, 1)) > 0)
284 		{
285 		  printf_unfiltered ("%c", isgraph (restype) ? restype : ' ');
286 		}
287 	      while ((restype = SERIAL_READCHAR (io, 1)) > 0)
288 		;
289 	      if (tty)
290 		{
291 		  printf_unfiltered ("\nThe board has sent notification that it was reset.\n");
292 		  printf_unfiltered ("Waiting for it to settle down...\n");
293 		}
294 	      sleep (3);
295 	      if (tty)
296 		printf_unfiltered ("\nTrying again.\n");
297 	      break;
298 	    default:
299 	      break;
300 	    case RDP_RES_VALUE:
301 	      {
302 		int resval = SERIAL_READCHAR (io, 1);
303 		switch (resval)
304 		  {
305 		  case SERIAL_TIMEOUT:
306 		    break;
307 		  case RDP_RES_VALUE_LITTLE_ENDIAN:
308 		    target_byte_order = LITTLE_ENDIAN;
309 		    sync = 1;
310 		    break;
311 		  case RDP_RES_VALUE_BIG_ENDIAN:
312 		    target_byte_order = BIG_ENDIAN;
313 		    sync = 1;
314 		    break;
315 		  default:
316 		    break;
317 		  }
318 	      }
319 	    }
320 	}
321     }
322 
323   if (!sync)
324     {
325       error ("Couldn't reset the board, try pressing the reset button");
326     }
327 }
328 
329 
330 #ifdef ANSI_PROTOTYPES
331 void
332 send_rdp (char *template,...)
333 #else
334 void
335 send_rdp (char *template, va_alist)
336      va_dcl
337 #endif
338 {
339   char buf[200];
340   char *dst = buf;
341   va_list alist;
342 #ifdef ANSI_PROTOTYPES
343   va_start (alist, template);
344 #else
345   va_start (alist);
346 #endif
347 
348   while (*template)
349     {
350       unsigned int val;
351       int *pi;
352       int *pstat;
353       char *pc;
354       int i;
355       switch (*template++)
356 	{
357 	case 'b':
358 	  val = va_arg (alist, int);
359 	  *dst++ = val;
360 	  break;
361 	case 'w':
362 	  val = va_arg (alist, int);
363 	  *dst++ = val;
364 	  *dst++ = val >> 8;
365 	  *dst++ = val >> 16;
366 	  *dst++ = val >> 24;
367 	  break;
368 	case 'S':
369 	  val = get_byte ();
370 	  if (val != RDP_RES_VALUE)
371 	    {
372 	      printf_unfiltered ("got bad res value of %d, %x\n", val, val);
373 	    }
374 	  break;
375 	case 'V':
376 	  pstat = va_arg (alist, int *);
377 	  pi = va_arg (alist, int *);
378 
379 	  *pstat = get_byte ();
380 	  /* Check the result was zero, if not read the syndrome */
381 	  if (*pstat)
382 	    {
383 	      *pi = get_word ();
384 	    }
385 	  break;
386 	case 'Z':
387 	  /* Check the result code, error if not zero */
388 	  if (get_byte ())
389 	    error ("Command garbled");
390 	  break;
391 	case 'W':
392 	  /* Read a word from the target */
393 	  pi = va_arg (alist, int *);
394 	  *pi = get_word ();
395 	  break;
396 	case 'P':
397 	  /* Read in some bytes from the target. */
398 	  pc = va_arg (alist, char *);
399 	  val = va_arg (alist, int);
400 	  for (i = 0; i < val; i++)
401 	    {
402 	      pc[i] = get_byte ();
403 	    }
404 	  break;
405 	case 'p':
406 	  /* send what's being pointed at */
407 	  pc = va_arg (alist, char *);
408 	  val = va_arg (alist, int);
409 	  dst = buf;
410 	  SERIAL_WRITE (io, pc, val);
411 	  break;
412 	case '-':
413 	  /* Send whats in the queue */
414 	  if (dst != buf)
415 	    {
416 	      SERIAL_WRITE (io, buf, dst - buf);
417 	      dst = buf;
418 	    }
419 	  break;
420 	case 'B':
421 	  pi = va_arg (alist, int *);
422 	  *pi = get_byte ();
423 	  break;
424 	default:
425 	  abort ();
426 	}
427     }
428   va_end (args);
429 
430   if (dst != buf)
431     abort ();
432 }
433 
434 
435 static int
436 rdp_write (memaddr, buf, len)
437      CORE_ADDR memaddr;
438      char *buf;
439      int len;
440 {
441   int res;
442   int val;
443 
444   send_rdp ("bww-p-SV", RDP_MEM_WRITE, memaddr, len, buf, len, &res, &val);
445 
446   if (res)
447     {
448       return val;
449     }
450   return len;
451 }
452 
453 
454 static int
455 rdp_read (memaddr, buf, len)
456      CORE_ADDR memaddr;
457      char *buf;
458      int len;
459 {
460   int res;
461   int val;
462   send_rdp ("bww-S-P-V",
463 	    RDP_MEM_READ, memaddr, len,
464 	    buf, len,
465 	    &res, &val);
466   if (res)
467     {
468       return val;
469     }
470   return len;
471 }
472 
473 static void
474 rdp_fetch_one_register (mask, buf)
475      int mask;
476      char *buf;
477 {
478   int val;
479   send_rdp ("bbw-SWZ", RDP_CPU_READ, RDP_CPU_READWRITE_MODE_CURRENT, mask, &val);
480   store_signed_integer (buf, 4, val);
481 }
482 
483 static void
484 rdp_fetch_one_fpu_register (mask, buf)
485      int mask;
486      char *buf;
487 {
488 #if 0
489   /* !!! Since the PIE board doesn't work as documented,
490      and it doesn't have FPU hardware anyway and since it
491      slows everything down, I've disabled this. */
492   int val;
493   if (mask == RDP_FPU_READWRITE_MASK_FPS)
494     {
495       /* this guy is only a word */
496       send_rdp ("bbw-SWZ", RDP_COPRO_READ, FPU_COPRO_NUMBER, mask, &val);
497       store_signed_integer (buf, 4, val);
498     }
499   else
500     {
501       /* There are 12 bytes long
502          !! fixme about endianness
503        */
504       int dummy;		/* I've seen these come back as four words !! */
505       send_rdp ("bbw-SWWWWZ", RDP_COPRO_READ, FPU_COPRO_NUMBER, mask, buf + 0, buf + 4, buf + 8, &dummy);
506     }
507 #endif
508   memset (buf, 0, MAX_REGISTER_RAW_SIZE);
509 }
510 
511 
512 static void
513 rdp_store_one_register (mask, buf)
514      int mask;
515      char *buf;
516 {
517   int val = extract_unsigned_integer (buf, 4);
518 
519   send_rdp ("bbww-SZ",
520 	    RDP_CPU_WRITE, RDP_CPU_READWRITE_MODE_CURRENT, mask, val);
521 }
522 
523 
524 static void
525 rdp_store_one_fpu_register (mask, buf)
526      int mask;
527      char *buf;
528 {
529 #if 0
530   /* See comment in fetch_one_fpu_register */
531   if (mask == RDP_FPU_READWRITE_MASK_FPS)
532     {
533       int val = extract_unsigned_integer (buf, 4);
534       /* this guy is only a word */
535       send_rdp ("bbww-SZ", RDP_COPRO_WRITE,
536 		FPU_COPRO_NUMBER,
537 		mask, val);
538     }
539   else
540     {
541       /* There are 12 bytes long
542          !! fixme about endianness
543        */
544       int dummy = 0;
545       /* I've seen these come as four words, not the three advertized !! */
546       printf ("Sending mask %x\n", mask);
547       send_rdp ("bbwwwww-SZ",
548 		RDP_COPRO_WRITE,
549 		FPU_COPRO_NUMBER,
550 		mask,
551 		*(int *) (buf + 0),
552 		*(int *) (buf + 4),
553 		*(int *) (buf + 8),
554 		0);
555 
556       printf ("done mask %x\n", mask);
557     }
558 #endif
559 }
560 
561 
562 /* Convert between GDB requests and the RDP layer. */
563 
564 static void
565 remote_rdp_fetch_register (regno)
566      int regno;
567 {
568   if (regno == -1)
569     {
570       for (regno = 0; regno < NUM_REGS; regno++)
571 	remote_rdp_fetch_register (regno);
572     }
573   else
574     {
575       char buf[MAX_REGISTER_RAW_SIZE];
576       if (regno < 15)
577 	rdp_fetch_one_register (1 << regno, buf);
578       else if (regno == PC_REGNUM)
579 	rdp_fetch_one_register (RDP_CPU_READWRITE_MASK_PC, buf);
580       else if (regno == PS_REGNUM)
581 	rdp_fetch_one_register (RDP_CPU_READWRITE_MASK_CPSR, buf);
582       else if (regno == FPS_REGNUM)
583 	rdp_fetch_one_fpu_register (RDP_FPU_READWRITE_MASK_FPS, buf);
584       else if (regno >= F0_REGNUM && regno <= F7_REGNUM)
585 	rdp_fetch_one_fpu_register (1 << (regno - F0_REGNUM), buf);
586       else
587 	{
588 	  printf ("Help me with fetch reg %d\n", regno);
589 	}
590       supply_register (regno, buf);
591     }
592 }
593 
594 
595 static void
596 remote_rdp_store_register (regno)
597      int regno;
598 {
599   if (regno == -1)
600     {
601       for (regno = 0; regno < NUM_REGS; regno++)
602 	remote_rdp_store_register (regno);
603     }
604   else
605     {
606       char tmp[MAX_REGISTER_RAW_SIZE];
607       read_register_gen (regno, tmp);
608       if (regno < 15)
609 	rdp_store_one_register (1 << regno, tmp);
610       else if (regno == PC_REGNUM)
611 	rdp_store_one_register (RDP_CPU_READWRITE_MASK_PC, tmp);
612       else if (regno == PS_REGNUM)
613 	rdp_store_one_register (RDP_CPU_READWRITE_MASK_CPSR, tmp);
614       else if (regno >= F0_REGNUM && regno <= F7_REGNUM)
615 	rdp_store_one_fpu_register (1 << (regno - F0_REGNUM), tmp);
616       else
617 	{
618 	  printf ("Help me with reg %d\n", regno);
619 	}
620     }
621 }
622 
623 static void
624 remote_rdp_kill ()
625 {
626   callback->shutdown (callback);
627 }
628 
629 
630 static void
631 rdp_info ()
632 {
633   send_rdp ("bw-S-W-Z", RDP_INFO, RDP_INFO_ABOUT_STEP,
634 	    &ds.step_info);
635   send_rdp ("bw-S-W-Z", RDP_INFO, RDP_INFO_ABOUT_BREAK,
636 	    &ds.break_info);
637   send_rdp ("bw-S-WW-Z", RDP_INFO, RDP_INFO_ABOUT_TARGET,
638 	    &ds.target_info,
639 	    &ds.model_info);
640 
641   ds.can_step = ds.step_info & RDP_INFO_ABOUT_STEP_1;
642 
643   ds.rdi_level = (ds.target_info >> 5) & 3;
644 }
645 
646 
647 static void
648 rdp_execute_start ()
649 {
650   /* Start it off, but don't wait for it */
651   send_rdp ("bb-", RDP_EXEC, RDP_EXEC_TYPE_SYNC);
652 }
653 
654 
655 
656 #define a_byte 1
657 #define a_word 2
658 #define a_string 3
659 
660 
661 typedef struct
662 {
663   CORE_ADDR n;
664   const char *s;
665 }
666 argsin;
667 
668 #define ABYTE 1
669 #define AWORD 2
670 #define ASTRING 3
671 #define ADDRLEN 4
672 
673 #define SWI_WriteC                      0x0
674 #define SWI_Write0                      0x2
675 #define SWI_ReadC                       0x4
676 #define SWI_CLI                         0x5
677 #define SWI_GetEnv                      0x10
678 #define SWI_Exit                        0x11
679 #define SWI_EnterOS                     0x16
680 
681 #define SWI_GetErrno                    0x60
682 #define SWI_Clock                       0x61
683 
684 #define SWI_Time                        0x63
685 #define SWI_Remove                      0x64
686 #define SWI_Rename                      0x65
687 #define SWI_Open                        0x66
688 
689 #define SWI_Close                       0x68
690 #define SWI_Write                       0x69
691 #define SWI_Read                        0x6a
692 #define SWI_Seek                        0x6b
693 #define SWI_Flen                        0x6c
694 
695 #define SWI_IsTTY                       0x6e
696 #define SWI_TmpNam                      0x6f
697 #define SWI_InstallHandler              0x70
698 #define SWI_GenerateError               0x71
699 
700 
701 static int
702 exec_swi (swi, args)
703      int swi;
704      argsin *args;
705 {
706   int i;
707   char c;
708   switch (swi)
709     {
710     case SWI_WriteC:
711       callback->write_stdout (callback, &c, 1);
712       return 0;
713     case SWI_Write0:
714       for (i = 0; i < args->n; i++)
715 	callback->write_stdout (callback, args->s, strlen (args->s));
716       return 0;
717     case SWI_ReadC:
718       callback->read_stdin (callback, &c, 1);
719       args->n = c;
720       return 1;
721     case SWI_CLI:
722       args->n = callback->system (callback, args->s);
723       return 1;
724     case SWI_GetErrno:
725       args->n = callback->get_errno (callback);
726       return 1;
727     case SWI_Time:
728       args->n = callback->time (callback, NULL);
729       return 1;
730     case SWI_Remove:
731       args->n = callback->unlink (callback, args->s);
732       return 1;
733     case SWI_Rename:
734       args->n = callback->rename (callback, args[0].s, args[1].s);
735       return 1;
736     case SWI_Open:
737       i = 0;
738 
739 #ifdef O_BINARY
740       if (args[1].n & 1)
741 	i |= O_BINARY;
742 #endif
743       if (args[1].n & 2)
744 	i |= O_RDWR;
745 
746       if (args[1].n & 4)
747 	{
748 	  i |= O_CREAT;
749 	}
750 
751       if (args[1].n & 8)
752 	i |= O_APPEND;
753 
754       args->n = callback->open (callback, args->s, i);
755       return 1;
756 
757     case SWI_Close:
758       args->n = callback->close (callback, args->n);
759       return 1;
760 
761     case SWI_Write:
762       args->n = callback->write (callback, args[0].n, args[1].s, args[1].n);
763       return 1;
764     case SWI_Read:
765       {
766 	char *copy = alloca (args[2].n);
767 	int done = callback->read (callback, args[0].n, copy, args[2].n);
768 	if (done > 0)
769 	  remote_rdp_xfer_inferior_memory (args[0].n, copy, done, 1, 0);
770 	args->n -= done;
771 	return 1;
772       }
773 
774     case SWI_Seek:
775       args->n = callback->lseek (callback, args[0].n, args[1].n, 0) >= 0;
776       return 1;
777     case SWI_Flen:
778       {
779 	long old = callback->lseek (callback, args->n, 1, 1);
780 	args->n = callback->lseek (callback, args->n, 2, 0);
781 	callback->lseek (callback, args->n, old, 0);
782 	return 1;
783       }
784 
785     case SWI_IsTTY:
786       args->n = callback->isatty (callback, args->n);
787       return 1;
788 
789     default:
790       return 0;
791     }
792 }
793 
794 
795 static void
796 handle_swi ()
797 {
798   argsin args[3];
799   char *buf;
800   int len;
801   int count = 0;
802 
803   int swino = get_word ();
804   int type = get_byte ();
805   while (type != 0)
806     {
807       switch (type & 0x3)
808 	{
809 	case ABYTE:
810 	  args[count].n = get_byte ();
811 	  break;
812 
813 	case AWORD:
814 	  args[count].n = get_word ();
815 	  break;
816 
817 	case ASTRING:
818 	  /* If the word is under 32 bytes it will be sent otherwise
819 	     an address to it is passed. Also: Special case of 255 */
820 
821 	  len = get_byte ();
822 	  if (len > 32)
823 	    {
824 	      if (len == 255)
825 		{
826 		  len = get_word ();
827 		}
828 	      buf = alloca (len);
829 	      remote_rdp_xfer_inferior_memory (get_word (),
830 					       buf,
831 					       len,
832 					       0,
833 					       0);
834 	    }
835 	  else
836 	    {
837 	      int i;
838 	      buf = alloca (len + 1);
839 	      for (i = 0; i < len; i++)
840 		buf[i] = get_byte ();
841 	      buf[i] = 0;
842 	    }
843 	  args[count].n = len;
844 	  args[count].s = buf;
845 	  break;
846 
847 	default:
848 	  error ("Unimplented SWI argument");
849 	}
850 
851       type = type >> 2;
852       count++;
853     }
854 
855   if (exec_swi (swino, args))
856     {
857       /* We have two options here reply with either a byte or a word
858          which is stored in args[0].n. There is no harm in replying with
859          a word all the time, so thats what I do! */
860       send_rdp ("bbw-", RDP_OSOpReply, RDP_OSOpWord, args[0].n);
861     }
862   else
863     {
864       send_rdp ("bb-", RDP_OSOpReply, RDP_OSOpNothing);
865     }
866 }
867 
868 static void
869 rdp_execute_finish ()
870 {
871   int running = 1;
872 
873   while (running)
874     {
875       int res;
876       res = SERIAL_READCHAR (io, 1);
877       while (res == SERIAL_TIMEOUT)
878 	{
879 	  QUIT;
880 	  printf_filtered ("Waiting for target..\n");
881 	  res = SERIAL_READCHAR (io, 1);
882 	}
883 
884       switch (res)
885 	{
886 	case RDP_RES_SWI:
887 	  handle_swi ();
888 	  break;
889 	case RDP_RES_VALUE:
890 	  send_rdp ("B", &ds.rdi_stopped_status);
891 	  running = 0;
892 	  break;
893 	case RDP_RESET:
894 	  printf_filtered ("Target reset\n");
895 	  running = 0;
896 	  break;
897 	default:
898 	  printf_filtered ("Ignoring %x\n", res);
899 	  break;
900 	}
901     }
902 }
903 
904 
905 static void
906 rdp_execute ()
907 {
908   rdp_execute_start ();
909   rdp_execute_finish ();
910 }
911 
912 static int
913 remote_rdp_insert_breakpoint (addr, save)
914      CORE_ADDR addr;
915      char *save;
916 {
917   int res;
918   if (ds.rdi_level > 0)
919     {
920       send_rdp ("bwb-SWB",
921 		RDP_SET_BREAK,
922 		addr,
923 		RDP_SET_BREAK_TYPE_PC_EQUAL | RDP_SET_BREAK_TYPE_GET_HANDLE,
924 		save,
925 		&res);
926     }
927   else
928     {
929       send_rdp ("bwb-SB",
930 		RDP_SET_BREAK,
931 		addr,
932 		RDP_SET_BREAK_TYPE_PC_EQUAL,
933 		&res);
934     }
935   return res;
936 }
937 
938 static int
939 remote_rdp_remove_breakpoint (addr, save)
940      CORE_ADDR addr;
941      char *save;
942 {
943   int res;
944   if (ds.rdi_level > 0)
945     {
946       send_rdp ("b-p-S-B",
947 		RDP_CLEAR_BREAK,
948 		save, 4,
949 		&res);
950     }
951   else
952     {
953       send_rdp ("bw-S-B",
954 		RDP_CLEAR_BREAK,
955 		addr,
956 		&res);
957     }
958   return res;
959 }
960 
961 static void
962 rdp_step ()
963 {
964   if (ds.can_step && 0)
965     {
966       /* The pie board can't do steps so I can't test this, and
967          the other code will always work. */
968       int status;
969       send_rdp ("bbw-S-B",
970 		RDP_STEP, 0, 1,
971 		&status);
972     }
973   else
974     {
975       char handle[4];
976       CORE_ADDR pc = read_register (PC_REGNUM);
977       pc = arm_get_next_pc (pc);
978       remote_rdp_insert_breakpoint (pc, &handle);
979       rdp_execute ();
980       remote_rdp_remove_breakpoint (pc, &handle);
981     }
982 }
983 
984 static void
985 remote_rdp_open (args, from_tty)
986      char *args;
987      int from_tty;
988 {
989   if (!args)
990     error_no_arg ("serial port device name");
991 
992   baud_rate = 9600;
993 
994   target_preopen (from_tty);
995 
996   io = SERIAL_OPEN (args);
997 
998   if (!io)
999     perror_with_name (args);
1000 
1001   SERIAL_RAW (io);
1002 
1003   rdp_init (1, from_tty);
1004 
1005 
1006   if (from_tty)
1007     {
1008       printf_unfiltered ("Remote RDP debugging using %s at %d baud\n", args, baud_rate);
1009     }
1010 
1011   rdp_info ();
1012 
1013   push_target (&remote_rdp_ops);
1014 
1015   callback->init (callback);
1016   flush_cached_frames ();
1017   registers_changed ();
1018   stop_pc = read_pc ();
1019   set_current_frame (create_new_frame (read_fp (), stop_pc));
1020   select_frame (get_current_frame (), 0);
1021   print_stack_frame (selected_frame, -1, 1);
1022 }
1023 
1024 
1025 
1026 /* Close out all files and local state before this target loses control. */
1027 
1028 static void
1029 remote_rdp_close (quitting)
1030      int quitting;
1031 {
1032   callback->shutdown (callback);
1033   if (io)
1034     SERIAL_CLOSE (io);
1035   io = 0;
1036 }
1037 
1038 
1039 /* Resume execution of the target process.  STEP says whether to single-step
1040    or to run free; SIGGNAL is the signal value (e.g. SIGINT) to be given
1041    to the target, or zero for no signal.  */
1042 
1043 static void
1044 remote_rdp_resume (pid, step, siggnal)
1045      int pid, step;
1046      enum target_signal siggnal;
1047 {
1048   if (step)
1049     rdp_step ();
1050   else
1051     rdp_execute ();
1052 }
1053 
1054 /* Wait for inferior process to do something.  Return pid of child,
1055    or -1 in case of error; store status through argument pointer STATUS,
1056    just as `wait' would.  */
1057 
1058 static int
1059 remote_rdp_wait (pid, status)
1060      int pid;
1061      struct target_waitstatus *status;
1062 {
1063   switch (ds.rdi_stopped_status)
1064     {
1065     default:
1066     case RDP_RES_RESET:
1067     case RDP_RES_SWI:
1068       status->kind = TARGET_WAITKIND_EXITED;
1069       status->value.integer = read_register (0);
1070       break;
1071     case RDP_RES_AT_BREAKPOINT:
1072       status->kind = TARGET_WAITKIND_STOPPED;
1073       /* The signal in sigrc is a host signal.  That probably
1074          should be fixed.  */
1075       status->value.sig = TARGET_SIGNAL_TRAP;
1076       break;
1077 #if 0
1078     case rdp_signalled:
1079       status->kind = TARGET_WAITKIND_SIGNALLED;
1080       /* The signal in sigrc is a host signal.  That probably
1081          should be fixed.  */
1082       status->value.sig = target_signal_from_host (sigrc);
1083       break;
1084 #endif
1085     }
1086 
1087   return inferior_pid;
1088 }
1089 
1090 /* Get ready to modify the registers array.  On machines which store
1091    individual registers, this doesn't need to do anything.  On machines
1092    which store all the registers in one fell swoop, this makes sure
1093    that registers contains all the registers from the program being
1094    debugged.  */
1095 
1096 static void
1097 remote_rdp_prepare_to_store ()
1098 {
1099   /* Do nothing, since we can store individual regs */
1100 }
1101 
1102 static int
1103 remote_rdp_xfer_inferior_memory (memaddr, myaddr, len, write, target)
1104      CORE_ADDR memaddr;
1105      char *myaddr;
1106      int len;
1107      int write;
1108      struct target_ops *target;	/* ignored */
1109 {
1110   /* I infer from D Taylor's code that there's a limit on the amount
1111      we can transfer in one chunk.. */
1112   int done = 0;
1113   while (done < len)
1114     {
1115       int justdone;
1116       int thisbite = len - done;
1117       if (thisbite > RDP_MOUTHFULL)
1118 	thisbite = RDP_MOUTHFULL;
1119 
1120       QUIT;
1121 
1122       if (write)
1123 	{
1124 	  justdone = rdp_write (memaddr + done, myaddr + done, thisbite);
1125 	}
1126       else
1127 	{
1128 	  justdone = rdp_read (memaddr + done, myaddr + done, thisbite);
1129 	}
1130 
1131       done += justdone;
1132 
1133       if (justdone != thisbite)
1134 	break;
1135     }
1136   return done;
1137 }
1138 
1139 
1140 
1141 struct yn
1142 {
1143   const char *name;
1144   int bit;
1145 };
1146 static struct yn stepinfo[] =
1147 {
1148   {"Step more than one instruction", RDP_INFO_ABOUT_STEP_GT_1},
1149   {"Step to jump", RDP_INFO_ABOUT_STEP_TO_JMP},
1150   {"Step one instruction", RDP_INFO_ABOUT_STEP_1},
1151   {0}
1152 };
1153 
1154 static struct yn breakinfo[] =
1155 {
1156   {"comparison breakpoints supported", RDP_INFO_ABOUT_BREAK_COMP},
1157   {"range breakpoints supported", RDP_INFO_ABOUT_BREAK_RANGE},
1158   {"watchpoints for byte reads supported", RDP_INFO_ABOUT_BREAK_BYTE_READ},
1159   {"watchpoints for half-word reads supported", RDP_INFO_ABOUT_BREAK_HALFWORD_READ},
1160   {"watchpoints for word reads supported", RDP_INFO_ABOUT_BREAK_WORD_READ},
1161   {"watchpoints for byte writes supported", RDP_INFO_ABOUT_BREAK_BYTE_WRITE},
1162   {"watchpoints for half-word writes supported", RDP_INFO_ABOUT_BREAK_HALFWORD_WRITE},
1163   {"watchpoints for word writes supported", RDP_INFO_ABOUT_BREAK_WORD_WRITE},
1164   {"mask break/watch-points supported", RDP_INFO_ABOUT_BREAK_MASK},
1165 {"thread-specific breakpoints supported", RDP_INFO_ABOUT_BREAK_THREAD_BREAK},
1166 {"thread-specific watchpoints supported", RDP_INFO_ABOUT_BREAK_THREAD_WATCH},
1167   {"conditional breakpoints supported", RDP_INFO_ABOUT_BREAK_COND},
1168   {0}
1169 };
1170 
1171 
1172 static void
1173 dump_bits (t, info)
1174      struct yn *t;
1175      int info;
1176 {
1177   while (t->name)
1178     {
1179       printf_unfiltered ("  %-45s : %s\n", t->name, (info & t->bit) ? "Yes" : "No");
1180       t++;
1181     }
1182 }
1183 
1184 static void
1185 remote_rdp_files_info (target)
1186      struct target_ops *target;
1187 {
1188   printf_filtered ("Target capabilities:\n");
1189   dump_bits (stepinfo, ds.step_info);
1190   dump_bits (breakinfo, ds.break_info);
1191   printf_unfiltered ("target level RDI %x\n", (ds.target_info >> 5) & 3);
1192 }
1193 
1194 
1195 /* Define the target subroutine names */
1196 
1197 struct target_ops remote_rdp_ops =
1198 {
1199   "rdp",			/* to_shortname */
1200   /* to_longname */
1201   "Remote Target using the RDProtocol",
1202   /* to_doc */
1203   "Use a remote ARM system which uses the ARM Remote Debugging Protocol",
1204   remote_rdp_open,		/* to_open */
1205   remote_rdp_close,		/* to_close */
1206   NULL,				/* to_attach */
1207   NULL,				/* to_detach */
1208   remote_rdp_resume,		/* to_resume */
1209   remote_rdp_wait,		/* to_wait */
1210   remote_rdp_fetch_register,	/* to_fetch_registers */
1211   remote_rdp_store_register,	/* to_store_registers */
1212   remote_rdp_prepare_to_store,	/* to_prepare_to_store */
1213   remote_rdp_xfer_inferior_memory,	/* to_xfer_memory */
1214   remote_rdp_files_info,	/* to_files_info */
1215   remote_rdp_insert_breakpoint,	/* to_insert_breakpoint */
1216   remote_rdp_remove_breakpoint,	/* to_remove_breakpoint */
1217   NULL,				/* to_terminal_init */
1218   NULL,				/* to_terminal_inferior */
1219   NULL,				/* to_terminal_ours_for_output */
1220   NULL,				/* to_terminal_ours */
1221   NULL,				/* to_terminal_info */
1222   remote_rdp_kill,		/* to_kill */
1223   generic_load,			/* to_load */
1224   NULL,				/* to_lookup_symbol */
1225   NULL,				/* to_create_inferior */
1226   generic_mourn_inferior,	/* to_mourn_inferior */
1227   0,				/* to_can_run */
1228   0,				/* to_notice_signals */
1229   0,				/* to_thread_alive */
1230   0,				/* to_stop */
1231   process_stratum,		/* to_stratum */
1232   NULL,				/* to_next */
1233   1,				/* to_has_all_memory */
1234   1,				/* to_has_memory */
1235   1,				/* to_has_stack */
1236   1,				/* to_has_registers */
1237   1,				/* to_has_execution */
1238   NULL,				/* sections */
1239   NULL,				/* sections_end */
1240   OPS_MAGIC,			/* to_magic */
1241 };
1242 
1243 void
1244 _initialize_remote_rdp ()
1245 {
1246   add_target (&remote_rdp_ops);
1247 }
1248