4e4e3498ab3be84ef8e8be497483332131d620ed
[deliverable/binutils-gdb.git] / gdb / remote-hms.c
1 /* Remote debugging interface for Hitachi HMS Monitor Version 1.0
2 Copyright 1992 Free Software Foundation, Inc.
3 Contributed by Cygnus Support. Written by Steve Chamberlain
4 (sac@cygnus.com).
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., 675 Mass Ave, Cambridge, MA 02139, USA. */
21
22 #include <stdio.h>
23 #include "defs.h"
24 #include "inferior.h"
25 #include "wait.h"
26 #include "value.h"
27 #include <string.h>
28 #include <ctype.h>
29 #include <fcntl.h>
30 #include <signal.h>
31 #include <setjmp.h>
32 #include <errno.h>
33 #include "terminal.h"
34 #include "target.h"
35 #include "gdbcore.h"
36
37 /* External data declarations */
38 extern int stop_soon_quietly; /* for wait_for_inferior */
39
40 /* Forward data declarations */
41 extern struct target_ops hms_ops; /* Forward declaration */
42
43 /* Forward function declarations */
44 static void hms_fetch_registers ();
45 static int hms_store_registers ();
46 static void hms_close ();
47 static int hms_clear_breakpoints();
48
49 extern struct target_ops hms_ops;
50
51 static int quiet = 1;
52
53 #ifdef DEBUG
54 # define DENTER(NAME) if (!quiet) (printf_filtered("Entering %s\n",NAME), fflush(stdout))
55 # define DEXIT(NAME) if (!quiet) (printf_filtered("Exiting %s\n",NAME), fflush(stdout))
56 #else
57 # define DENTER(NAME)
58 # define DEXIT(NAME)
59 #endif
60
61
62 /***********************************************************************/
63 /* Caching stuff stolen from remote-nindy.c */
64
65 /* The data cache records all the data read from the remote machine
66 since the last time it stopped.
67
68 Each cache block holds LINE_SIZE bytes of data
69 starting at a multiple-of-LINE_SIZE address. */
70
71
72 #define LINE_SIZE_POWER 4
73 #define LINE_SIZE (1<<LINE_SIZE_POWER) /* eg 1<<3 == 8 */
74 #define LINE_SIZE_MASK ((LINE_SIZE-1)) /* eg 7*2+1= 111*/
75 #define DCACHE_SIZE 64 /* Number of cache blocks */
76 #define XFORM(x) ((x&LINE_SIZE_MASK)>>2)
77 struct dcache_block {
78 struct dcache_block *next, *last;
79 unsigned int addr; /* Address for which data is recorded. */
80 int data[LINE_SIZE/sizeof(int)];
81 };
82
83 struct dcache_block dcache_free, dcache_valid;
84
85 /* Free all the data cache blocks, thus discarding all cached data. */
86 static
87 void
88 dcache_flush ()
89 {
90 register struct dcache_block *db;
91
92 while ((db = dcache_valid.next) != &dcache_valid)
93 {
94 remque (db);
95 insque (db, &dcache_free);
96 }
97 }
98
99 /*
100 * If addr is present in the dcache, return the address of the block
101 * containing it.
102 */
103 static
104 struct dcache_block *
105 dcache_hit (addr)
106 unsigned int addr;
107 {
108 register struct dcache_block *db;
109
110 if (addr & 3)
111 abort ();
112
113 /* Search all cache blocks for one that is at this address. */
114 db = dcache_valid.next;
115 while (db != &dcache_valid)
116 {
117 if ((addr & ~LINE_SIZE_MASK)== db->addr)
118 return db;
119 db = db->next;
120 }
121 return NULL;
122 }
123
124 /* Return the int data at address ADDR in dcache block DC. */
125 static
126 int
127 dcache_value (db, addr)
128 struct dcache_block *db;
129 unsigned int addr;
130 {
131 if (addr & 3)
132 abort ();
133 return (db->data[XFORM(addr)]);
134 }
135
136 /* Get a free cache block, put or keep it on the valid list,
137 and return its address. The caller should store into the block
138 the address and data that it describes, then remque it from the
139 free list and insert it into the valid list. This procedure
140 prevents errors from creeping in if a ninMemGet is interrupted
141 (which used to put garbage blocks in the valid list...). */
142 static
143 struct dcache_block *
144 dcache_alloc ()
145 {
146 register struct dcache_block *db;
147
148 if ((db = dcache_free.next) == &dcache_free)
149 {
150 /* If we can't get one from the free list, take last valid and put
151 it on the free list. */
152 db = dcache_valid.last;
153 remque (db);
154 insque (db, &dcache_free);
155 }
156
157 remque (db);
158 insque (db, &dcache_valid);
159 return (db);
160 }
161
162 /* Return the contents of the word at address ADDR in the remote machine,
163 using the data cache. */
164 static
165 int
166 dcache_fetch (addr)
167 CORE_ADDR addr;
168 {
169 register struct dcache_block *db;
170
171 db = dcache_hit (addr);
172 if (db == 0)
173 {
174 db = dcache_alloc ();
175 immediate_quit++;
176 hms_read_inferior_memory(addr & ~LINE_SIZE_MASK, (unsigned char *)db->data, LINE_SIZE);
177 immediate_quit--;
178 db->addr = addr & ~LINE_SIZE_MASK;
179 remque (db); /* Off the free list */
180 insque (db, &dcache_valid); /* On the valid list */
181 }
182 return (dcache_value (db, addr));
183 }
184
185 /* Write the word at ADDR both in the data cache and in the remote machine. */
186 static void
187 dcache_poke (addr, data)
188 CORE_ADDR addr;
189 int data;
190 {
191 register struct dcache_block *db;
192
193 /* First make sure the word is IN the cache. DB is its cache block. */
194 db = dcache_hit (addr);
195 if (db == 0)
196 {
197 db = dcache_alloc ();
198 immediate_quit++;
199 hms_write_inferior_memory(addr & ~LINE_SIZE_MASK, (unsigned char *)db->data, LINE_SIZE);
200 immediate_quit--;
201 db->addr = addr & ~LINE_SIZE_MASK;
202 remque (db); /* Off the free list */
203 insque (db, &dcache_valid); /* On the valid list */
204 }
205
206 /* Modify the word in the cache. */
207 db->data[XFORM(addr)] = data;
208
209 /* Send the changed word. */
210 immediate_quit++;
211 hms_write_inferior_memory(addr, (unsigned char *)&data, 4);
212 immediate_quit--;
213 }
214
215 /* The cache itself. */
216 struct dcache_block the_cache[DCACHE_SIZE];
217
218 /* Initialize the data cache. */
219 static void
220 dcache_init ()
221 {
222 register i;
223 register struct dcache_block *db;
224
225 db = the_cache;
226 dcache_free.next = dcache_free.last = &dcache_free;
227 dcache_valid.next = dcache_valid.last = &dcache_valid;
228 for (i=0;i<DCACHE_SIZE;i++,db++)
229 insque (db, &dcache_free);
230 }
231
232
233 /***********************************************************************
234 * I/O stuff stolen from remote-eb.c
235 ***********************************************************************/
236
237 static int timeout = 2;
238 static char *dev_name = "/dev/ttya";
239
240
241
242
243 /* Descriptor for I/O to remote machine. Initialize it to -1 so that
244 hms_open knows that we don't have a file open when the program
245 starts. */
246 int hms_desc = -1;
247 #define OPEN(x) ((x) >= 0)
248
249
250 void hms_open();
251
252 #define ON 1
253 #define OFF 0
254 static void
255 rawmode(desc, turnon)
256 int desc;
257 int turnon;
258 {
259 TERMINAL sg;
260
261 if (desc < 0)
262 return;
263
264 ioctl (desc, TIOCGETP, &sg);
265
266 if (turnon) {
267 #ifdef HAVE_TERMIO
268 sg.c_lflag &= ~(ICANON);
269 #else
270 sg.sg_flags |= RAW;
271 #endif
272 } else {
273 #ifdef HAVE_TERMIO
274 sg.c_lflag |= ICANON;
275 #else
276 sg.sg_flags &= ~(RAW);
277 #endif
278 }
279 ioctl (desc, TIOCSETP, &sg);
280 }
281
282
283 /* Read a character from the remote system, doing all the fancy
284 timeout stuff. */
285 static int
286 readchar ()
287 {
288 char buf;
289
290 buf = '\0';
291 #ifdef HAVE_TERMIO
292 /* termio does the timeout for us. */
293 read (hms_desc, &buf, 1);
294 #else
295 alarm (timeout);
296 if (read (hms_desc, &buf, 1) < 0)
297 {
298 if (errno == EINTR)
299 error ("Timeout reading from remote system.");
300 else
301 perror_with_name ("remote");
302 }
303 alarm (0);
304 #endif
305
306 if (buf == '\0')
307 error ("Timeout reading from remote system.");
308
309 if (!quiet)
310 printf("%c",buf);
311
312 return buf & 0x7f;
313 }
314
315 static int
316 readchar_nofail ()
317 {
318 char buf;
319
320 buf = '\0';
321 #ifdef HAVE_TERMIO
322 /* termio does the timeout for us. */
323 read (hms_desc, &buf, 1);
324 #else
325 alarm (timeout);
326 if (read (hms_desc, &buf, 1) < 0)
327 {
328 return 0;
329 }
330 alarm (0);
331 #endif
332
333 if (buf == '\0')
334 {
335 return 0;
336 }
337 return buf & 0x7f;
338 }
339
340 /* Keep discarding input from the remote system, until STRING is found.
341 Let the user break out immediately. */
342 static void
343 expect (string)
344 char *string;
345 {
346 char *p = string;
347
348
349 immediate_quit = 1;
350 while (1)
351 {
352 if (readchar() == *p)
353 {
354 p++;
355 if (*p == '\0')
356 {
357 immediate_quit = 0;
358 return;
359 }
360 }
361 else
362 p = string;
363 }
364 }
365
366 /* Keep discarding input until we see the hms prompt.
367
368 The convention for dealing with the prompt is that you
369 o give your command
370 o *then* wait for the prompt.
371
372 Thus the last thing that a procedure does with the serial line
373 will be an expect_prompt(). Exception: hms_resume does not
374 wait for the prompt, because the terminal is being handed over
375 to the inferior. However, the next thing which happens after that
376 is a hms_wait which does wait for the prompt.
377 Note that this includes abnormal exit, e.g. error(). This is
378 necessary to prevent getting into states from which we can't
379 recover. */
380 static void
381 expect_prompt ()
382 {
383
384 expect ("HMS>");
385 }
386
387 /* Get a hex digit from the remote system & return its value.
388 If ignore_space is nonzero, ignore spaces (not newline, tab, etc). */
389 static int
390 get_hex_digit (ignore_space)
391 int ignore_space;
392 {
393 int ch;
394 while (1)
395 {
396 ch = readchar ();
397 if (ch >= '0' && ch <= '9')
398 return ch - '0';
399 else if (ch >= 'A' && ch <= 'F')
400 return ch - 'A' + 10;
401 else if (ch >= 'a' && ch <= 'f')
402 return ch - 'a' + 10;
403 else if (ch == ' ' && ignore_space)
404 ;
405 else
406 {
407 expect_prompt ();
408 error ("Invalid hex digit from remote system.");
409 }
410 }
411 }
412
413 /* Get a byte from hms_desc and put it in *BYT. Accept any number
414 leading spaces. */
415 static void
416 get_hex_byte (byt)
417 char *byt;
418 {
419 int val;
420
421 val = get_hex_digit (1) << 4;
422 val |= get_hex_digit (0);
423 *byt = val;
424 }
425
426 /* Read a 32-bit hex word from the hms, preceded by a space */
427 static long
428 get_hex_word()
429 {
430 long val;
431 int j;
432
433 val = 0;
434 for (j = 0; j < 8; j++)
435 val = (val << 4) + get_hex_digit (j == 0);
436 return val;
437 }
438 /* Called when SIGALRM signal sent due to alarm() timeout. */
439 #ifndef HAVE_TERMIO
440
441 #ifndef __STDC__
442 # ifndef volatile
443 # define volatile /**/
444 # endif
445 #endif
446 volatile int n_alarms;
447
448 void
449 hms_timer ()
450 {
451 n_alarms++;
452 }
453 #endif
454
455
456 /* Number of SIGTRAPs we need to simulate. That is, the next
457 NEED_ARTIFICIAL_TRAP calls to hms_wait should just return
458 SIGTRAP without actually waiting for anything. */
459
460 static int need_artificial_trap = 0;
461
462 void
463 hms_kill(arg,from_tty)
464 char *arg;
465 int from_tty;
466 {
467
468 }
469
470 static check_open()
471 {
472 if (!OPEN(hms_desc)) {
473 hms_open("",0);
474 }
475 }
476
477 /*
478 * Download a file specified in 'args', to the hms.
479 */
480 static void
481 hms_load(args,fromtty)
482 char *args;
483 int fromtty;
484 {
485 bfd *abfd;
486 asection *s;
487 int n;
488 char buffer[1024];
489
490 DENTER("hms_load()");
491 check_open();
492
493 dcache_flush();
494 inferior_pid = 0;
495 abfd = bfd_openr(args,"coff-h8300");
496 if (!abfd)
497 {
498 printf_filtered("Unable to open file %s\n", args);
499 return;
500 }
501
502 if (bfd_check_format(abfd, bfd_object) ==0)
503 {
504 printf_filtered("File is not an object file\n");
505 return ;
506 }
507
508 s = abfd->sections;
509 while (s != (asection *)NULL)
510 {
511 if (s->flags & SEC_LOAD)
512 {
513 char *buffer = xmalloc(s->_raw_size);
514 bfd_get_section_contents(abfd, s, buffer, 0, s->_raw_size);
515
516 hms_write_inferior_memory(s->vma, buffer, s->_raw_size);
517 free(buffer);
518 }
519 s = s->next;
520 }
521
522 DEXIT("hms_load()");
523 }
524
525 /* This is called not only when we first attach, but also when the
526 user types "run" after having attached. */
527 void
528 hms_create_inferior (execfile, args, env)
529 char *execfile;
530 char *args;
531 char **env;
532 {
533 int entry_pt;
534
535 DENTER("hms_create_inferior()");
536
537 if (args && *args)
538 error ("Can't pass arguments to remote hms process.");
539
540 if (execfile == 0 || exec_bfd == 0)
541 error ("No exec file specified");
542
543 entry_pt = (int) bfd_get_start_address (exec_bfd);
544 check_open();
545
546 if (OPEN(hms_desc))
547 {
548
549 hms_kill(NULL,NULL);
550 hms_clear_breakpoints();
551 init_wait_for_inferior ();
552 /* Clear the input because what the hms sends back is different
553 * depending on whether it was running or not.
554 */
555
556 hms_write_cr("r");
557
558 expect_prompt();
559
560
561 insert_breakpoints (); /* Needed to get correct instruction in cache */
562 proceed(entry_pt, -1, 0);
563
564
565 }
566 DEXIT("hms_create_inferior()");
567 }
568
569 /* Translate baud rates from integers to damn B_codes. Unix should
570 have outgrown this crap years ago, but even POSIX wouldn't buck it. */
571
572 #ifndef B19200
573 #define B19200 EXTA
574 #endif
575 #ifndef B38400
576 #define B38400 EXTB
577 #endif
578
579 static struct {int rate, damn_b;} baudtab[] = {
580 {9600, B9600},
581 {19200, B19200},
582 {300, B300},
583 {1200, B1200},
584 {2400, B2400},
585 {4800, B4800},
586 {-1, -1},
587 };
588
589 static int damn_b (rate)
590 int rate;
591 {
592 int i;
593
594 for (i = 0; baudtab[i].rate != -1; i++)
595 if (rate == baudtab[i].rate) return baudtab[i].damn_b;
596 return B19200;
597 }
598
599
600 /* Open a connection to a remote debugger.
601 NAME is the filename used for communication, then a space,
602 then the baud rate.
603 */
604
605 static char *
606 find_end_of_word(s)
607 char *s;
608 {
609 while (*s && !isspace(*s))
610 s++;
611 return s;
612 }
613
614 static char *get_word(p)
615 char **p;
616 {
617 char *s = *p;
618 char *word ;
619 char *copy;
620 size_t len;
621
622 while (isspace(*s))
623 s++;
624
625 word = s;
626
627 len = 0;
628
629 while (*s && !isspace(*s))
630 {
631 s++;
632 len++;
633
634 }
635 copy = xmalloc(len+1);
636 memcpy(copy, word, len);
637 copy[len] = 0;
638 *p = s;
639 return copy;
640 }
641
642 static int baudrate = 9600;
643
644 static int
645 is_baudrate_right()
646 {
647
648
649 /* Put this port into NORMAL mode, send the 'normal' character */
650 hms_write("\001", 1); /* Control A */
651 hms_write("\r", 1); /* Cr */
652
653 while ( readchar_nofail()) /* Skip noise we put there */
654 ;
655
656 hms_write("r");
657 if (readchar_nofail() == 'r')
658 return 1;
659
660 /* Not the right baudrate, or the board's not on */
661 return 0;
662
663
664 }
665 static void
666 set_rate()
667 {
668 TERMINAL sg;
669 ioctl (hms_desc, TIOCGETP, &sg);
670 #ifdef HAVE_TERMIO
671 sg.c_cc[VMIN] = 0; /* read with timeout. */
672 sg.c_cc[VTIME] = timeout * 10;
673 sg.c_lflag &= ~(ICANON | ECHO);
674 sg.c_cflag = (sg.c_cflag & ~CBAUD) | damn_b (baudrate);
675 #else
676 sg.sg_ispeed = damn_b (baudrate);
677 sg.sg_ospeed = damn_b (baudrate);
678 sg.sg_flags |= RAW | ANYP;
679 sg.sg_flags &= ~ECHO;
680 #endif
681
682 ioctl (hms_desc, TIOCSETP, &sg);
683 }
684
685 static void
686 get_baudrate_right()
687 {
688
689 int which_rate = 0;
690
691 while (!is_baudrate_right())
692 {
693 if (baudtab[which_rate].rate == -1)
694 {
695 which_rate = 0;
696 }
697 else
698 {
699 which_rate++;
700 }
701
702 baudrate = baudtab[which_rate].rate;
703 printf_filtered("Board not responding, trying %d baud\n",baudrate);
704 QUIT;
705 set_rate();
706 }
707 }
708
709 static void
710 hms_open (name, from_tty)
711 char *name;
712 int from_tty;
713 {
714
715 unsigned int prl;
716 char *p;
717
718 DENTER("hms_open()");
719 if(name == 0)
720 {
721 name = "";
722
723 }
724
725 hms_close (0);
726
727 hms_desc = open (dev_name, O_RDWR);
728 if (hms_desc < 0)
729 perror_with_name (dev_name);
730
731 set_rate();
732
733 dcache_init();
734
735
736 /* start_remote (); /* Initialize gdb process mechanisms */
737
738
739 #ifndef HAVE_TERMIO
740 #ifndef NO_SIGINTERRUPT
741 /* Cause SIGALRM's to make reads fail with EINTR instead of resuming
742 the read. */
743 if (siginterrupt (SIGALRM, 1) != 0)
744 perror ("hms_open: error in siginterrupt");
745 #endif
746
747 /* Set up read timeout timer. */
748 if ((void (*)) signal (SIGALRM, hms_timer) == (void (*)) -1)
749 perror ("hms_open: error in signal");
750 #endif
751
752 get_baudrate_right();
753
754 /* Hello? Are you there? */
755 write (hms_desc, "\r", 1);
756
757 expect_prompt ();
758
759 /* Clear any break points */
760 hms_clear_breakpoints();
761
762
763 printf_filtered("Remote debugging on an H8/300 HMS via %s.\n",dev_name);
764
765 DEXIT("hms_open()");
766 }
767
768 /* Close out all files and local state before this target loses control. */
769
770 static void
771 hms_close (quitting)
772 int quitting;
773 {
774
775 DENTER("hms_close()");
776
777 /* Clear any break points */
778 hms_clear_breakpoints();
779
780 /* Put this port back into REMOTE mode */
781 if (OPEN(hms_desc)) {
782
783 sleep(1); /* Let any output make it all the way back */
784 write(hms_desc, "R\r", 2);
785 }
786
787 /* Due to a bug in Unix, fclose closes not only the stdio stream,
788 but also the file descriptor. So we don't actually close
789 hms_desc. */
790 if (OPEN(hms_desc))
791 close (hms_desc);
792
793 /* Do not try to close hms_desc again, later in the program. */
794
795 hms_desc = -1;
796
797 DEXIT("hms_close()");
798 }
799
800 /* Attach to the target that is already loaded and possibly running */
801 static void
802 hms_attach (args, from_tty)
803 char *args;
804 int from_tty;
805 {
806
807 DENTER("hms_attach()");
808
809 /* push_target(&hms_ops); /* This done in hms_open() */
810
811 mark_breakpoints_out ();
812
813 /* Send the hms a kill. It is ok if it is not already running */
814 #if 0
815 fprintf(hms_stream, "K\r");
816 expect_prompt(); /* Slurp the echo */
817 #endif
818 /* We will get a task spawn event immediately. */
819 init_wait_for_inferior ();
820 clear_proceed_status ();
821 stop_soon_quietly = 1;
822 wait_for_inferior ();
823 stop_soon_quietly = 0;
824 normal_stop ();
825 DEXIT("hms_attach()");
826 }
827
828
829 /* Terminate the open connection to the remote debugger.
830 Use this when you want to detach and do something else
831 with your gdb. */
832 void
833 hms_detach (args,from_tty)
834 char *args;
835 int from_tty;
836 {
837 DENTER("hms_detach()");
838 if (OPEN(hms_desc)) { /* Send it on its way (tell it to continue) */
839 hms_clear_breakpoints();
840 #if 0
841 fprintf(hms_stream,"G\r");
842 #endif
843 }
844
845 pop_target(); /* calls hms_close to do the real work */
846 if (from_tty)
847 printf_filtered ("Ending remote %s debugging\n", target_shortname);
848 DEXIT("hms_detach()");
849 }
850
851 /* Tell the remote machine to resume. */
852
853 void
854 hms_resume (step, sig)
855 int step, sig;
856 {
857 DENTER("hms_resume()");
858 dcache_flush();
859
860 if (step)
861 {
862 hms_write_cr("s");
863
864 hms_write("\003",1);
865 expect_prompt();
866 /* Force the next hms_wait to return a trap. Not doing anything
867 about I/O from the target means that the user has to type
868 "continue" to see any. FIXME, this should be fixed. */
869 need_artificial_trap = 1;
870 }
871 else
872 {
873 hms_write_cr("g");
874 expect("g\r");
875 }
876 DEXIT("hms_resume()");
877 }
878
879 /* Wait until the remote machine stops, then return,
880 storing status in STATUS just as `wait' would. */
881
882 int
883 hms_wait (status)
884 WAITTYPE *status;
885 {
886 /* Strings to look for. '?' means match any single character.
887 Note that with the algorithm we use, the initial character
888 of the string cannot recur in the string, or we will not
889 find some cases of the string in the input. */
890
891 static char bpt[] = "At breakpoint:\r";
892 /* It would be tempting to look for "\n[__exit + 0x8]\n"
893 but that requires loading symbols with "yc i" and even if
894 we did do that we don't know that the file has symbols. */
895 static char exitmsg[] = "HMS>";
896 char *bp = bpt;
897 char *ep = exitmsg;
898
899 /* Large enough for either sizeof (bpt) or sizeof (exitmsg) chars. */
900 char swallowed[50];
901 /* Current position in swallowed. */
902 char *swallowed_p = swallowed;
903
904 int ch;
905 int ch_handled;
906 int old_timeout = timeout;
907 int old_immediate_quit = immediate_quit;
908 int swallowed_cr = 0;
909
910 DENTER("hms_wait()");
911
912 WSETEXIT ((*status), 0);
913
914 if (need_artificial_trap != 0)
915 {
916 WSETSTOP ((*status), SIGTRAP);
917 need_artificial_trap--;
918 return 0;
919 }
920
921 timeout = 0; /* Don't time out -- user program is running. */
922 immediate_quit = 1; /* Helps ability to QUIT */
923 while (1) {
924 QUIT; /* Let user quit and leave process running */
925 ch_handled = 0;
926 ch = readchar ();
927 if (ch == *bp) {
928 bp++;
929 if (*bp == '\0')
930 break;
931 ch_handled = 1;
932
933 *swallowed_p++ = ch;
934 } else
935 bp = bpt;
936 if (ch == *ep || *ep == '?') {
937 ep++;
938 if (*ep == '\0')
939 break;
940
941 if (!ch_handled)
942 *swallowed_p++ = ch;
943 ch_handled = 1;
944 } else
945 ep = exitmsg;
946 if (!ch_handled) {
947 char *p;
948 /* Print out any characters which have been swallowed. */
949 for (p = swallowed; p < swallowed_p; ++p)
950 putc (*p, stdout);
951 swallowed_p = swallowed;
952
953
954 if ((ch != '\r' && ch != '\n') || swallowed_cr>10)
955 {
956 putc (ch, stdout);
957 swallowed_cr = 10;
958 }
959 swallowed_cr ++;
960
961 }
962 }
963 if (*bp== '\0')
964 {
965 WSETSTOP ((*status), SIGTRAP);
966 expect_prompt();
967 }
968 else
969 {
970 WSETEXIT ((*status), 0);
971 }
972
973 timeout = old_timeout;
974 immediate_quit = old_immediate_quit;
975 DEXIT("hms_wait()");
976 return 0;
977 }
978
979 /* Return the name of register number REGNO
980 in the form input and output by hms.
981
982 Returns a pointer to a static buffer containing the answer. */
983 static char *
984 get_reg_name (regno)
985 int regno;
986 {
987 static char *rn[NUM_REGS]= REGISTER_NAMES;
988
989
990 return rn[regno];
991
992 }
993
994 /* Read the remote registers. */
995 static int gethex(length, start, ok)
996 unsigned int length;
997 char *start;
998 int *ok;
999 {
1000 int result = 0;
1001 while (length--)
1002 {
1003 result <<= 4 ;
1004 if (*start >='a' && *start <= 'f')
1005 {
1006 result += *start - 'a' + 10;
1007 }
1008 else if (*start >='A' && *start <= 'F')
1009 {
1010 result += *start - 'A' + 10;
1011 }
1012 else if (*start >='0' && *start <= '9')
1013 {
1014 result += *start - '0' ;
1015 }
1016 else *ok = 0;
1017 start++;
1018
1019 }
1020 return result;
1021 }
1022 static int
1023 timed_read(buf, n, timeout)
1024 char *buf;
1025
1026 {
1027 int i;
1028 char c;
1029 i = 0;
1030 while (i < n)
1031 {
1032 c = readchar();
1033
1034 if (c == 0) return i;
1035 buf[i] = c;
1036 i++;
1037
1038 }
1039 return i;
1040
1041 }
1042 hms_write(a,l)
1043 char *a;
1044 {
1045 int i;
1046 write(hms_desc,a,l);
1047 if (!quiet)
1048 for (i = 0; i < l ; i++)
1049 {
1050 printf("%c", a[i]);
1051 }
1052 }
1053
1054 hms_write_cr(s)
1055 char *s;
1056 {
1057 hms_write( s, strlen(s));
1058 hms_write("\r",1);
1059 }
1060
1061 static void
1062 hms_fetch_registers ()
1063 {
1064 #define REGREPLY_SIZE 79
1065 char linebuf[REGREPLY_SIZE+1];
1066 int i;
1067 int s ;
1068 int gottok;
1069
1070 REGISTER_TYPE reg[NUM_REGS];
1071 int foo[8];
1072 check_open();
1073
1074 do
1075 {
1076
1077 hms_write_cr("r");
1078 s = timed_read(linebuf, REGREPLY_SIZE, 1);
1079
1080
1081 linebuf[REGREPLY_SIZE] = 0;
1082 gottok = 0;
1083 if (linebuf[0] == 'r' &&
1084 linebuf[1] == '\r' &&
1085 linebuf[2] == '\n' &&
1086 linebuf[3] == 'P' &&
1087 linebuf[4] == 'C' &&
1088 linebuf[5] == '=' &&
1089 linebuf[75] == 'H' &&
1090 linebuf[76] == 'M' &&
1091 linebuf[77] == 'S')
1092 {
1093 /*
1094 PC=XXXX CCR=XX:XXXXXXXX R0-R7= XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX
1095 5436789012345678901234567890123456789012345678901234567890123456789012
1096 0 1 2 3 4 5 6
1097 */
1098 gottok = 1;
1099
1100 reg[PC_REGNUM] = gethex(4,linebuf+6, &gottok);
1101 reg[CCR_REGNUM] = gethex(2,linebuf+15, &gottok);
1102 for (i = 0; i < 8; i++)
1103 {
1104 reg[i] = gethex(4, linebuf+34+5*i, &gottok);
1105 }
1106 }
1107 }
1108 while (!gottok);
1109 for (i = 0; i < NUM_REGS; i++)
1110 {
1111 supply_register (i, reg+i);
1112 }
1113 }
1114
1115 /* Fetch register REGNO, or all registers if REGNO is -1.
1116 */
1117 static void
1118 hms_fetch_register (regno)
1119 int regno;
1120 {
1121
1122 hms_fetch_registers ();
1123
1124 }
1125
1126 /* Store the remote registers from the contents of the block REGS. */
1127
1128 static int
1129 hms_store_registers ()
1130 {
1131 int i;
1132 for (i = 0; i < NUM_REGS; i++)
1133 hms_store_register(i);
1134 return 0;
1135
1136 }
1137
1138 /* Store register REGNO, or all if REGNO == -1.
1139 Return errno value. */
1140 int
1141 hms_store_register (regno)
1142 int regno;
1143 {
1144
1145 /* printf("hms_store_register() called.\n"); fflush(stdout); /* */
1146 if (regno == -1)
1147 hms_store_registers ();
1148 else
1149 {
1150 char *name = get_reg_name (regno);
1151 char buffer[100];
1152 sprintf(buffer,"r %s=%x", name, read_register(regno));
1153 hms_write_cr(buffer);
1154 expect_prompt();
1155 }
1156
1157 DEXIT("hms_store_registers()");
1158 return 0;
1159 }
1160
1161 /* Get ready to modify the registers array. On machines which store
1162 individual registers, this doesn't need to do anything. On machines
1163 which store all the registers in one fell swoop, this makes sure
1164 that registers contains all the registers from the program being
1165 debugged. */
1166
1167 void
1168 hms_prepare_to_store ()
1169 {
1170 /* Do nothing, since we can store individual regs */
1171 }
1172
1173 static CORE_ADDR
1174 translate_addr(addr)
1175 CORE_ADDR addr;
1176 {
1177
1178 return(addr);
1179
1180 }
1181
1182 /* Read a word from remote address ADDR and return it.
1183 * This goes through the data cache.
1184 */
1185 int
1186 hms_fetch_word (addr)
1187 CORE_ADDR addr;
1188 {
1189 return dcache_fetch (addr);
1190 }
1191
1192 /* Write a word WORD into remote address ADDR.
1193 This goes through the data cache. */
1194
1195 void
1196 hms_store_word (addr, word)
1197 CORE_ADDR addr;
1198 int word;
1199 {
1200 dcache_poke (addr, word);
1201 }
1202
1203 int
1204 hms_xfer_inferior_memory(memaddr, myaddr, len, write, target)
1205 CORE_ADDR memaddr;
1206 char *myaddr;
1207 int len;
1208 int write;
1209 struct target_ops *target; /* ignored */
1210 {
1211 register int i;
1212 /* Round starting address down to longword boundary. */
1213 register CORE_ADDR addr;
1214 /* Round ending address up; get number of longwords that makes. */
1215 register int count;
1216 /* Allocate buffer of that many longwords. */
1217 register int *buffer ;
1218
1219 memaddr &= 0xffff;
1220 addr = memaddr & - sizeof (int);
1221 count = (((memaddr + len) - addr) + sizeof (int) - 1) / sizeof (int);
1222
1223
1224 buffer = (int *)alloca (count * sizeof (int));
1225 if (write)
1226 {
1227 /* Fill start and end extra bytes of buffer with existing memory data. */
1228
1229 if (addr != memaddr || len < (int)sizeof (int)) {
1230 /* Need part of initial word -- fetch it. */
1231 buffer[0] = hms_fetch_word (addr);
1232 }
1233
1234 if (count > 1) /* FIXME, avoid if even boundary */
1235 {
1236 buffer[count - 1]
1237 = hms_fetch_word (addr + (count - 1) * sizeof (int));
1238 }
1239
1240 /* Copy data to be written over corresponding part of buffer */
1241
1242 bcopy (myaddr, (char *) buffer + (memaddr & (sizeof (int) - 1)), len);
1243
1244 /* Write the entire buffer. */
1245
1246 for (i = 0; i < count; i++, addr += sizeof (int))
1247 {
1248 errno = 0;
1249 hms_store_word (addr, buffer[i]);
1250 if (errno)
1251 {
1252
1253 return 0;
1254 }
1255
1256 }
1257 }
1258 else
1259 {
1260 /* Read all the longwords */
1261 for (i = 0; i < count; i++, addr += sizeof (int))
1262 {
1263 errno = 0;
1264 buffer[i] = hms_fetch_word (addr);
1265 if (errno)
1266 {
1267 return 0;
1268 }
1269 QUIT;
1270 }
1271
1272 /* Copy appropriate bytes out of the buffer. */
1273 bcopy ((char *) buffer + (memaddr & (sizeof (int) - 1)), myaddr, len);
1274 }
1275
1276
1277 return len;
1278 }
1279
1280 #if 0
1281 int
1282 hms_xfer_inferior_memory (memaddr, myaddr, len, write)
1283 CORE_ADDR memaddr;
1284 char *myaddr;
1285 int len;
1286 int write;
1287 {
1288 memaddr &= 0xffff;
1289 if (write)
1290 return hms_write_inferior_memory (memaddr, myaddr, len);
1291 else
1292 return hms_read_inferior_memory (memaddr, myaddr, len);
1293
1294 }
1295 #endif
1296
1297 int
1298 hms_write_inferior_memory (memaddr, myaddr, len)
1299 CORE_ADDR memaddr;
1300 char *myaddr;
1301 int len;
1302 {
1303
1304 bfd *abfd = bfd_openw(dev_name, "srec");
1305 asection *a;
1306
1307 bfd_set_format(abfd, bfd_object);
1308 a = bfd_make_section(abfd, ".text");
1309 a->vma = memaddr;
1310 a->_raw_size = len;
1311 a->flags = SEC_LOAD | SEC_HAS_CONTENTS;
1312 hms_write_cr("tl"); /* tell hms here comes the recs */
1313 bfd_set_section_contents(abfd, a, myaddr, 0, len);
1314 bfd_close(abfd);
1315
1316 expect_prompt();
1317 }
1318
1319 void
1320 hms_files_info ()
1321 {
1322 printf_filtered("\tAttached to %s at %d baud and running program %s\n",
1323 dev_name, baudrate, bfd_get_filename(exec_bfd));
1324 printf_filtered("\ton an H8/300 processor.\n");
1325 }
1326
1327 /* Copy LEN bytes of data from debugger memory at MYADDR
1328 to inferior's memory at MEMADDR. Returns errno value.
1329 * sb/sh instructions don't work on unaligned addresses, when TU=1.
1330 */
1331
1332
1333 /* Read LEN bytes from inferior memory at MEMADDR. Put the result
1334 at debugger address MYADDR. Returns errno value. */
1335 int
1336 hms_read_inferior_memory(memaddr, myaddr, len)
1337 CORE_ADDR memaddr;
1338 char *myaddr;
1339 int len;
1340 {
1341 /* Align to nearest low 16 bits */
1342 int i;
1343
1344 #if 0
1345 CORE_ADDR start = memaddr & ~0xf;
1346 CORE_ADDR end = ((memaddr + len +16) & ~0xf) -1;
1347 #endif
1348 CORE_ADDR start = memaddr;
1349 CORE_ADDR end = memaddr + len -1;
1350
1351 int ok =1;
1352
1353 /*
1354 AAAA: XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX '................'
1355 012345678901234567890123456789012345678901234567890123456789012345
1356 0 1 2 3 4 5 6
1357 */
1358 char buffer[66];
1359 if (memaddr & 0xf) abort();
1360 if (len != 16) abort();
1361
1362 sprintf(buffer, "m %4x %4x", start, end);
1363 hms_write_cr(buffer);
1364 /* drop the echo and newline*/
1365 for (i = 0; i < 13; i++)
1366 readchar();
1367
1368
1369
1370 /* Grab the lines as they come out and fill the area */
1371 /* Skip over cr */
1372 while(1)
1373 {
1374 int p;
1375 int i;
1376 int addr;
1377 size_t idx;
1378
1379 char byte[16];
1380 buffer[0] = readchar();
1381 if (buffer[0] == 'M')
1382 break;
1383 for (i = 1; i < 66; i++)
1384 buffer[i] = readchar();
1385
1386 /* Now parse the line */
1387
1388 addr = gethex(4, buffer, &ok);
1389 idx = 6;
1390 for (p = 0; p < 16; p+=2)
1391 {
1392 byte[p] = gethex(2, buffer + idx, &ok);
1393 byte[p+1] = gethex(2, buffer+ idx + 2, &ok);
1394 idx+=5;
1395
1396 }
1397
1398
1399 for (p = 0; p<16;p++)
1400 {
1401 if (addr + p >= memaddr &&
1402 addr + p < memaddr + len)
1403 {
1404 myaddr[ (addr + p)-memaddr] = byte[p];
1405
1406 }
1407
1408 }
1409 }
1410
1411
1412
1413 hms_write("\003",1);
1414 expect_prompt();
1415
1416
1417
1418
1419 return len;
1420
1421 }
1422
1423 /* This routine is run as a hook, just before the main command loop is
1424 entered. If gdb is configured for the H8, but has not had its
1425 target specified yet, this will loop prompting the user to do so.
1426 */
1427
1428 hms_before_main_loop ()
1429 {
1430 char ttyname[100];
1431 char *p, *p2;
1432 extern FILE *instream;
1433 extern jmp_buf to_top_level;
1434
1435 push_target (&hms_ops);
1436 #if 0
1437
1438 while (current_target != &hms_ops) {
1439 /* remote tty not specified yet */
1440 if ( instream == stdin ){
1441 printf("\nEnter device and filename, or \"quit\" to quit: ");
1442 fflush( stdout );
1443 }
1444 fgets( ttyname, sizeof(ttyname)-1, stdin );
1445
1446 if ( !strcmp("quit", ttyname) ){
1447 exit(1);
1448 }
1449
1450 hms_open( ttyname, 1 );
1451
1452 /* Now that we have a tty open for talking to the remote machine,
1453 download the executable file if one was specified. */
1454 if ( !setjmp(to_top_level) && exec_bfd ) {
1455 target_load (bfd_get_filename (exec_bfd), 1);
1456 }
1457 }
1458 #endif
1459 }
1460
1461
1462 #define MAX_BREAKS 16
1463 static int num_brkpts=0;
1464 static int
1465 hms_insert_breakpoint(addr, save)
1466 CORE_ADDR addr;
1467 char *save; /* Throw away, let hms save instructions */
1468 {
1469
1470 DENTER("hms_insert_breakpoint()");
1471 check_open();
1472
1473 if (num_brkpts < MAX_BREAKS) {
1474 char buffer[100];
1475 num_brkpts++;
1476 sprintf(buffer,"b %x", addr & 0xffff);
1477 hms_write_cr(buffer);
1478 expect_prompt ();
1479 DEXIT("hms_insert_breakpoint() success");
1480 return(0); /* Success */
1481 } else {
1482 fprintf_filtered(stderr,
1483 "Too many break points, break point not installed\n");
1484 DEXIT("hms_insert_breakpoint() failure");
1485 return(1); /* Failure */
1486 }
1487
1488
1489 }
1490 static int
1491 hms_remove_breakpoint(addr, save)
1492 CORE_ADDR addr;
1493 char *save; /* Throw away, let hms save instructions */
1494 {
1495 DENTER("hms_remove_breakpoint()");
1496 if (num_brkpts > 0) {
1497 char buffer[100];
1498
1499 num_brkpts--;
1500 sprintf(buffer,"b - %x", addr & 0xffff);
1501 hms_write_cr(buffer);
1502 expect_prompt();
1503
1504 }
1505 DEXIT("hms_remove_breakpoint()");
1506 return(0);
1507 }
1508
1509 /* Clear the hmss notion of what the break points are */
1510 static int
1511 hms_clear_breakpoints()
1512 {
1513
1514 DENTER("hms_clear_breakpoint()");
1515 if (OPEN(hms_desc)) {
1516 hms_write_cr("b -");
1517 expect_prompt ();
1518 }
1519 num_brkpts = 0;
1520
1521 DEXIT("hms_clear_breakpoint()");
1522 }
1523 static void
1524 hms_mourn()
1525 {
1526 DENTER("hms_mourn()");
1527 hms_clear_breakpoints();
1528 /* pop_target (); /* Pop back to no-child state */
1529 generic_mourn_inferior ();
1530 DEXIT("hms_mourn()");
1531 }
1532
1533 /* Display everthing we read in from the hms until we match/see the
1534 * specified string
1535 */
1536 static int
1537 display_until(str)
1538 char *str;
1539 {
1540 int i=0,j,c;
1541
1542 while (c=readchar()) {
1543 if (c==str[i]) {
1544 i++;
1545 if (i == strlen(str)) return;
1546 } else {
1547 if (i) {
1548 for (j=0 ; j<i ; j++) /* Put everthing we matched */
1549 putchar(str[j]);
1550 i=0;
1551 }
1552 putchar(c);
1553 }
1554 }
1555
1556 }
1557
1558
1559 /* Put a command string, in args, out to the hms. The hms is assumed to
1560 be in raw mode, all writing/reading done through hms_desc.
1561 Ouput from the hms is placed on the users terminal until the
1562 prompt from the hms is seen.
1563 FIXME: Can't handle commands that take input. */
1564
1565 void
1566 hms_com (args, fromtty)
1567 char *args;
1568 int fromtty;
1569 {
1570 check_open();
1571
1572 if (!args) return;
1573
1574 /* Clear all input so only command relative output is displayed */
1575
1576
1577 hms_write_cr(args);
1578 hms_write("\030",1);
1579 expect_prompt();
1580
1581 }
1582
1583 /* Define the target subroutine names */
1584
1585 struct target_ops hms_ops = {
1586 "hms", "Remote HMS monitor",
1587 "Use the H8 evaluation board running the HMS monitor connected\n\
1588 by a serial line.",
1589
1590 hms_open, hms_close,
1591 hms_attach, hms_detach, hms_resume, hms_wait,
1592 hms_fetch_register, hms_store_register,
1593 hms_prepare_to_store, 0, 0, /* conv_to, conv_from */
1594 hms_xfer_inferior_memory,
1595 hms_files_info,
1596 hms_insert_breakpoint, hms_remove_breakpoint, /* Breakpoints */
1597 0, 0, 0, 0, 0, /* Terminal handling */
1598 hms_kill, /* FIXME, kill */
1599 hms_load,
1600 0, /* lookup_symbol */
1601 hms_create_inferior, /* create_inferior */
1602 hms_mourn, /* mourn_inferior FIXME */
1603 process_stratum, 0, /* next */
1604 1, 1, 1, 1, 1, /* all mem, mem, stack, regs, exec */
1605 0,0, /* Section pointers */
1606 OPS_MAGIC, /* Always the last thing */
1607 };
1608
1609
1610 hms_quiet()
1611 {
1612 quiet = ! quiet;
1613 }
1614
1615 hms_device(s)
1616 char *s;
1617 {
1618 if (s) {
1619 dev_name = get_word(&s);
1620 }
1621 }
1622
1623 static hms_speed(s)
1624 char *s;
1625 {
1626 if (s)
1627 {
1628 char buffer[100];
1629 int newrate = atoi(s);
1630 int which = 0;
1631 while (baudtab[which].rate != newrate)
1632 {
1633 if (baudtab[which].rate == -1)
1634 {
1635 error("Can't use %d baud\n", newrate);
1636 }
1637 which++;
1638 }
1639
1640
1641
1642 printf_filtered("Checking target is in sync\n");
1643
1644
1645 get_baudrate_right();
1646 baudrate = newrate;
1647 printf_filtered("Sending commands to set target to %d\n",
1648 baudrate);
1649
1650 sprintf(buffer, "tm %d. N 8 1", baudrate);
1651 hms_write(buffer);
1652 }
1653 }
1654
1655 /***********************************************************************/
1656
1657 void
1658 _initialize_remote_hms ()
1659 {
1660 add_target (&hms_ops);
1661 add_com ("hms <command>", class_obscure, hms_com,
1662 "Send a command to the HMS monitor.");
1663 add_com ("snoop", class_obscure, hms_quiet,
1664 "Show what commands are going to the monitor");
1665 add_com ("device", class_obscure, hms_device,
1666 "Set the terminal line for HMS communications");
1667
1668 add_com ("speed", class_obscure, hms_speed,
1669 "Set the terminal line speed for HMS communications");
1670
1671 }
1672
1673
This page took 0.062873 seconds and 4 git commands to generate.