summaryrefslogtreecommitdiff
path: root/usr
diff options
context:
space:
mode:
authorToomas Soome <tsoome@me.com>2022-03-30 15:51:51 +0300
committerToomas Soome <tsoome@me.com>2022-07-13 21:54:45 +0300
commit902bba376031b794865234f1621102c7f4bf9d2b (patch)
tree2172b98882b7e03cf46d47c210c1e1419b4a6038 /usr
parent9b664393d4fdda96221e6ea9ea95790d3c15be70 (diff)
downloadillumos-joyent-902bba376031b794865234f1621102c7f4bf9d2b.tar.gz
14608 ttymon should use tty-mode property
Reviewed by: Jason King <jason.brian.king+illumos@gmail.com> Approved by: Robert Mustacchi <rm@fingolfin.org>
Diffstat (limited to 'usr')
-rw-r--r--usr/src/cmd/ttymon/tmchild.c2
-rw-r--r--usr/src/cmd/ttymon/tmexpress.c46
-rw-r--r--usr/src/cmd/ttymon/tmextern.h2
-rw-r--r--usr/src/cmd/ttymon/tmstruct.h1
-rw-r--r--usr/src/cmd/ttymon/tmterm.c2
-rw-r--r--usr/src/cmd/ttymon/ttymon.c88
6 files changed, 134 insertions, 7 deletions
diff --git a/usr/src/cmd/ttymon/tmchild.c b/usr/src/cmd/ttymon/tmchild.c
index a58099974b..960a9a816c 100644
--- a/usr/src/cmd/ttymon/tmchild.c
+++ b/usr/src/cmd/ttymon/tmchild.c
@@ -99,7 +99,7 @@ tmchild(struct pmtab *pmtab)
*/
(void) setsid();
}
- speedef = get_speed(pmtab->p_ttylabel);
+ speedef = get_speed(pmtab);
openline(pmtab, speedef);
if (pmtab->p_ttyflags & (C_FLAG|B_FLAG)) {
if (pmtab->p_fd >= 0) {
diff --git a/usr/src/cmd/ttymon/tmexpress.c b/usr/src/cmd/ttymon/tmexpress.c
index 345fdd1529..2a3f91d147 100644
--- a/usr/src/cmd/ttymon/tmexpress.c
+++ b/usr/src/cmd/ttymon/tmexpress.c
@@ -34,7 +34,6 @@
#include <ctype.h>
#include <string.h>
#include <signal.h>
-#include <sys/stat.h>
#include <utmpx.h>
#include <pwd.h>
#include <dirent.h>
@@ -42,6 +41,7 @@
#include <sys/acl.h>
#include <sys/stat.h>
#include <sys/types.h>
+#include <sys/mkdev.h>
#include <sys/console.h>
#include <libdevinfo.h>
#include "ttymon.h"
@@ -143,6 +143,44 @@ ttymon_express(int argc, char **argv)
}
/*
+ * For serial device, return ttyX-mode property value.
+ */
+static char *
+get_ttymode_prop(dev_t rconsdev)
+{
+ char *rootpath = "/";
+ char path[MAXPATHLEN];
+ di_node_t root;
+ char *propname, *v;
+ struct stat st;
+
+ (void) snprintf(path, sizeof (path), "/dev/tty%c",
+ 'a' + minor(rconsdev));
+ if (stat(path, &st) < 0)
+ return (NULL);
+
+ if (st.st_rdev != rconsdev)
+ return (NULL);
+
+ if (asprintf(&propname, "%s-mode", path + 5) <= 0)
+ return (NULL);
+
+ root = di_init(rootpath, DINFOPROP);
+ if (root == DI_NODE_NIL) {
+ free(propname);
+ return (NULL);
+ }
+
+ v = NULL;
+ if (di_prop_lookup_strings(DDI_DEV_T_ANY, root, propname, &v) > 0)
+ v = strdup(v);
+
+ di_fini(root);
+ free(propname);
+ return (v);
+}
+
+/*
* parse_arg - parse cmd line arguments
*/
static int
@@ -172,11 +210,13 @@ parse_args(int argc, char **argv, struct pmtab *pmtab)
pmtab->p_termtype = "";
pmtab->p_device = "";
pmtab->p_status = GETTY;
+ pmtab->p_ttymode = NULL;
if (strcmp(lastname(argv[0]), "getty") == 0) {
pmtab->p_ttylabel = "300";
getty_options(argc, argv, pmtab);
} else {
int cn_fd;
+ struct cons_getdev cnd;
pmtab->p_ttylabel = "9600";
ttymon_options(argc, argv, pmtab);
@@ -200,6 +240,10 @@ parse_args(int argc, char **argv, struct pmtab *pmtab)
if (ioctl(cn_fd, CONS_GETTERM, &cnterm) != -1)
pmtab->p_termtype = cnterm.cn_term_type;
+
+ if (ioctl(cn_fd, CONS_GETDEV, &cnd) != -1)
+ pmtab->p_ttymode =
+ get_ttymode_prop(cnd.cnd_rconsdev);
(void) close(cn_fd);
}
}
diff --git a/usr/src/cmd/ttymon/tmextern.h b/usr/src/cmd/ttymon/tmextern.h
index b08c59f04d..955e5773ff 100644
--- a/usr/src/cmd/ttymon/tmextern.h
+++ b/usr/src/cmd/ttymon/tmextern.h
@@ -222,7 +222,7 @@ extern "C" {
extern int Splflag;
/* ttymon.c */
- extern struct Gdef *get_speed(char *);
+ extern struct Gdef *get_speed(struct pmtab *);
extern void open_device(struct pmtab *);
extern void set_softcar(struct pmtab *);
extern void setup_PCpipe(void);
diff --git a/usr/src/cmd/ttymon/tmstruct.h b/usr/src/cmd/ttymon/tmstruct.h
index 288c1ec122..8c4582896a 100644
--- a/usr/src/cmd/ttymon/tmstruct.h
+++ b/usr/src/cmd/ttymon/tmstruct.h
@@ -74,6 +74,7 @@ struct pmtab {
uid_t p_uid; /* uid of p_identity */
gid_t p_gid; /* gid of p_identity */
char *p_dir; /* home dir of p_identity */
+ char *p_ttymode; /* mode line for serial device */
struct pmtab *p_next;
};
diff --git a/usr/src/cmd/ttymon/tmterm.c b/usr/src/cmd/ttymon/tmterm.c
index 96e63af2d3..613cf2597d 100644
--- a/usr/src/cmd/ttymon/tmterm.c
+++ b/usr/src/cmd/ttymon/tmterm.c
@@ -244,7 +244,7 @@ initial_termio(int fd, struct pmtab *pmptr)
int ret;
struct Gdef *speedef;
- speedef = get_speed(pmptr->p_ttylabel);
+ speedef = get_speed(pmptr);
if (speedef->g_autobaud & A_FLAG) {
pmptr->p_ttyflags |= A_FLAG;
if (auto_termio(fd) == -1) {
diff --git a/usr/src/cmd/ttymon/ttymon.c b/usr/src/cmd/ttymon/ttymon.c
index 03ff520059..0c061a9c8c 100644
--- a/usr/src/cmd/ttymon/ttymon.c
+++ b/usr/src/cmd/ttymon/ttymon.c
@@ -26,6 +26,7 @@
/* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */
/* All Rights Reserved */
+#include <ctype.h>
#include <stdio_ext.h>
#include <stdlib.h>
#include <fcntl.h>
@@ -597,25 +598,106 @@ free_defs(void)
}
/*
+ * rebuild flags entry using speed from ttymode.
+ */
+static char *
+merge_flags(char *src, char *ttymode)
+{
+ char *data, *ptr, *flags;
+
+ /* copy speed entry */
+ data = strsave(src);
+ flags = strsave(ttymode);
+ ptr = strchr(flags, ',');
+ if (ptr == NULL) { /* ttymode is corrupted */
+ free(flags);
+ return (data);
+ }
+ *ptr = '\0';
+ ptr = flags;
+ flags = strsave(flags);
+ free(ptr);
+
+ /*
+ * The flags line is supposed to have stty keywords separated by space.
+ * We need to split up the keywords, replace the speed and
+ * reconstruct the flags line.
+ */
+
+ ptr = strtok(data, " \t");
+ if (ptr == NULL) {
+ free(data);
+ return (flags);
+ }
+
+ do {
+ char *tmp;
+
+ /* skip speed */
+ if (isdigit(*ptr))
+ continue;
+
+ if (asprintf(&tmp, "%s %s", flags, ptr) <= 0) {
+ /* should we complain? */
+ break;
+ }
+ free(flags);
+ flags = tmp;
+ } while ((ptr = strtok(NULL, " \t")) != NULL);
+
+ free(data);
+ return (flags);
+}
+
+/*
* struct Gdef *get_speed(ttylabel)
* - search "/etc/ttydefs" for speed and term. specification
* using "ttylabel". If "ttylabel" is NULL, default
* to DEFAULT
+ * - for /dev/console, if we are in fact using serial console,
+ * use ttyX-mode value to get speed. This allows us to use
+ * the value set for serial console either from firmware (or BMC sol),
+ * or boot loader default.
* arg: ttylabel - label/id of speed settings.
*/
struct Gdef *
-get_speed(char *ttylabel)
+get_speed(struct pmtab *pmptr)
{
+ static struct Gdef serial = { 0 };
struct Gdef *sp;
+ char *ttylabel = pmptr->p_ttylabel;
if ((ttylabel != NULL) && (*ttylabel != '\0')) {
if ((sp = find_def(ttylabel)) == NULL) {
log("unable to find <%s> in \"%s\"", ttylabel, TTYDEFS);
sp = &DEFAULT; /* use default */
}
- } else sp = &DEFAULT; /* use default */
- return (sp);
+ } else {
+ sp = &DEFAULT; /* use default */
+ }
+
+ /*
+ * if this is not /dev/console or /dev/console is not using serial,
+ * we are done.
+ */
+ if (pmptr->p_ttymode == NULL ||
+ strcmp(pmptr->p_device, "/dev/console") != 0)
+ return (sp);
+
+ /* is entry for serial set up? */
+ if (serial.g_id == NULL) {
+ /*
+ * Copy data from sp, except we need to update inital and
+ * final flags.
+ */
+ serial.g_id = strsave(sp->g_id);
+ serial.g_iflags = merge_flags(sp->g_iflags, pmptr->p_ttymode);
+ serial.g_fflags = merge_flags(sp->g_fflags, pmptr->p_ttymode);
+ serial.g_autobaud = sp->g_autobaud;
+ serial.g_nextid = strsave(sp->g_nextid);
+ }
+ return (&serial);
}
/*