import gdb-1999-08-30 snapshot
[external/binutils.git] / gdb / ser-unix.c
1 /* Serial interface for local (hardwired) serial ports on Un*x like systems
2    Copyright 1992, 1993, 1994, 1998 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,
19    Boston, MA 02111-1307, USA.  */
20
21 #include "defs.h"
22 #include "serial.h"
23 #include <fcntl.h>
24 #include <sys/types.h>
25 #include "terminal.h"
26
27 #ifdef HAVE_TERMIOS
28
29 struct hardwire_ttystate
30   {
31     struct termios termios;
32   };
33 #endif /* termios */
34
35 #ifdef HAVE_TERMIO
36
37 /* It is believed that all systems which have added job control to SVR3
38    (e.g. sco) have also added termios.  Even if not, trying to figure out
39    all the variations (TIOCGPGRP vs. TCGETPGRP, etc.) would be pretty
40    bewildering.  So we don't attempt it.  */
41
42 struct hardwire_ttystate
43   {
44     struct termio termio;
45   };
46 #endif /* termio */
47
48 #ifdef HAVE_SGTTY
49 /* Needed for the code which uses select().  We would include <sys/select.h>
50    too if it existed on all systems.  */
51 #include <sys/time.h>
52
53 struct hardwire_ttystate
54   {
55     struct sgttyb sgttyb;
56     struct tchars tc;
57     struct ltchars ltc;
58     /* Line discipline flags.  */
59     int lmode;
60   };
61 #endif /* sgtty */
62
63 static int hardwire_open PARAMS ((serial_t scb, const char *name));
64 static void hardwire_raw PARAMS ((serial_t scb));
65 static int wait_for PARAMS ((serial_t scb, int timeout));
66 static int hardwire_readchar PARAMS ((serial_t scb, int timeout));
67 static int rate_to_code PARAMS ((int rate));
68 static int hardwire_setbaudrate PARAMS ((serial_t scb, int rate));
69 static int hardwire_write PARAMS ((serial_t scb, const char *str, int len));
70 static void hardwire_close PARAMS ((serial_t scb));
71 static int get_tty_state PARAMS ((serial_t scb, struct hardwire_ttystate * state));
72 static int set_tty_state PARAMS ((serial_t scb, struct hardwire_ttystate * state));
73 static serial_ttystate hardwire_get_tty_state PARAMS ((serial_t scb));
74 static int hardwire_set_tty_state PARAMS ((serial_t scb, serial_ttystate state));
75 static int hardwire_noflush_set_tty_state PARAMS ((serial_t, serial_ttystate,
76                                                    serial_ttystate));
77 static void hardwire_print_tty_state PARAMS ((serial_t, serial_ttystate));
78 static int hardwire_drain_output PARAMS ((serial_t));
79 static int hardwire_flush_output PARAMS ((serial_t));
80 static int hardwire_flush_input PARAMS ((serial_t));
81 static int hardwire_send_break PARAMS ((serial_t));
82 static int hardwire_setstopbits PARAMS ((serial_t, int));
83
84 void _initialize_ser_hardwire PARAMS ((void));
85
86 extern int (*ui_loop_hook) PARAMS ((int));
87
88 /* Open up a real live device for serial I/O */
89
90 static int
91 hardwire_open (scb, name)
92      serial_t scb;
93      const char *name;
94 {
95   scb->fd = open (name, O_RDWR);
96   if (scb->fd < 0)
97     return -1;
98
99   return 0;
100 }
101
102 static int
103 get_tty_state (scb, state)
104      serial_t scb;
105      struct hardwire_ttystate *state;
106 {
107 #ifdef HAVE_TERMIOS
108   if (tcgetattr (scb->fd, &state->termios) < 0)
109     return -1;
110
111   return 0;
112 #endif
113
114 #ifdef HAVE_TERMIO
115   if (ioctl (scb->fd, TCGETA, &state->termio) < 0)
116     return -1;
117   return 0;
118 #endif
119
120 #ifdef HAVE_SGTTY
121   if (ioctl (scb->fd, TIOCGETP, &state->sgttyb) < 0)
122     return -1;
123   if (ioctl (scb->fd, TIOCGETC, &state->tc) < 0)
124     return -1;
125   if (ioctl (scb->fd, TIOCGLTC, &state->ltc) < 0)
126     return -1;
127   if (ioctl (scb->fd, TIOCLGET, &state->lmode) < 0)
128     return -1;
129
130   return 0;
131 #endif
132 }
133
134 static int
135 set_tty_state (scb, state)
136      serial_t scb;
137      struct hardwire_ttystate *state;
138 {
139 #ifdef HAVE_TERMIOS
140   if (tcsetattr (scb->fd, TCSANOW, &state->termios) < 0)
141     return -1;
142
143   return 0;
144 #endif
145
146 #ifdef HAVE_TERMIO
147   if (ioctl (scb->fd, TCSETA, &state->termio) < 0)
148     return -1;
149   return 0;
150 #endif
151
152 #ifdef HAVE_SGTTY
153   if (ioctl (scb->fd, TIOCSETN, &state->sgttyb) < 0)
154     return -1;
155   if (ioctl (scb->fd, TIOCSETC, &state->tc) < 0)
156     return -1;
157   if (ioctl (scb->fd, TIOCSLTC, &state->ltc) < 0)
158     return -1;
159   if (ioctl (scb->fd, TIOCLSET, &state->lmode) < 0)
160     return -1;
161
162   return 0;
163 #endif
164 }
165
166 static serial_ttystate
167 hardwire_get_tty_state (scb)
168      serial_t scb;
169 {
170   struct hardwire_ttystate *state;
171
172   state = (struct hardwire_ttystate *) xmalloc (sizeof *state);
173
174   if (get_tty_state (scb, state))
175     return NULL;
176
177   return (serial_ttystate) state;
178 }
179
180 static int
181 hardwire_set_tty_state (scb, ttystate)
182      serial_t scb;
183      serial_ttystate ttystate;
184 {
185   struct hardwire_ttystate *state;
186
187   state = (struct hardwire_ttystate *) ttystate;
188
189   return set_tty_state (scb, state);
190 }
191
192 static int
193 hardwire_noflush_set_tty_state (scb, new_ttystate, old_ttystate)
194      serial_t scb;
195      serial_ttystate new_ttystate;
196      serial_ttystate old_ttystate;
197 {
198   struct hardwire_ttystate new_state;
199 #ifdef HAVE_SGTTY
200   struct hardwire_ttystate *state = (struct hardwire_ttystate *) old_ttystate;
201 #endif
202
203   new_state = *(struct hardwire_ttystate *) new_ttystate;
204
205   /* Don't change in or out of raw mode; we don't want to flush input.
206      termio and termios have no such restriction; for them flushing input
207      is separate from setting the attributes.  */
208
209 #ifdef HAVE_SGTTY
210   if (state->sgttyb.sg_flags & RAW)
211     new_state.sgttyb.sg_flags |= RAW;
212   else
213     new_state.sgttyb.sg_flags &= ~RAW;
214
215   /* I'm not sure whether this is necessary; the manpage just mentions
216      RAW not CBREAK.  */
217   if (state->sgttyb.sg_flags & CBREAK)
218     new_state.sgttyb.sg_flags |= CBREAK;
219   else
220     new_state.sgttyb.sg_flags &= ~CBREAK;
221 #endif
222
223   return set_tty_state (scb, &new_state);
224 }
225
226 static void
227 hardwire_print_tty_state (scb, ttystate)
228      serial_t scb;
229      serial_ttystate ttystate;
230 {
231   struct hardwire_ttystate *state = (struct hardwire_ttystate *) ttystate;
232   int i;
233
234 #ifdef HAVE_TERMIOS
235   printf_filtered ("c_iflag = 0x%x, c_oflag = 0x%x,\n",
236                    state->termios.c_iflag, state->termios.c_oflag);
237   printf_filtered ("c_cflag = 0x%x, c_lflag = 0x%x\n",
238                    state->termios.c_cflag, state->termios.c_lflag);
239 #if 0
240   /* This not in POSIX, and is not really documented by those systems
241      which have it (at least not Sun).  */
242   printf_filtered ("c_line = 0x%x.\n", state->termios.c_line);
243 #endif
244   printf_filtered ("c_cc: ");
245   for (i = 0; i < NCCS; i += 1)
246     printf_filtered ("0x%x ", state->termios.c_cc[i]);
247   printf_filtered ("\n");
248 #endif
249
250 #ifdef HAVE_TERMIO
251   printf_filtered ("c_iflag = 0x%x, c_oflag = 0x%x,\n",
252                    state->termio.c_iflag, state->termio.c_oflag);
253   printf_filtered ("c_cflag = 0x%x, c_lflag = 0x%x, c_line = 0x%x.\n",
254                    state->termio.c_cflag, state->termio.c_lflag,
255                    state->termio.c_line);
256   printf_filtered ("c_cc: ");
257   for (i = 0; i < NCC; i += 1)
258     printf_filtered ("0x%x ", state->termio.c_cc[i]);
259   printf_filtered ("\n");
260 #endif
261
262 #ifdef HAVE_SGTTY
263   printf_filtered ("sgttyb.sg_flags = 0x%x.\n", state->sgttyb.sg_flags);
264
265   printf_filtered ("tchars: ");
266   for (i = 0; i < (int) sizeof (struct tchars); i++)
267     printf_filtered ("0x%x ", ((unsigned char *) &state->tc)[i]);
268   printf_filtered ("\n");
269
270   printf_filtered ("ltchars: ");
271   for (i = 0; i < (int) sizeof (struct ltchars); i++)
272     printf_filtered ("0x%x ", ((unsigned char *) &state->ltc)[i]);
273   printf_filtered ("\n");
274
275   printf_filtered ("lmode:  0x%x\n", state->lmode);
276 #endif
277 }
278
279 /* Wait for the output to drain away, as opposed to flushing (discarding) it */
280
281 static int
282 hardwire_drain_output (scb)
283      serial_t scb;
284 {
285 #ifdef HAVE_TERMIOS
286   return tcdrain (scb->fd);
287 #endif
288
289 #ifdef HAVE_TERMIO
290   return ioctl (scb->fd, TCSBRK, 1);
291 #endif
292
293 #ifdef HAVE_SGTTY
294   /* Get the current state and then restore it using TIOCSETP,
295      which should cause the output to drain and pending input
296      to be discarded. */
297   {
298     struct hardwire_ttystate state;
299     if (get_tty_state (scb, &state))
300       {
301         return (-1);
302       }
303     else
304       {
305         return (ioctl (scb->fd, TIOCSETP, &state.sgttyb));
306       }
307   }
308 #endif
309 }
310
311 static int
312 hardwire_flush_output (scb)
313      serial_t scb;
314 {
315 #ifdef HAVE_TERMIOS
316   return tcflush (scb->fd, TCOFLUSH);
317 #endif
318
319 #ifdef HAVE_TERMIO
320   return ioctl (scb->fd, TCFLSH, 1);
321 #endif
322
323 #ifdef HAVE_SGTTY
324   /* This flushes both input and output, but we can't do better.  */
325   return ioctl (scb->fd, TIOCFLUSH, 0);
326 #endif
327 }
328
329 static int
330 hardwire_flush_input (scb)
331      serial_t scb;
332 {
333   scb->bufcnt = 0;
334   scb->bufp = scb->buf;
335
336 #ifdef HAVE_TERMIOS
337   return tcflush (scb->fd, TCIFLUSH);
338 #endif
339
340 #ifdef HAVE_TERMIO
341   return ioctl (scb->fd, TCFLSH, 0);
342 #endif
343
344 #ifdef HAVE_SGTTY
345   /* This flushes both input and output, but we can't do better.  */
346   return ioctl (scb->fd, TIOCFLUSH, 0);
347 #endif
348 }
349
350 static int
351 hardwire_send_break (scb)
352      serial_t scb;
353 {
354 #ifdef HAVE_TERMIOS
355   return tcsendbreak (scb->fd, 0);
356 #endif
357
358 #ifdef HAVE_TERMIO
359   return ioctl (scb->fd, TCSBRK, 0);
360 #endif
361
362 #ifdef HAVE_SGTTY
363   {
364     int status;
365     struct timeval timeout;
366
367     status = ioctl (scb->fd, TIOCSBRK, 0);
368
369     /* Can't use usleep; it doesn't exist in BSD 4.2.  */
370     /* Note that if this select() is interrupted by a signal it will not wait
371        the full length of time.  I think that is OK.  */
372     timeout.tv_sec = 0;
373     timeout.tv_usec = 250000;
374     select (0, 0, 0, 0, &timeout);
375     status = ioctl (scb->fd, TIOCCBRK, 0);
376     return status;
377   }
378 #endif
379 }
380
381 static void
382 hardwire_raw (scb)
383      serial_t scb;
384 {
385   struct hardwire_ttystate state;
386
387   if (get_tty_state (scb, &state))
388     fprintf_unfiltered (gdb_stderr, "get_tty_state failed: %s\n", safe_strerror (errno));
389
390 #ifdef HAVE_TERMIOS
391   state.termios.c_iflag = 0;
392   state.termios.c_oflag = 0;
393   state.termios.c_lflag = 0;
394   state.termios.c_cflag &= ~(CSIZE | PARENB);
395   state.termios.c_cflag |= CLOCAL | CS8;
396   state.termios.c_cc[VMIN] = 0;
397   state.termios.c_cc[VTIME] = 0;
398 #endif
399
400 #ifdef HAVE_TERMIO
401   state.termio.c_iflag = 0;
402   state.termio.c_oflag = 0;
403   state.termio.c_lflag = 0;
404   state.termio.c_cflag &= ~(CSIZE | PARENB);
405   state.termio.c_cflag |= CLOCAL | CS8;
406   state.termio.c_cc[VMIN] = 0;
407   state.termio.c_cc[VTIME] = 0;
408 #endif
409
410 #ifdef HAVE_SGTTY
411   state.sgttyb.sg_flags |= RAW | ANYP;
412   state.sgttyb.sg_flags &= ~(CBREAK | ECHO);
413 #endif
414
415   scb->current_timeout = 0;
416
417   if (set_tty_state (scb, &state))
418     fprintf_unfiltered (gdb_stderr, "set_tty_state failed: %s\n", safe_strerror (errno));
419 }
420
421 /* Wait for input on scb, with timeout seconds.  Returns 0 on success,
422    otherwise SERIAL_TIMEOUT or SERIAL_ERROR.
423
424    For termio{s}, we actually just setup VTIME if necessary, and let the
425    timeout occur in the read() in hardwire_read().
426  */
427
428 static int
429 wait_for (scb, timeout)
430      serial_t scb;
431      int timeout;
432 {
433 #ifdef HAVE_SGTTY
434   {
435     struct timeval tv;
436     fd_set readfds;
437
438     FD_ZERO (&readfds);
439
440     tv.tv_sec = timeout;
441     tv.tv_usec = 0;
442
443     FD_SET (scb->fd, &readfds);
444
445     while (1)
446       {
447         int numfds;
448
449         if (timeout >= 0)
450           numfds = select (scb->fd + 1, &readfds, 0, 0, &tv);
451         else
452           numfds = select (scb->fd + 1, &readfds, 0, 0, 0);
453
454         if (numfds <= 0)
455           if (numfds == 0)
456             return SERIAL_TIMEOUT;
457           else if (errno == EINTR)
458             continue;
459           else
460             return SERIAL_ERROR;        /* Got an error from select or poll */
461
462         return 0;
463       }
464   }
465 #endif /* HAVE_SGTTY */
466
467 #if defined HAVE_TERMIO || defined HAVE_TERMIOS
468   if (timeout == scb->current_timeout)
469     return 0;
470
471   scb->current_timeout = timeout;
472
473   {
474     struct hardwire_ttystate state;
475
476     if (get_tty_state (scb, &state))
477       fprintf_unfiltered (gdb_stderr, "get_tty_state failed: %s\n", safe_strerror (errno));
478
479 #ifdef HAVE_TERMIOS
480     if (timeout < 0)
481       {
482         /* No timeout.  */
483         state.termios.c_cc[VTIME] = 0;
484         state.termios.c_cc[VMIN] = 1;
485       }
486     else
487       {
488         state.termios.c_cc[VMIN] = 0;
489         state.termios.c_cc[VTIME] = timeout * 10;
490         if (state.termios.c_cc[VTIME] != timeout * 10)
491           {
492
493             /* If c_cc is an 8-bit signed character, we can't go 
494                bigger than this.  If it is always unsigned, we could use
495                25.  */
496
497             scb->current_timeout = 12;
498             state.termios.c_cc[VTIME] = scb->current_timeout * 10;
499             scb->timeout_remaining = timeout - scb->current_timeout;
500           }
501       }
502 #endif
503
504 #ifdef HAVE_TERMIO
505     if (timeout < 0)
506       {
507         /* No timeout.  */
508         state.termio.c_cc[VTIME] = 0;
509         state.termio.c_cc[VMIN] = 1;
510       }
511     else
512       {
513         state.termio.c_cc[VMIN] = 0;
514         state.termio.c_cc[VTIME] = timeout * 10;
515         if (state.termio.c_cc[VTIME] != timeout * 10)
516           {
517             /* If c_cc is an 8-bit signed character, we can't go 
518                bigger than this.  If it is always unsigned, we could use
519                25.  */
520
521             scb->current_timeout = 12;
522             state.termio.c_cc[VTIME] = scb->current_timeout * 10;
523             scb->timeout_remaining = timeout - scb->current_timeout;
524           }
525       }
526 #endif
527
528     if (set_tty_state (scb, &state))
529       fprintf_unfiltered (gdb_stderr, "set_tty_state failed: %s\n", safe_strerror (errno));
530
531     return 0;
532   }
533 #endif /* HAVE_TERMIO || HAVE_TERMIOS */
534 }
535
536 /* Read a character with user-specified timeout.  TIMEOUT is number of seconds
537    to wait, or -1 to wait forever.  Use timeout of 0 to effect a poll.  Returns
538    char if successful.  Returns SERIAL_TIMEOUT if timeout expired, EOF if line
539    dropped dead, or SERIAL_ERROR for any other error (see errno in that case).  */
540 static int
541 hardwire_readchar (scb, timeout)
542      serial_t scb;
543      int timeout;
544 {
545   int status, delta;
546   int detach = 0;
547
548   if (scb->bufcnt-- > 0)
549     return *scb->bufp++;
550
551   if (timeout > 0)
552     timeout++;
553
554   /* We have to be able to keep the GUI alive here, so we break the original
555      timeout into steps of 1 second, running the "keep the GUI alive" hook 
556      each time through the loop.
557      Also, timeout = 0 means to poll, so we just set the delta to 0, so we
558      will only go through the loop once. */
559
560   delta = (timeout == 0 ? 0 : 1);
561   while (1)
562     {
563
564       /* N.B. The UI may destroy our world (for instance by calling
565          remote_stop,) in which case we want to get out of here as
566          quickly as possible.  It is not safe to touch scb, since
567          someone else might have freed it.  The ui_loop_hook signals that 
568          we should exit by returning 1. */
569
570       if (ui_loop_hook)
571         detach = ui_loop_hook (0);
572
573       if (detach)
574         return SERIAL_TIMEOUT;
575
576       scb->timeout_remaining = (timeout < 0 ? timeout : timeout - delta);
577       status = wait_for (scb, delta);
578
579       if (status < 0)
580         return status;
581
582       scb->bufcnt = read (scb->fd, scb->buf, BUFSIZ);
583
584       if (scb->bufcnt <= 0)
585         {
586           if (scb->bufcnt == 0)
587             {
588               /* Zero characters means timeout (it could also be EOF, but
589                  we don't (yet at least) distinguish).  */
590               if (scb->timeout_remaining > 0)
591                 {
592                   timeout = scb->timeout_remaining;
593                   continue;
594                 }
595               else if (scb->timeout_remaining < 0)
596                 continue;
597               else
598                 return SERIAL_TIMEOUT;
599             }
600           else if (errno == EINTR)
601             continue;
602           else
603             return SERIAL_ERROR;        /* Got an error from read */
604         }
605
606       scb->bufcnt--;
607       scb->bufp = scb->buf;
608       return *scb->bufp++;
609     }
610 }
611
612 #ifndef B19200
613 #define B19200 EXTA
614 #endif
615
616 #ifndef B38400
617 #define B38400 EXTB
618 #endif
619
620 /* Translate baud rates from integers to damn B_codes.  Unix should
621    have outgrown this crap years ago, but even POSIX wouldn't buck it.  */
622
623 static struct
624 {
625   int rate;
626   int code;
627 }
628 baudtab[] =
629 {
630   {
631     50, B50
632   }
633   ,
634   {
635     75, B75
636   }
637   ,
638   {
639     110, B110
640   }
641   ,
642   {
643     134, B134
644   }
645   ,
646   {
647     150, B150
648   }
649   ,
650   {
651     200, B200
652   }
653   ,
654   {
655     300, B300
656   }
657   ,
658   {
659     600, B600
660   }
661   ,
662   {
663     1200, B1200
664   }
665   ,
666   {
667     1800, B1800
668   }
669   ,
670   {
671     2400, B2400
672   }
673   ,
674   {
675     4800, B4800
676   }
677   ,
678   {
679     9600, B9600
680   }
681   ,
682   {
683     19200, B19200
684   }
685   ,
686   {
687     38400, B38400
688   }
689   ,
690 #ifdef B57600
691   {
692     57600, B57600
693   }
694   ,
695 #endif
696 #ifdef B115200
697   {
698     115200, B115200
699   }
700   ,
701 #endif
702 #ifdef B230400
703   {
704     230400, B230400
705   }
706   ,
707 #endif
708 #ifdef B460800
709   {
710     460800, B460800
711   }
712   ,
713 #endif
714   {
715     -1, -1
716   }
717   ,
718 };
719
720 static int
721 rate_to_code (rate)
722      int rate;
723 {
724   int i;
725
726   for (i = 0; baudtab[i].rate != -1; i++)
727     if (rate == baudtab[i].rate)
728       return baudtab[i].code;
729
730   return -1;
731 }
732
733 static int
734 hardwire_setbaudrate (scb, rate)
735      serial_t scb;
736      int rate;
737 {
738   struct hardwire_ttystate state;
739
740   if (get_tty_state (scb, &state))
741     return -1;
742
743 #ifdef HAVE_TERMIOS
744   cfsetospeed (&state.termios, rate_to_code (rate));
745   cfsetispeed (&state.termios, rate_to_code (rate));
746 #endif
747
748 #ifdef HAVE_TERMIO
749 #ifndef CIBAUD
750 #define CIBAUD CBAUD
751 #endif
752
753   state.termio.c_cflag &= ~(CBAUD | CIBAUD);
754   state.termio.c_cflag |= rate_to_code (rate);
755 #endif
756
757 #ifdef HAVE_SGTTY
758   state.sgttyb.sg_ispeed = rate_to_code (rate);
759   state.sgttyb.sg_ospeed = rate_to_code (rate);
760 #endif
761
762   return set_tty_state (scb, &state);
763 }
764
765 static int
766 hardwire_setstopbits (scb, num)
767      serial_t scb;
768      int num;
769 {
770   struct hardwire_ttystate state;
771   int newbit;
772
773   if (get_tty_state (scb, &state))
774     return -1;
775
776   switch (num)
777     {
778     case SERIAL_1_STOPBITS:
779       newbit = 0;
780       break;
781     case SERIAL_1_AND_A_HALF_STOPBITS:
782     case SERIAL_2_STOPBITS:
783       newbit = 1;
784       break;
785     default:
786       return 1;
787     }
788
789 #ifdef HAVE_TERMIOS
790   if (!newbit)
791     state.termios.c_cflag &= ~CSTOPB;
792   else
793     state.termios.c_cflag |= CSTOPB;    /* two bits */
794 #endif
795
796 #ifdef HAVE_TERMIO
797   if (!newbit)
798     state.termio.c_cflag &= ~CSTOPB;
799   else
800     state.termio.c_cflag |= CSTOPB;     /* two bits */
801 #endif
802
803 #ifdef HAVE_SGTTY
804   return 0;                     /* sgtty doesn't support this */
805 #endif
806
807   return set_tty_state (scb, &state);
808 }
809
810 static int
811 hardwire_write (scb, str, len)
812      serial_t scb;
813      const char *str;
814      int len;
815 {
816   int cc;
817
818   while (len > 0)
819     {
820       cc = write (scb->fd, str, len);
821
822       if (cc < 0)
823         return 1;
824       len -= cc;
825       str += cc;
826     }
827   return 0;
828 }
829
830 static void
831 hardwire_close (scb)
832      serial_t scb;
833 {
834   if (scb->fd < 0)
835     return;
836
837   close (scb->fd);
838   scb->fd = -1;
839 }
840
841 static struct serial_ops hardwire_ops =
842 {
843   "hardwire",
844   0,
845   hardwire_open,
846   hardwire_close,
847   hardwire_readchar,
848   hardwire_write,
849   hardwire_flush_output,
850   hardwire_flush_input,
851   hardwire_send_break,
852   hardwire_raw,
853   hardwire_get_tty_state,
854   hardwire_set_tty_state,
855   hardwire_print_tty_state,
856   hardwire_noflush_set_tty_state,
857   hardwire_setbaudrate,
858   hardwire_setstopbits,
859   hardwire_drain_output,        /* wait for output to drain */
860 };
861
862 void
863 _initialize_ser_hardwire ()
864 {
865   serial_add_interface (&hardwire_ops);
866 }