summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarc Balmer <mbalmer@cvs.openbsd.org>2007-11-03 15:22:55 +0000
committerMarc Balmer <mbalmer@cvs.openbsd.org>2007-11-03 15:22:55 +0000
commit2f089dff11daa9936fc599117e35ee39cf77f271 (patch)
tree87ccd46911e8742217fc6ab4607e97d313d34f57
parent5c64f6f7434f9454799bce6568464c9e08bbbcad (diff)
ldattach(8) is a command to attach line discipline to a tty line. It can
be used from the command line or from init(8) by adding an entry to the /etc/ttys file. ldattach(8) can be extended to support new line disciplines. feedback many, ok deraadt, mikeb
-rw-r--r--sbin/ldattach/Makefile10
-rw-r--r--sbin/ldattach/ldattach.8152
-rw-r--r--sbin/ldattach/ldattach.c219
3 files changed, 381 insertions, 0 deletions
diff --git a/sbin/ldattach/Makefile b/sbin/ldattach/Makefile
new file mode 100644
index 00000000000..fd297d48bf6
--- /dev/null
+++ b/sbin/ldattach/Makefile
@@ -0,0 +1,10 @@
+# $OpenBSD: Makefile,v 1.1 2007/11/03 15:22:54 mbalmer Exp $
+
+PROG= ldattach
+MAN= ldattach.8
+
+CFLAGS+= -Wall -Werror
+
+BINDIR= /sbin
+
+.include <bsd.prog.mk>
diff --git a/sbin/ldattach/ldattach.8 b/sbin/ldattach/ldattach.8
new file mode 100644
index 00000000000..bc56d232198
--- /dev/null
+++ b/sbin/ldattach/ldattach.8
@@ -0,0 +1,152 @@
+.\" $OpenBSD: ldattach.8,v 1.1 2007/11/03 15:22:54 mbalmer Exp $
+.\"
+.\" Copyright (c) 2007 Marc Balmer <mbalmer@openbsd.org>
+.\"
+.\" Permission to use, copy, modify, and distribute this software for any
+.\" purpose with or without fee is hereby granted, provided that the above
+.\" copyright notice and this permission notice appear in all copies.
+.\"
+.\" THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+.\" WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+.\" MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+.\" ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+.\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+.\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+.\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+.\"
+.Dd $Mdocdate: November 3 2007 $
+.Dt LDATTACH 8
+.Os
+.Sh NAME
+.Nm ldattach
+.Nd attach a line discipline to a serial line
+.Sh SYNOPSIS
+.Nm ldattach
+.Op Fl 7dehmo
+.Op Fl s Ar baudrate
+.Op Fl t Ar cond
+.Ar discipline
+.Ar device
+.Sh DESCRIPTION
+.Nm
+is used to attach a line discipline to a serial line to allow for in-kernel
+processing of the received and/or sent data.
+Depending on the line discipline being attached, one or more options may be
+applied.
+.Pp
+.Nm
+can be used from the command line or in
+.Xr ttys 5
+entries to attach line disciplines at system startup time by having
+.Xr init 8
+start
+.Nm
+on the designated interface.
+.Pp
+The following options are available:
+.Bl -tag -width Ds
+.It Fl 7
+Use 7 databits instead of 8.
+.It Fl d
+Do not daemonize.
+.It Fl e
+Use even parity.
+If both
+.Fl e
+and
+.Fl o
+are given, then no parity is used (the default).
+.It Fl h
+Turn on RTS/CTS flow control.
+By default, no flow control is done.
+.It Fl m
+Maintain modem control signals after closing the line.
+Specifically, this disables HUPCL.
+.It Fl o
+Use odd parity.
+If both
+.Fl e
+and
+.Fl o
+are given, then no parity is used (the default).
+.It Fl s Ar baudrate
+Specifies the speed of the connection.
+If not specified, the default of 4800 baud is used.
+.It Fl t Ar cond
+.Xr nmea 4
+line discipline only.
+Chooses the condition which will cause the current system time to be
+immediately copied to the terminal timestamp storage for subsequent use by
+.Xr nmea 4 .
+Only one can be used.
+.Pp
+.Bl -tag -width DCDXX -offset indent -compact
+.It dcd
+Copy the timestamp when DCD is asserted.
+.It !dcd
+Copy the timestamp when DCD is deasserted.
+.It cts
+Copy the timestamp when CTS is asserted.
+.It !cts
+Copy the timestamp when CTS is deasserted.
+.El
+.Pp
+If no condition is specified, the
+.Xr nmea 4
+line discipline will timestamp on receiving the leading
+.Sq $
+character of each block of NMEA sentences.
+.It Ar discipline
+Specifies the name of the line discipline to be attached.
+.Pp
+.Bl -tag -width nmeaXX -offset -indet -compact
+.It nmea
+Attach the
+.Xr nmea 4
+line discipline.
+.It slip
+Attach the
+.Xr sl 4
+line discipline.
+.El
+.It Ar device
+Specifies the name of the serial line.
+.Ar device
+should be a string of the form
+.Dq cuaXX ,
+or
+.Dq /dev/cuaXX .
+.El
+.Pp
+If
+.Nm
+was not started by
+.Xr init 8 ,
+the line discipline can be detached by
+killing off the
+.Nm
+process.
+.Sh EXAMPLES
+To start
+.Nm
+by using
+.Xr init 8
+to attach the
+.Xr nmea 4
+line discipline to
+.Pa /dev/cua00 ,
+add a line of the following form to
+.Pa /etc/ttys :
+.Bd -literal -offset indent
+cua00 "/sbin/ldattach nmea" unknown on
+.Ed
+.Sh SEE ALSO
+.Xr nmea 4 ,
+.Xr sl 4 ,
+.Xr tty 4 ,
+.Xr ttys 5
+.Sh HISTORY
+The
+.Nm
+command first appeared in
+.Ox 4.3 .
diff --git a/sbin/ldattach/ldattach.c b/sbin/ldattach/ldattach.c
new file mode 100644
index 00000000000..e7fb3238f3b
--- /dev/null
+++ b/sbin/ldattach/ldattach.c
@@ -0,0 +1,219 @@
+/* $OpenBSD: ldattach.c,v 1.1 2007/11/03 15:22:54 mbalmer Exp $ */
+
+/*
+ * Copyright (c) 2007 Marc Balmer <mbalmer@openbsd.org>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/*
+ * A replacement for slattach(8) and nmeaattach(8) that can be used from
+ * the commandline or from init(8) (using entries in /etc/ttys).
+ */
+
+#include <sys/ioctl.h>
+#include <sys/ttycom.h>
+
+#include <err.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <paths.h>
+#include <signal.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <syslog.h>
+#include <termios.h>
+#include <unistd.h>
+
+__dead void usage(void);
+void coroner(int);
+
+volatile sig_atomic_t dying = 0;
+
+__dead void
+usage(void)
+{
+ extern char *__progname;
+
+ fprintf(stderr, "usage: %s [-7dehmo] [-s baudrate] "
+ "[-t cond] discipline device\n", __progname);
+ exit(1);
+}
+
+int
+main(int argc, char *argv[])
+{
+ struct termios tty;
+ struct tstamps tstamps;
+ const char *errstr;
+ tcflag_t cflag = HUPCL | CS8;
+ sigset_t sigset;
+ pid_t ppid;
+ int ch, fd, ldisc, nodaemon = 0, speed = B4800, parity = 0;
+ char devname[32], *dev, *disc;
+
+ tstamps.ts_set = tstamps.ts_clr = 0;
+
+ if ((ppid = getppid()) == 1)
+ nodaemon = 1;
+
+ while ((ch = getopt(argc, argv, "7dehmos:t:")) != -1) {
+ switch (ch) {
+ case '7':
+ cflag &= ~CS8;
+ cflag |= CS7;
+ break;
+ case 'd':
+ nodaemon = 1;
+ break;
+ case 'e':
+ if (parity != 0)
+ parity = 0; /* -o -e */
+ else
+ parity = -1; /* even */
+ break;
+ case 'h':
+ cflag |= CRTSCTS;
+ break;
+ case 'm':
+ cflag &= ~HUPCL;
+ break;
+ case 'o':
+ if (parity != 0)
+ parity = 0; /* -e -o */
+ else
+ parity = 1; /* odd */
+ break;
+ case 's':
+ speed = (int)strtonum(optarg, 50, 230400, &errstr);
+ if (errstr) {
+ if (ppid != 1)
+ errx(1, "speed is %s: %s", errstr,
+ optarg);
+ else
+ goto bail_out;
+ }
+ break;
+ case 't':
+ if (!strcasecmp(optarg, "dcd"))
+ tstamps.ts_set |= TIOCM_CAR;
+ else if (!strcasecmp(optarg, "!dcd"))
+ tstamps.ts_clr |= TIOCM_CAR;
+ else if (!strcasecmp(optarg, "cts"))
+ tstamps.ts_set |= TIOCM_CTS;
+ else if (!strcasecmp(optarg, "!cts"))
+ tstamps.ts_clr |= TIOCM_CTS;
+ else {
+ if (ppid != 1)
+ errx(1, "'%s' not supported for "
+ "timestamping", optarg);
+ else
+ goto bail_out;
+ }
+ break;
+ default:
+ if (ppid != -1)
+ usage();
+ }
+ }
+ argc -= optind;
+ argv += optind;
+
+ if (ppid != 1 && argc != 2)
+ usage();
+
+ disc = *argv++;
+ dev = *argv;
+ if (strncmp(_PATH_DEV, dev, sizeof(_PATH_DEV) - 1)) {
+ (void)snprintf(devname, sizeof(devname),
+ "%s%s", _PATH_DEV, dev);
+ dev = devname;
+ }
+ syslog(LOG_INFO, "attach %s on %s", disc, dev);
+ if ((fd = open(dev, O_RDWR)) < 0)
+ goto bail_out;
+
+ if (!strcmp(disc, "slip"))
+ ldisc = SLIPDISC;
+ else if (!strcmp(disc, "nmea"))
+ ldisc = NMEADISC;
+ else {
+ syslog(LOG_ERR, "unknown line discipline %s", disc);
+ goto bail_out;
+ }
+
+ switch (parity) {
+ case -1: /* even parity */
+ cflag |= PARENB;
+ break;
+ case 1: /* odd parity */
+ cflag |= PARENB | PARODD;
+ break;
+ }
+
+ tty.c_cflag = CREAD | cflag;
+ tty.c_iflag = 0;
+ tty.c_lflag = 0;
+ tty.c_oflag = 0;
+ tty.c_cc[VMIN] = 1;
+ tty.c_cc[VTIME] = 0;
+ cfsetspeed(&tty, speed);
+ if (tcsetattr(fd, TCSADRAIN, &tty) < 0) {
+ if (ppid != 1)
+ warnx("tcsetattr");
+ goto bail_out;
+ }
+
+ /* setup common to all line disciplines */
+ if (ioctl(fd, TIOCSDTR, 0) < 0)
+ warn("TIOCSDTR");
+ if (ioctl(fd, TIOCSETD, &ldisc) < 0) {
+ syslog(LOG_ERR, "can't set the %s line discipline on %s", disc,
+ dev);
+ goto bail_out;
+ }
+
+ /* line discpline specific setup */
+ switch (ldisc) {
+ case NMEADISC:
+ if (ioctl(fd, TIOCSTSTAMP, &tstamps) < 0) {
+ warnx("TIOCSTSTAMP");
+ goto bail_out;
+ }
+ break;
+ }
+
+ if (!nodaemon && daemon(0, 0))
+ errx(1, "can't daemonize");
+
+ signal(SIGHUP, coroner);
+ signal(SIGTERM, coroner);
+
+ sigemptyset(&sigset);
+ while (!dying)
+ sigsuspend(&sigset);
+
+bail_out:
+ if (ppid == 1)
+ sleep(30); /* delay restart when called from init */
+
+ return 0;
+}
+
+/* ARGSUSED */
+void
+coroner(int useless)
+{
+ dying = 1;
+}