home *** CD-ROM | disk | FTP | other *** search
- From: tchrist@convex.COM (Tom Christiansen)
- Newsgroups: comp.unix.questions,alt.sources
- Subject: Re: When does wtmp reset?
- Message-ID: <1991May21.231242.6970@convex.com>
- Date: 21 May 91 23:12:42 GMT
-
- From the keyboard of tpm-sprl!tpm@uunet.uu.net (Terence P. Ma):
- :I know that the last login date is in /var/adm/lastlog. Is there an easy
- :way to get the lastlogin date and time of all users or groups of users
- :without using "finger -s user1 user2 ..." to get at it?
-
- Here's a C program to do that. Perl version (runs 3x slower; sigh)
- available upon request.
-
- --tom
-
- /*
- * lastlog - print last login time for all users, based on times
- * stored in /usr/adm/lastlog.
- *
- * Lines are printed oldest first, with name, date/time, and gecos
- * field on each line.
- *
- * No command line options. Runs on VAX/4.2 BSD Unix.
- *
- * compile with: cc -O -o lastlog lastlog.c
- *
- * Rex Sanders, US Geological Survey, Pacific Marine Geology, 12/19/85
- */
-
- #include <stdio.h>
- #include <strings.h>
- #include <sys/file.h>
- #include <sys/types.h>
- #include <lastlog.h>
- #include <pwd.h>
- #include <sysexits.h>
-
- /* maximum number of users/entries in /etc/passwd */
- #define MAXU 5000
- /* maximum length of the gecos field in /etc/passwd */
- #define MAXG 100
-
- char *ctime ();
- long lseek ();
-
- struct info_s {
- int time;
- char name[9];
- char gecos[MAXG];
- };
- struct info_s info[MAXU];
-
- main (argc, argv) char **argv; {
- int infocmp ();
- struct lastlog ll;
- struct passwd *pw;
- char lastdate[25];
- int llfd;
- register int nusers = 0;
- register int i;
-
- if ((llfd = open ("/usr/adm/lastlog", O_RDONLY)) < 0) {
- perror ("lastlog: /usr/adm/lastlog");
- exit (EX_OSFILE);
- }
-
- /*
- * For each user in password file, grab password info
- */
- while (pw = getpwent ()) {
- /*
- * Grab info from lastlog file
- */
- if (!strcmp(pw->pw_passwd,"*"))
- continue;
- if (lseek (llfd, (long) pw -> pw_uid * sizeof ll, 0) == -1) {
- fprintf(stderr,"%s: lseek for uid %d failed\n", *argv, pw->pw_uid);
- continue;
- }
- if (read (llfd, (char *) & ll, sizeof ll) != sizeof ll) {
- fprintf(stderr, "%s: read for uid %d failed\n", *argv, pw->pw_uid);
- continue;
- }
-
-
- info[nusers].time = ll.ll_time;
- strncpy (info[nusers].name, pw -> pw_name, 9);
- strncpy (info[nusers].gecos, pw -> pw_gecos, MAXG);
- if (nusers++ == MAXU) {
- fprintf(stderr, "%s: recompile with MAXU > %d\n",
- *argv, MAXU);
- exit(EX_SOFTWARE);
- }
- }
-
- /*
- * Sort users by last login time
- */
- qsort ((char *) info, nusers, sizeof (struct info_s), infocmp);
-
- /*
- * Print info for each user
- */
- for (i = 0; i < nusers; i++) {
- if (info[i].time) {
- strncpy (lastdate, ctime (&info[i].time), 24);
- lastdate[24] = '\0';
- }
- else
- strcpy (lastdate, "never logged in");
-
- printf ("%-8s %-24s %s\n", info[i].name, lastdate,
- info[i].gecos);
- }
-
- close (llfd);
- endpwent ();
- }
-
- /*
- * infocmp - compare 2 info entries for qsort
- */
-
- infocmp (info1, info2)
- struct info_s *info1,
- *info2;
- {
- register int r;
-
- if (info1 -> time == info2 -> time)
- r = 0;
- else
- r = (info1 -> time > info2 -> time) ? 1 : -1;
-
- return (r);
- }
- --
- Tom Christiansen tchrist@convex.com convex!tchrist
- "So much mail, so little time."
-