+/*
+ * Given a buffer returned by tgetent(), this routine will turn
+ * the pipe seperated list of names in the buffer into an array
+ * of pointers to null terminated names. We toss out any bad,
+ * duplicate, or verbose names (names with spaces).
+ */
+
+static char *unknown[] = { "UNKNOWN", 0 };
+
+char **
+mklist(buf, name)
+char *buf, *name;
+{
+ register int n;
+ register char c, *cp, **argvp, *cp2, **argv;
+ char *malloc();
+
+ if (name) {
+ if (strlen(name) > 40)
+ name = 0;
+ else {
+ unknown[0] = name;
+ upcase(name);
+ }
+ }
+ /*
+ * Count up the number of names.
+ */
+ for (n = 1, cp = buf; *cp && *cp != ':'; cp++) {
+ if (*cp == '|')
+ n++;
+ }
+ /*
+ * Allocate an array to put the name pointers into
+ */
+ argv = (char **)malloc((n+3)*sizeof(char *));
+ if (argv == 0)
+ return(unknown);
+
+ /*
+ * Fill up the array of pointers to names.
+ */
+ *argv = 0;
+ argvp = argv+1;
+ n = 0;
+ for (cp = cp2 = buf; (c = *cp); cp++) {
+ if (c == '|' || c == ':') {
+ *cp++ = '\0';
+ /*
+ * Skip entries that have spaces or are over 40
+ * characters long. If this is our environment
+ * name, then put it up front. Otherwise, as
+ * long as this is not a duplicate name (case
+ * insensitive) add it to the list.
+ */
+ if (n || (cp - cp2 > 41))
+ ;
+ else if (name && (strncasecmp(name, cp2, cp-cp2) == 0))
+ *argv = cp2;
+ else if (is_unique(cp2, argv+1, argvp))
+ *argvp++ = cp2;
+ if (c == ':')
+ break;
+ /*
+ * Skip multiple delimiters. Reset cp2 to
+ * the beginning of the next name. Reset n,
+ * the flag for names with spaces.
+ */
+ while ((c = *cp) == '|')
+ cp++;
+ cp2 = cp;
+ n = 0;
+ }
+ /*
+ * Skip entries with spaces or non-ascii values.
+ * Convert lower case letters to upper case.
+ */
+ if ((c == ' ') || !isascii(c))
+ n = 1;
+ else if (islower(c))
+ *cp = toupper(c);
+ }
+
+ /*
+ * Check for an old V6 2 character name. If the second
+ * name points to the beginning of the buffer, and is
+ * only 2 characters long, move it to the end of the array.
+ */
+ if ((argv[1] == buf) && (strlen(argv[1]) == 2)) {
+ *argvp++ = buf;
+ cp = *argv++;
+ *argv = cp;
+ }
+
+ /*
+ * Duplicate last name, for TTYPE option, and null
+ * terminate the array. If we didn't find a match on
+ * our terminal name, put that name at the beginning.
+ */
+ cp = *(argvp-1);
+ *argvp++ = cp;
+ *argvp = 0;
+
+ if (*argv == 0) {
+ if (name)
+ *argv = name;
+ else
+ argv++;
+ }
+ if (*argv)
+ return(argv);
+ else
+ return(unknown);
+}
+
+is_unique(name, as, ae)
+register char *name, **as, **ae;
+{
+ register char **ap;
+ register int n;
+
+ n = strlen(name) + 1;
+ for (ap = as; ap < ae; ap++)
+ if (strncasecmp(*ap, name, n) == 0)
+ return(0);
+ return (1);
+}
+
+#ifdef TERMCAP
+char ttytype[1024];
+setupterm(tname, fd, errp)
+char *tname;
+int fd, *errp;
+{
+ if (tgetent(ttytype, tname) == 1) {
+ ttytype[1023] = '\0';
+ if (errp)
+ *errp = 1;
+ return(0);
+ }
+ if (errp)
+ *errp = 0;
+ return(-1);
+}
+#endif
+
+char *
+gettermname()
+{
+ char *tname;
+ static int first = 1;
+ extern char ttytype[];
+ static char **tnamep;
+ static char **next;
+ char *getenv();
+ int err;
+
+ if (first) {
+ first = 0;
+ if ((tname = getenv("TERM")) &&
+ (setupterm(tname, 1, &err) == 0)) {
+ tnamep = mklist(ttytype, tname);
+ } else {
+ if (tname && (strlen(tname) <= 40)) {
+ unknown[0] = tname;
+ upcase(tname);
+ }
+ tnamep = unknown;
+ }
+ next = tnamep;
+ }
+ if (*next == 0)
+ next = tnamep;
+ return(*next++);
+}