summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSolomon Peachy <pizza@shaftnet.org>2014-10-14 11:16:02 -0400
committerSolomon Peachy <pizza@shaftnet.org>2014-10-14 11:16:02 -0400
commitd8d860c4587a0ce6138ca49a1e73c9e542be95fc (patch)
tree8eee0e22a10842102f3a480c39f397594616f602
parent4f06d96cef39340ea7c990c01c2f82de7e4f4adc (diff)
downloadsobredirect-d8d860c4587a0ce6138ca49a1e73c9e542be95fc.tar.gz
sobredirect-d8d860c4587a0ce6138ca49a1e73c9e542be95fc.tar.bz2
sobredirect-d8d860c4587a0ce6138ca49a1e73c9e542be95fc.zip
Add support for custom, nonstandard baud rates.
-rw-r--r--common.c39
1 files changed, 35 insertions, 4 deletions
diff --git a/common.c b/common.c
index 12ba671..7f9d887 100644
--- a/common.c
+++ b/common.c
@@ -22,12 +22,16 @@
#include "common.h"
#include <termios.h>
+#include <sys/ioctl.h>
+#include <linux/tty.h>
+#include <linux/serial.h>
int setserial(struct termios *cfg, int ser_fd, int baud,
int databits, char parity, int stopbits,
int hw_flow, int sw_flow, int modemlines)
{
int rval = 0;
+ int custom = 0;
rval = tcgetattr(ser_fd, cfg);
if (rval) goto done;
@@ -56,11 +60,23 @@ int setserial(struct termios *cfg, int ser_fd, int baud,
SERIAL_BAUD_CASE(57600);
SERIAL_BAUD_CASE(115200);
SERIAL_BAUD_CASE(230400);
+ SERIAL_BAUD_CASE(460800);
+ SERIAL_BAUD_CASE(576000);
+ SERIAL_BAUD_CASE(921600);
+ SERIAL_BAUD_CASE(1000000);
+ SERIAL_BAUD_CASE(1152000);
+ SERIAL_BAUD_CASE(1500000);
+ SERIAL_BAUD_CASE(2000000);
+ SERIAL_BAUD_CASE(2500000);
+ SERIAL_BAUD_CASE(3000000);
+ SERIAL_BAUD_CASE(3500000);
+ SERIAL_BAUD_CASE(4000000);
default:
- fprintf(stderr, "Invalid serial baud rate specified (%d)\n",
+ fprintf(stderr, "Non-standard baud rate specified; may not function (%d)\n",
baud);
- rval = 1;
- goto done;
+ cfsetispeed(cfg, B38400);
+ cfsetospeed(cfg, B38400);
+ custom = 1;
}
parity &= ~0x20; /* make things case insensitive */
@@ -138,9 +154,24 @@ int setserial(struct termios *cfg, int ser_fd, int baud,
rval = tcsetattr(ser_fd, TCSANOW, cfg);
if (rval) goto done;
+ if (custom) {
+ struct serial_struct serinfo;
+
+ if (ioctl(ser_fd, TIOCGSERIAL, &serinfo) < 0) {
+ perror("Can't get serial info:");
+ goto done;
+ }
+ serinfo.flags &= ~ASYNC_SPD_MASK;
+ serinfo.flags |= ASYNC_SPD_CUST;
+ serinfo.custom_divisor = serinfo.baud_base / baud;
+ if (ioctl(ser_fd, TIOCSSERIAL, &serinfo) < 0) {
+ perror("Can't set serial info:");
+ goto done;
+ }
+ }
+
done:
if (rval) fprintf(stderr, "ERROR.. %d\n", rval);
-
{
struct termios cfg2;
tcgetattr(ser_fd, &cfg2);