xref: /openbmc/u-boot/tools/gdb/serial.c (revision 5b1d7137)
1 #include <unistd.h>
2 #include <string.h>
3 #include <fcntl.h>
4 #include <sys/time.h>
5 #include "serial.h"
6 
7 #if defined(__sun__)	 || \
8     defined(__OpenBSD__) || \
9     defined(__FreeBSD__) || \
10     defined(__NetBSD__)	 || \
11     defined(__APPLE__)
12 static struct termios tios = { BRKINT, 0, B115200|CS8|CREAD, 0, { 0 } };
13 #else
14 static struct termios tios = { BRKINT, 0, B115200|CS8|CREAD, 0,   0   };
15 #endif
16 
17 static struct speedmap {
18     char *str;
19     speed_t val;
20 } speedmap[] = {
21     { "50", B50 },		{ "75", B75 },		{ "110", B110 },
22     { "134", B134 },		{ "150", B150 },	{ "200", B200 },
23     { "300", B300 },		{ "600", B600 },	{ "1200", B1200 },
24     { "1800", B1800 },		{ "2400", B2400 },	{ "4800", B4800 },
25     { "9600", B9600 },		{ "19200", B19200 },	{ "38400", B38400 },
26     { "57600", B57600 },
27 #ifdef	B76800
28     { "76800", B76800 },
29 #endif
30     { "115200", B115200 },
31 #ifdef	B153600
32     { "153600", B153600 },
33 #endif
34     { "230400", B230400 },
35 #ifdef	B307200
36     { "307200", B307200 },
37 #endif
38 #ifdef B460800
39     { "460800", B460800 }
40 #endif
41 };
42 static int nspeeds = sizeof speedmap / sizeof speedmap[0];
43 
44 speed_t
45 cvtspeed(char *str)
46 {
47     struct speedmap *smp = speedmap, *esmp = &speedmap[nspeeds];
48 
49     while (smp < esmp) {
50 	if (strcmp(str, smp->str) == 0)
51 	    return (smp->val);
52 	smp++;
53     }
54     return B0;
55 }
56 
57 int
58 serialopen(char *device, speed_t speed)
59 {
60     int fd;
61 
62     if (cfsetospeed(&tios, speed) < 0)
63 	return -1;
64 
65     if ((fd = open(device, O_RDWR)) < 0)
66 	return -1;
67 
68     if (tcsetattr(fd, TCSAFLUSH, &tios) < 0) {
69 	(void)close(fd);
70 	return -1;
71     }
72 
73     return fd;
74 }
75 
76 int
77 serialreadchar(int fd, int timeout)
78 {
79     fd_set fds;
80     struct timeval tv;
81     int n;
82     char ch;
83 
84     tv.tv_sec = timeout;
85     tv.tv_usec = 0;
86 
87     FD_ZERO(&fds);
88     FD_SET(fd, &fds);
89 
90     /* this is a fucking horrible quick hack - fix this */
91 
92     if ((n = select(fd + 1, &fds, 0, 0, &tv)) < 0)
93 	return SERIAL_ERROR;
94 
95     if (n == 0)
96 	return SERIAL_TIMEOUT;
97 
98     if ((n = read(fd, &ch, 1)) < 0)
99 	return SERIAL_ERROR;
100 
101     if (n == 0)
102 	return SERIAL_EOF;
103 
104     return ch;
105 }
106 
107 int
108 serialwrite(int fd, char *buf, int len)
109 {
110     int n;
111 
112     do {
113 	n = write(fd, buf, len);
114 	if (n < 0)
115 	    return 1;
116 	len -= n;
117 	buf += n;
118     } while (len > 0);
119     return 0;
120 }
121 
122 int
123 serialclose(int fd)
124 {
125     return close(fd);
126 }
127