2004-02-14 Elena Zannoni <ezannoni@redhat.com>
[platform/upstream/binutils.git] / gdb / serial.c
1 /* Generic serial interface routines
2
3    Copyright 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
4    2001, 2002 Free Software 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 #include "defs.h"
24 #include <ctype.h>
25 #include "serial.h"
26 #include "gdb_string.h"
27 #include "gdbcmd.h"
28
29 extern void _initialize_serial (void);
30
31 /* Is serial being debugged? */
32
33 static int global_serial_debug_p;
34
35 /* Linked list of serial I/O handlers */
36
37 static struct serial_ops *serial_ops_list = NULL;
38
39 /* This is the last serial stream opened.  Used by connect command. */
40
41 static struct serial *last_serial_opened = NULL;
42
43 /* Pointer to list of scb's. */
44
45 static struct serial *scb_base;
46
47 /* Non-NULL gives filename which contains a recording of the remote session,
48    suitable for playback by gdbserver. */
49
50 static char *serial_logfile = NULL;
51 static struct ui_file *serial_logfp = NULL;
52
53 static struct serial_ops *serial_interface_lookup (char *);
54 static void serial_logchar (struct ui_file *stream, int ch_type, int ch, int timeout);
55 static const char logbase_hex[] = "hex";
56 static const char logbase_octal[] = "octal";
57 static const char logbase_ascii[] = "ascii";
58 static const char *logbase_enums[] =
59 {logbase_hex, logbase_octal, logbase_ascii, NULL};
60 static const char *serial_logbase = logbase_ascii;
61 \f
62
63 static int serial_current_type = 0;
64
65 /* Log char CH of type CHTYPE, with TIMEOUT */
66
67 /* Define bogus char to represent a BREAK.  Should be careful to choose a value
68    that can't be confused with a normal char, or an error code.  */
69 #define SERIAL_BREAK 1235
70
71 static void
72 serial_logchar (struct ui_file *stream, int ch_type, int ch, int timeout)
73 {
74   if (ch_type != serial_current_type)
75     {
76       fprintf_unfiltered (stream, "\n%c ", ch_type);
77       serial_current_type = ch_type;
78     }
79
80   if (serial_logbase != logbase_ascii)
81     fputc_unfiltered (' ', stream);
82
83   switch (ch)
84     {
85     case SERIAL_TIMEOUT:
86       fprintf_unfiltered (stream, "<Timeout: %d seconds>", timeout);
87       return;
88     case SERIAL_ERROR:
89       fprintf_unfiltered (stream, "<Error: %s>", safe_strerror (errno));
90       return;
91     case SERIAL_EOF:
92       fputs_unfiltered ("<Eof>", stream);
93       return;
94     case SERIAL_BREAK:
95       fputs_unfiltered ("<Break>", stream);
96       return;
97     default:
98       if (serial_logbase == logbase_hex)
99         fprintf_unfiltered (stream, "%02x", ch & 0xff);
100       else if (serial_logbase == logbase_octal)
101         fprintf_unfiltered (stream, "%03o", ch & 0xff);
102       else
103         switch (ch)
104           {
105           case '\\':
106             fputs_unfiltered ("\\\\", stream);
107             break;
108           case '\b':
109             fputs_unfiltered ("\\b", stream);
110             break;
111           case '\f':
112             fputs_unfiltered ("\\f", stream);
113             break;
114           case '\n':
115             fputs_unfiltered ("\\n", stream);
116             break;
117           case '\r':
118             fputs_unfiltered ("\\r", stream);
119             break;
120           case '\t':
121             fputs_unfiltered ("\\t", stream);
122             break;
123           case '\v':
124             fputs_unfiltered ("\\v", stream);
125             break;
126           default:
127             fprintf_unfiltered (stream, isprint (ch) ? "%c" : "\\x%02x", ch & 0xFF);
128             break;
129           }
130     }
131 }
132
133 void
134 serial_log_command (const char *cmd)
135 {
136   if (!serial_logfp)
137     return;
138
139   serial_current_type = 'c';
140
141   fputs_unfiltered ("\nc ", serial_logfp);
142   fputs_unfiltered (cmd, serial_logfp);
143
144   /* Make sure that the log file is as up-to-date as possible,
145      in case we are getting ready to dump core or something. */
146   gdb_flush (serial_logfp);
147 }
148
149 \f
150 static struct serial_ops *
151 serial_interface_lookup (char *name)
152 {
153   struct serial_ops *ops;
154
155   for (ops = serial_ops_list; ops; ops = ops->next)
156     if (strcmp (name, ops->name) == 0)
157       return ops;
158
159   return NULL;
160 }
161
162 void
163 serial_add_interface (struct serial_ops *optable)
164 {
165   optable->next = serial_ops_list;
166   serial_ops_list = optable;
167 }
168
169 /* Open up a device or a network socket, depending upon the syntax of NAME. */
170
171 struct serial *
172 serial_open (const char *name)
173 {
174   struct serial *scb;
175   struct serial_ops *ops;
176   const char *open_name = name;
177
178   for (scb = scb_base; scb; scb = scb->next)
179     if (scb->name && strcmp (scb->name, name) == 0)
180       {
181         scb->refcnt++;
182         return scb;
183       }
184
185   if (strcmp (name, "pc") == 0)
186     ops = serial_interface_lookup ("pc");
187   else if (strchr (name, ':'))
188     ops = serial_interface_lookup ("tcp");
189   else if (strncmp (name, "lpt", 3) == 0)
190     ops = serial_interface_lookup ("parallel");
191   else if (strncmp (name, "|", 1) == 0)
192     {
193       ops = serial_interface_lookup ("pipe");
194       open_name = name + 1; /* discard ``|'' */
195     }
196   else
197     ops = serial_interface_lookup ("hardwire");
198
199   if (!ops)
200     return NULL;
201
202   scb = XMALLOC (struct serial);
203
204   scb->ops = ops;
205
206   scb->bufcnt = 0;
207   scb->bufp = scb->buf;
208
209   if (scb->ops->open (scb, open_name))
210     {
211       xfree (scb);
212       return NULL;
213     }
214
215   scb->name = xstrdup (name);
216   scb->next = scb_base;
217   scb->refcnt = 1;
218   scb->debug_p = 0;
219   scb->async_state = 0;
220   scb->async_handler = NULL;
221   scb->async_context = NULL;
222   scb_base = scb;
223
224   last_serial_opened = scb;
225
226   if (serial_logfile != NULL)
227     {
228       serial_logfp = gdb_fopen (serial_logfile, "w");
229       if (serial_logfp == NULL)
230         perror_with_name (serial_logfile);
231     }
232
233   return scb;
234 }
235
236 struct serial *
237 serial_fdopen (const int fd)
238 {
239   struct serial *scb;
240   struct serial_ops *ops;
241
242   for (scb = scb_base; scb; scb = scb->next)
243     if (scb->fd == fd)
244       {
245         scb->refcnt++;
246         return scb;
247       }
248
249   ops = serial_interface_lookup ("hardwire");
250
251   if (!ops)
252     return NULL;
253
254   scb = XMALLOC (struct serial);
255
256   scb->ops = ops;
257
258   scb->bufcnt = 0;
259   scb->bufp = scb->buf;
260
261   scb->fd = fd;
262
263   scb->name = NULL;
264   scb->next = scb_base;
265   scb->refcnt = 1;
266   scb->debug_p = 0;
267   scb->async_state = 0;
268   scb->async_handler = NULL;
269   scb->async_context = NULL;
270   scb_base = scb;
271
272   last_serial_opened = scb;
273
274   return scb;
275 }
276
277 static void
278 do_serial_close (struct serial *scb, int really_close)
279 {
280   struct serial *tmp_scb;
281
282   last_serial_opened = NULL;
283
284   if (serial_logfp)
285     {
286       fputs_unfiltered ("\nEnd of log\n", serial_logfp);
287       serial_current_type = 0;
288
289       /* XXX - What if serial_logfp == gdb_stdout or gdb_stderr? */
290       ui_file_delete (serial_logfp);
291       serial_logfp = NULL;
292     }
293
294 /* This is bogus.  It's not our fault if you pass us a bad scb...!  Rob, you
295    should fix your code instead.  */
296
297   if (!scb)
298     return;
299
300   scb->refcnt--;
301   if (scb->refcnt > 0)
302     return;
303
304   /* ensure that the FD has been taken out of async mode */
305   if (scb->async_handler != NULL)
306     serial_async (scb, NULL, NULL);
307
308   if (really_close)
309     scb->ops->close (scb);
310
311   if (scb->name)
312     xfree (scb->name);
313
314   if (scb_base == scb)
315     scb_base = scb_base->next;
316   else
317     for (tmp_scb = scb_base; tmp_scb; tmp_scb = tmp_scb->next)
318       {
319         if (tmp_scb->next != scb)
320           continue;
321
322         tmp_scb->next = tmp_scb->next->next;
323         break;
324       }
325
326   xfree (scb);
327 }
328
329 void
330 serial_close (struct serial *scb)
331 {
332   do_serial_close (scb, 1);
333 }
334
335 void
336 serial_un_fdopen (struct serial *scb)
337 {
338   do_serial_close (scb, 0);
339 }
340
341 int
342 serial_readchar (struct serial *scb, int timeout)
343 {
344   int ch;
345
346   /* FIXME: cagney/1999-10-11: Don't enable this check until the ASYNC
347      code is finished. */
348   if (0 && serial_is_async_p (scb) && timeout < 0)
349     internal_error (__FILE__, __LINE__,
350                     "serial_readchar: blocking read in async mode");
351
352   ch = scb->ops->readchar (scb, timeout);
353   if (serial_logfp != NULL)
354     {
355       serial_logchar (serial_logfp, 'r', ch, timeout);
356
357       /* Make sure that the log file is as up-to-date as possible,
358          in case we are getting ready to dump core or something. */
359       gdb_flush (serial_logfp);
360     }
361   if (serial_debug_p (scb))
362     {
363       fprintf_unfiltered (gdb_stdlog, "[");
364       serial_logchar (gdb_stdlog, 'r', ch, timeout);
365       fprintf_unfiltered (gdb_stdlog, "]");
366       gdb_flush (gdb_stdlog);
367     }
368
369   return (ch);
370 }
371
372 int
373 serial_write (struct serial *scb, const char *str, int len)
374 {
375   if (serial_logfp != NULL)
376     {
377       int count;
378
379       for (count = 0; count < len; count++)
380         serial_logchar (serial_logfp, 'w', str[count] & 0xff, 0);
381
382       /* Make sure that the log file is as up-to-date as possible,
383          in case we are getting ready to dump core or something. */
384       gdb_flush (serial_logfp);
385     }
386
387   return (scb->ops->write (scb, str, len));
388 }
389
390 void
391 serial_printf (struct serial *desc, const char *format,...)
392 {
393   va_list args;
394   char *buf;
395   va_start (args, format);
396
397   xvasprintf (&buf, format, args);
398   serial_write (desc, buf, strlen (buf));
399
400   xfree (buf);
401   va_end (args);
402 }
403
404 int
405 serial_drain_output (struct serial *scb)
406 {
407   return scb->ops->drain_output (scb);
408 }
409
410 int
411 serial_flush_output (struct serial *scb)
412 {
413   return scb->ops->flush_output (scb);
414 }
415
416 int
417 serial_flush_input (struct serial *scb)
418 {
419   return scb->ops->flush_input (scb);
420 }
421
422 int
423 serial_send_break (struct serial *scb)
424 {
425   if (serial_logfp != NULL)
426     serial_logchar (serial_logfp, 'w', SERIAL_BREAK, 0);
427
428   return (scb->ops->send_break (scb));
429 }
430
431 void
432 serial_raw (struct serial *scb)
433 {
434   scb->ops->go_raw (scb);
435 }
436
437 serial_ttystate
438 serial_get_tty_state (struct serial *scb)
439 {
440   return scb->ops->get_tty_state (scb);
441 }
442
443 int
444 serial_set_tty_state (struct serial *scb, serial_ttystate ttystate)
445 {
446   return scb->ops->set_tty_state (scb, ttystate);
447 }
448
449 void
450 serial_print_tty_state (struct serial *scb,
451                         serial_ttystate ttystate,
452                         struct ui_file *stream)
453 {
454   scb->ops->print_tty_state (scb, ttystate, stream);
455 }
456
457 int
458 serial_noflush_set_tty_state (struct serial *scb,
459                               serial_ttystate new_ttystate,
460                               serial_ttystate old_ttystate)
461 {
462   return scb->ops->noflush_set_tty_state (scb, new_ttystate, old_ttystate);
463 }
464
465 int
466 serial_setbaudrate (struct serial *scb, int rate)
467 {
468   return scb->ops->setbaudrate (scb, rate);
469 }
470
471 int
472 serial_setstopbits (struct serial *scb, int num)
473 {
474   return scb->ops->setstopbits (scb, num);
475 }
476
477 int
478 serial_can_async_p (struct serial *scb)
479 {
480   return (scb->ops->async != NULL);
481 }
482
483 int
484 serial_is_async_p (struct serial *scb)
485 {
486   return (scb->ops->async != NULL) && (scb->async_handler != NULL);
487 }
488
489 void
490 serial_async (struct serial *scb,
491               serial_event_ftype *handler,
492               void *context)
493 {
494   /* Only change mode if there is a need. */
495   if ((scb->async_handler == NULL)
496       != (handler == NULL))
497     scb->ops->async (scb, handler != NULL);
498   scb->async_handler = handler;
499   scb->async_context = context;
500 }
501
502 int
503 deprecated_serial_fd (struct serial *scb)
504 {
505   /* FIXME: should this output a warning that deprecated code is being
506      called? */
507   if (scb->fd < 0)
508     {
509       internal_error (__FILE__, __LINE__,
510                       "serial: FD not valid");
511     }
512   return scb->fd; /* sigh */
513 }
514
515 void
516 serial_debug (struct serial *scb, int debug_p)
517 {
518   scb->debug_p = debug_p;
519 }
520
521 int
522 serial_debug_p (struct serial *scb)
523 {
524   return scb->debug_p || global_serial_debug_p;
525 }
526
527
528 #if 0
529 /* The connect command is #if 0 because I hadn't thought of an elegant
530    way to wait for I/O on two `struct serial *'s simultaneously.  Two
531    solutions came to mind:
532
533    1) Fork, and have have one fork handle the to user direction,
534    and have the other hand the to target direction.  This
535    obviously won't cut it for MSDOS.
536
537    2) Use something like select.  This assumes that stdin and
538    the target side can both be waited on via the same
539    mechanism.  This may not be true for DOS, if GDB is
540    talking to the target via a TCP socket.
541    -grossman, 8 Jun 93 */
542
543 /* Connect the user directly to the remote system.  This command acts just like
544    the 'cu' or 'tip' command.  Use <CR>~. or <CR>~^D to break out.  */
545
546 static struct serial *tty_desc; /* Controlling terminal */
547
548 static void
549 cleanup_tty (serial_ttystate ttystate)
550 {
551   printf_unfiltered ("\r\n[Exiting connect mode]\r\n");
552   serial_set_tty_state (tty_desc, ttystate);
553   xfree (ttystate);
554   serial_close (tty_desc);
555 }
556
557 static void
558 connect_command (char *args, int fromtty)
559 {
560   int c;
561   char cur_esc = 0;
562   serial_ttystate ttystate;
563   struct serial *port_desc;             /* TTY port */
564
565   dont_repeat ();
566
567   if (args)
568     fprintf_unfiltered (gdb_stderr, "This command takes no args.  They have been ignored.\n");
569
570   printf_unfiltered ("[Entering connect mode.  Use ~. or ~^D to escape]\n");
571
572   tty_desc = serial_fdopen (0);
573   port_desc = last_serial_opened;
574
575   ttystate = serial_get_tty_state (tty_desc);
576
577   serial_raw (tty_desc);
578   serial_raw (port_desc);
579
580   make_cleanup (cleanup_tty, ttystate);
581
582   while (1)
583     {
584       int mask;
585
586       mask = serial_wait_2 (tty_desc, port_desc, -1);
587
588       if (mask & 2)
589         {                       /* tty input */
590           char cx;
591
592           while (1)
593             {
594               c = serial_readchar (tty_desc, 0);
595
596               if (c == SERIAL_TIMEOUT)
597                 break;
598
599               if (c < 0)
600                 perror_with_name ("connect");
601
602               cx = c;
603               serial_write (port_desc, &cx, 1);
604
605               switch (cur_esc)
606                 {
607                 case 0:
608                   if (c == '\r')
609                     cur_esc = c;
610                   break;
611                 case '\r':
612                   if (c == '~')
613                     cur_esc = c;
614                   else
615                     cur_esc = 0;
616                   break;
617                 case '~':
618                   if (c == '.' || c == '\004')
619                     return;
620                   else
621                     cur_esc = 0;
622                 }
623             }
624         }
625
626       if (mask & 1)
627         {                       /* Port input */
628           char cx;
629
630           while (1)
631             {
632               c = serial_readchar (port_desc, 0);
633
634               if (c == SERIAL_TIMEOUT)
635                 break;
636
637               if (c < 0)
638                 perror_with_name ("connect");
639
640               cx = c;
641
642               serial_write (tty_desc, &cx, 1);
643             }
644         }
645     }
646 }
647 #endif /* 0 */
648
649 /* Serial set/show framework.  */
650
651 static struct cmd_list_element *serial_set_cmdlist;
652 static struct cmd_list_element *serial_show_cmdlist;
653
654 static void
655 serial_set_cmd (char *args, int from_tty)
656 {
657   printf_unfiltered ("\"set serial\" must be followed by the name of a command.\n");
658   help_list (serial_set_cmdlist, "set serial ", -1, gdb_stdout);
659 }
660
661 static void
662 serial_show_cmd (char *args, int from_tty)
663 {
664   cmd_show_list (serial_show_cmdlist, from_tty, "");
665 }
666
667
668 void
669 _initialize_serial (void)
670 {
671 #if 0
672   add_com ("connect", class_obscure, connect_command,
673            "Connect the terminal directly up to the command monitor.\n\
674 Use <CR>~. or <CR>~^D to break out.");
675 #endif /* 0 */
676
677   add_prefix_cmd ("serial", class_maintenance, serial_set_cmd, "\
678 Set default serial/parallel port configuration.",
679                   &serial_set_cmdlist, "set serial ",
680                   0/*allow-unknown*/,
681                   &setlist);
682
683   add_prefix_cmd ("serial", class_maintenance, serial_show_cmd, "\
684 Show default serial/parallel port configuration.",
685                   &serial_show_cmdlist, "show serial ",
686                   0/*allow-unknown*/,
687                   &showlist);
688
689   add_show_from_set
690     (add_set_cmd ("remotelogfile", no_class,
691                   var_filename, (char *) &serial_logfile,
692                   "Set filename for remote session recording.\n\
693 This file is used to record the remote session for future playback\n\
694 by gdbserver.",
695                   &setlist),
696      &showlist);
697
698   add_show_from_set
699     (add_set_enum_cmd ("remotelogbase", no_class,
700                        logbase_enums, &serial_logbase,
701                        "Set numerical base for remote session logging",
702                        &setlist),
703      &showlist);
704
705   add_show_from_set (add_set_cmd ("serial",
706                                   class_maintenance,
707                                   var_zinteger,
708                                   (char *)&global_serial_debug_p,
709                                   "Set serial debugging.\n\
710 When non-zero, serial port debugging is enabled.", &setdebuglist),
711                      &showdebuglist);
712 }