From 62bc1af6c6a1201db551e1ec523e757415464fd5 Mon Sep 17 00:00:00 2001 From: root Date: Sun, 25 Oct 2020 13:26:29 +0000 Subject: tidy up, make less awful --- util.c | 306 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 306 insertions(+) create mode 100644 util.c (limited to 'util.c') diff --git a/util.c b/util.c new file mode 100644 index 0000000..95268b4 --- /dev/null +++ b/util.c @@ -0,0 +1,306 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + + + +#include "util.h" + + +void +set_nonblocking (int fd) +{ + long arg = 0; + arg = fcntl (fd, F_GETFL, arg); + arg |= O_NONBLOCK; + fcntl (fd, F_SETFL, arg); +} + +void +set_blocking (int fd) +{ + long arg = 0; + arg = fcntl (fd, F_GETFL, arg); + arg &= ~O_NONBLOCK; + fcntl (fd, F_SETFL, arg); +} + +int fd_can_read (int fd) +{ + struct timeval tv = {0}; + fd_set rfds; + FD_ZERO (&rfds); + FD_SET (fd, &rfds); + + if (select (fd + 1, &rfds, NULL, NULL, &tv) == 1) + return 1; + + return 0; +} + +int fd_drain (int fd) +{ + char c; + + while (fd_can_read (fd)) + if (read (fd, &c, 1) != 1) return -1; + + + return 0; +} + + +static speed_t +baud_to_speed_t (int baud) +{ + switch (baud) { +#ifdef B0 + + case 0: + return B0; +#endif +#ifdef B50 + + case 50: + return B50; +#endif +#ifdef B75 + + case 75: + return B75; +#endif +#ifdef B110 + + case 110: + return B110; +#endif +#ifdef B134 + + case 134: + return B134; +#endif +#ifdef B150 + + case 150: + return B150; +#endif +#ifdef B200 + + case 200: + return B200; +#endif +#ifdef B300 + + case 300: + return B300; +#endif +#ifdef B600 + + case 600: + return B600; +#endif +#ifdef B1200 + + case 1200: + return B1200; +#endif +#ifdef B1800 + + case 1800: + return B1800; +#endif +#ifdef B2400 + + case 2400: + return B2400; +#endif +#ifdef B4800 + + case 4800: + return B4800; +#endif +#ifdef B9600 + + case 9600: + return B9600; +#endif +#ifdef B19200 + + case 19200: + return B19200; +#endif +#ifdef B38400 + + case 38400: + return B38400; +#endif +#ifdef B57600 + + case 57600: + return B57600; +#endif +#ifdef B115200 + + case 115200: + return B115200; +#endif +#ifdef B230400 + + case 230400: + return B230400; +#endif + } + + return -1; +} + + + +static void +default_termios (struct termios *termios) +{ + termios->c_iflag = 0; + termios->c_oflag = NL0 | CR0 | TAB0 | BS0 | VT0 | FF0; + termios->c_lflag = 0; + termios->c_cflag = CS8 | CREAD | CLOCAL; + + termios->c_cc[VINTR] = 003; + termios->c_cc[VQUIT] = 034; + termios->c_cc[VERASE] = 0177; + termios->c_cc[VKILL] = 025; + termios->c_cc[VEOF] = 004; + termios->c_cc[VEOL] = 0; + termios->c_cc[VEOL2] = 0; + termios->c_cc[VSTART] = 021; + termios->c_cc[VSTOP] = 023; + termios->c_cc[VSUSP] = 032; + termios->c_cc[VLNEXT] = 026; + termios->c_cc[VWERASE] = 027; + termios->c_cc[VREPRINT] = 022; + termios->c_cc[VDISCARD] = 017; + + +} + + +//XXX: no locks + +int open_tty (const char *path, int baud) +{ + int fd; + struct termios termios; + speed_t s = baud_to_speed_t (baud); + + if (s == (speed_t) -1) return -1; + + + fd = open (path, O_RDWR | O_NOCTTY | O_NONBLOCK); + + + if (tcgetattr (fd, &termios)) { + close (fd); + return -1; + } + + default_termios (&termios); + + if (tcsetattr (fd, TCSANOW, &termios)) { + close (fd); + return -1; + } + + cfsetispeed (&termios, s); + cfsetospeed (&termios, s); + + return fd; +} + + + +static int host_to_sin (const char *host, struct sockaddr_in *sin) +{ + + struct hostent *he = gethostbyname2 (host, AF_INET); + + if (!he) { + if (!inet_aton (host, &sin->sin_addr)) + return -1; + + return 0; + } + + if (he->h_addrtype != AF_INET) + return -1; + + sin->sin_family = AF_INET; + + memcpy (&sin->sin_addr, he->h_addr_list[0], he->h_length); + + return 0; +} + + +int open_tcp_client (const char *host, unsigned port) +{ + struct sockaddr_in sin = {0}; + int fd; + + + if (host_to_sin (host, &sin)) + return -1; + + + fd = socket (PF_INET, SOCK_STREAM, 0); + + if (fd < 0) return -1; + + sin.sin_port = htons (port); + + if (connect (fd, (struct sockaddr *)&sin, sizeof (sin))) { + close (fd); + return -1; + } + + return fd; +} + +int open_tcp_server (unsigned port) +{ + int fd; + int enable = 1; + struct sockaddr_in sin = {0}; + + fd = socket (PF_INET, SOCK_STREAM, 0); + + if (fd < 0) return -1; + + if (setsockopt (fd, SOL_SOCKET, SO_REUSEADDR, &enable, sizeof (enable))) + return -1; + + sin.sin_family = AF_INET; + sin.sin_port = htons (port); + sin.sin_addr.s_addr = INADDR_ANY; + + if (bind (fd, (struct sockaddr *)&sin, sizeof (sin))) { + close (fd); + return -1; + } + + if (listen (fd, 5)) { + close (fd); + return -1; + } + + return fd; +} + + + + -- cgit v1.2.3