Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/usr.bin/who add utmpx support; lots of code can be shared no...



details:   https://anonhg.NetBSD.org/src/rev/b097efb9ec90
branches:  trunk
changeset: 534511:b097efb9ec90
user:      christos <christos%NetBSD.org@localhost>
date:      Sun Jul 28 21:46:34 2002 +0000

description:
add utmpx support; lots of code can be shared now with w.

diffstat:

 usr.bin/who/Makefile |    3 +-
 usr.bin/who/who.c    |  327 ++++++++++++++++++++++++++++++++++++++------------
 2 files changed, 249 insertions(+), 81 deletions(-)

diffs (truncated from 456 to 300 lines):

diff -r 9f4cd52521b4 -r b097efb9ec90 usr.bin/who/Makefile
--- a/usr.bin/who/Makefile      Sun Jul 28 21:45:39 2002 +0000
+++ b/usr.bin/who/Makefile      Sun Jul 28 21:46:34 2002 +0000
@@ -1,6 +1,7 @@
-#      $NetBSD: Makefile,v 1.5 1997/10/20 03:20:27 lukem Exp $
+#      $NetBSD: Makefile,v 1.6 2002/07/28 21:46:34 christos Exp $
 #      @(#)Makefile    8.1 (Berkeley) 6/6/93
 
 PROG=  who
+CPPFLAGS+=     -DSUPPORT_UTMPX -DSUPPORT_UTMP
 
 .include <bsd.prog.mk>
diff -r 9f4cd52521b4 -r b097efb9ec90 usr.bin/who/who.c
--- a/usr.bin/who/who.c Sun Jul 28 21:45:39 2002 +0000
+++ b/usr.bin/who/who.c Sun Jul 28 21:46:34 2002 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: who.c,v 1.8 1999/07/17 16:41:44 christos Exp $ */
+/*     $NetBSD: who.c,v 1.9 2002/07/28 21:46:34 christos Exp $ */
 
 /*
  * Copyright (c) 1989, 1993
@@ -47,7 +47,7 @@
 #if 0
 static char sccsid[] = "@(#)who.c      8.1 (Berkeley) 6/6/93";
 #endif
-__RCSID("$NetBSD: who.c,v 1.8 1999/07/17 16:41:44 christos Exp $");
+__RCSID("$NetBSD: who.c,v 1.9 2002/07/28 21:46:34 christos Exp $");
 #endif /* not lint */
 
 #include <sys/types.h>
@@ -60,26 +60,47 @@
 #include <string.h>
 #include <time.h>
 #include <unistd.h>
+#ifdef SUPPORT_UTMP
 #include <utmp.h>
+#endif
+#ifdef SUPPORT_UTMPX
+#include <utmpx.h>
+#endif
+
+struct entry {
+       char name[65];
+       char line[65];
+       char host[257];
+       time_t time;
+       struct entry *next;
+};
 
-void output __P((struct utmp *));
-void output_labels __P((void));
-void who_am_i __P((FILE *));
-FILE *file __P((char *));
-void usage __P((void));
+static void output_labels(void);
+static void who_am_i(const char *, int);
+static void usage(void);
+static void process(const char *, int);
+#ifdef SUPPORT_UTMP
+static void getentry(struct entry *, struct utmp *);
+#endif
+#ifdef SUPPORT_UTMPX
+static void getentryx(struct entry *, struct utmpx *);
+#endif
+#if defined(SUPPORT_UTMPX) && defined(SUPPORT_UTMP)
+static int setup(const char *);
+static void adjust_size(struct entry *e);
+#endif
+static void print(const char *, const char *, time_t, const char *);
 
-int show_term;                 /* show term state */
-int show_idle;                 /* show idle time */
+int main(int, char **);
 
-int main __P((int, char **));
+static int show_term;                  /* show term state */
+static int show_idle;                  /* show idle time */
+
+static int maxname = 8, maxline = 8, maxhost = 16;
 
 int
-main(argc, argv)
-       int argc;
-       char **argv;
+main(int argc, char **argv)
 {
-       struct utmp usr;
-       FILE *ufp;
        int c, only_current_term, show_labels;
 
        setlocale(LC_ALL, "");
@@ -112,36 +133,23 @@
                /* NOTREACHED */
        }
 
-       if (show_labels)
-               output_labels();
-
        switch (argc) {
        case 0:                                 /* who */
-               ufp = file(_PATH_UTMP);
-
                if (only_current_term) {
-                       who_am_i(ufp);
+                       who_am_i(NULL, show_labels);
                } else {
-                       /* only entries with both name and line fields */
-                       while (fread((char *)&usr, sizeof(usr), 1, ufp) == 1)
-                               if (*usr.ut_name && *usr.ut_line)
-                                       output(&usr);
+                       process(NULL, show_labels);
                }
                break;
        case 1:                                 /* who utmp_file */
-               ufp = file(*argv);
-
                if (only_current_term) {
-                       who_am_i(ufp);
+                       who_am_i(*argv, show_labels);
                } else {
-                       /* all entries */
-                       while (fread((char *)&usr, sizeof(usr), 1, ufp) == 1)
-                               output(&usr);
+                       process(*argv, show_labels);
                }
                break;
        case 2:                                 /* who am i */
-               ufp = file(_PATH_UTMP);
-               who_am_i(ufp);
+               who_am_i(NULL, show_labels);
                break;
        default:
                usage();
@@ -150,44 +158,218 @@
        exit(0);
 }
 
-void
-who_am_i(ufp)
-       FILE *ufp;
+#if defined(SUPPORT_UTMPX) && defined(SUPPORT_UTMP)
+static void
+adjust_size(struct entry *e)
+{
+       int max;
+
+       if ((max = strlen(e->name)) > maxname)
+               maxname = max;
+       if ((max = strlen(e->line)) > maxline)
+               maxline = max;
+       if ((max = strlen(e->host)) > maxhost)
+               maxhost = max;
+}
+
+static int
+setup(const char *fname)
 {
-       struct utmp usr;
+       int what = 3;
+
+       if (fname == NULL) {
+#ifdef SUPPORT_UTMPX
+               setutent();
+#endif
+#ifdef SUPPORT_UTMP
+               setutxent();
+#endif
+       } else {
+               size_t len = strlen(fname);
+               if (len == 0)
+                       errx(1, "Filename cannot be 0 length.");
+               what = fname[len - 1] == 'x' ? 1 : 2;
+               if (what == 1) {
+#ifdef SUPPORT_UTMPX
+                       if (utmpxname(fname) == 0)
+                               err(1, "Cannot open `%s'", fname);
+#else
+                       errx(1, "utmpx support not compiled in");
+#endif
+               } else {
+#ifdef SUPPORT_UTMPX
+                       if (utmpname(fname) == 0)
+                               err(1, "Cannot open `%s'", fname);
+#else
+                       errx(1, "utmp support not compiled in");
+#endif
+               }
+       }
+       return what;
+}
+#endif
+
+static void
+who_am_i(const char *fname, int show_labels)
+{
+#ifdef SUPPORT_UTMPX
+       struct utmpx *utx;
+#endif
+#ifdef SUPPORT_UTMP
+       struct utmp *ut;
+#endif
        struct passwd *pw;
        char *p;
        char *t;
+       time_t now;
+#if defined(SUPPORT_UTMP) && defined(SUPPORT_UTMPX)
+       int what = setup(fname);
+#endif
 
        /* search through the utmp and find an entry for this tty */
-       if ((p = ttyname(0)) != NULL) {
+       if ((p = ttyname(STDIN_FILENO)) != NULL) {
+
                /* strip any directory component */
                if ((t = strrchr(p, '/')) != NULL)
                        p = t + 1;
-               while (fread((char *)&usr, sizeof(usr), 1, ufp) == 1)
-                       if (usr.ut_name[0] != '\0' &&
-                           !strcmp(usr.ut_line, p)) {
-                               output(&usr);
+#ifdef SUPPORT_UTMPX
+               while ((what & 1) && (utx = getutxent()) != NULL)
+                       if (utx->ut_type == USER_PROCESS &&
+                           !strcmp(utx->ut_line, p)) {
+                               struct entry e;
+                               getentryx(&e, utx);
+                               if (show_labels)
+                                       output_labels();
+                               print(e.name, e.line, e.time, e.host);
+                               return;
+                       }
+#endif
+#ifdef SUPPORT_UTMP
+               while ((what & 2) && (ut = getutent()) != NULL)
+                       if (!strcmp(ut->ut_line, p)) {
+                               struct entry e;
+                               getentry(&e, ut);
+                               if (show_labels)
+                                       output_labels();
+                               print(e.name, e.line, e.time, e.host);
                                return;
                        }
-               /* well, at least we know what the tty is */
-               (void)strncpy(usr.ut_line, p, UT_LINESIZE);
+#endif
        } else
-               (void)strcpy(usr.ut_line, "tty??");
+               p = "tty??";
 
+       (void)time(&now);
        pw = getpwuid(getuid());
-       (void)strncpy(usr.ut_name, pw ? pw->pw_name : "?", UT_NAMESIZE);
-       (void)time(&usr.ut_time);
-       *usr.ut_host = '\0';
-       output(&usr);
+       if (show_labels)
+               output_labels();
+       print(pw ? pw->pw_name : "?", p, now, "");
 }
 
-void
-output(up)
-       struct utmp *up;
+static void
+process(const char *fname, int show_labels)
+{
+#ifdef SUPPORT_UTMPX
+       struct utmpx *utx;
+#endif
+#ifdef SUPPORT_UTMP
+       struct utmp *ut;
+#endif
+       struct entry *ep, *ehead = NULL;
+#if defined(SUPPORT_UTMP) && defined(SUPPORT_UTMPX)
+       int what = setup(fname);
+       struct entry **nextp = &ehead;
+#endif
+
+#ifdef SUPPORT_UTMPX
+       while ((what & 1) && (utx = getutxent()) != NULL) {
+               if (fname == NULL && utx->ut_type != USER_PROCESS)
+                       continue;
+               if ((ep = calloc(1, sizeof(struct entry))) == NULL)
+                       err(1, NULL);
+               getentryx(ep, utx);
+               *nextp = ep;
+               nextp = &(ep->next);
+       }
+#endif
+
+#ifdef SUPPORT_UTMP
+       while ((what & 2) && (ut = getutent()) != NULL) {
+               if (fname == NULL && (*ut->ut_name == '\0' ||
+                   *ut->ut_line == '\0'))
+                       continue;
+               /* Don't process entries that we have utmpx for */
+               for (ep = ehead; ep != NULL; ep = ep->next) {
+                       if (strncmp(ep->line, ut->ut_line,
+                           sizeof(ut->ut_line)) == 0)
+                               break;



Home | Main Index | Thread Index | Old Index