[cpp] #include <stdio.h>
#include <stdlib.h>
#include <utmp.h>
#include <fcntl.h>
#include <unistd.h>
#include <time.h>
void show_info(struct utmp *);
void showtime(long);
int main()
{
int fd;
struct utmp current_record;
int reclen = sizeof(struct utmp);
/* UTMP_FILE就是/var/run/utmp.在/usr/include/paths.h下 */
fd = open(UTMP_FILE, O_RDONLY);
if (fd == -1)
{
perror(UTMP_FILE);
exit(1);
}
while (read(fd, ¤t_record, reclen))
show_info(¤t_record);
close(fd);
return 0;
}
/* displays the contents of the utmp struct, display nothing if utmp has no user name */
void show_info(struct utmp *utbufp)
{
if (utbufp->ut_type != USER_PROCESS)
return;
printf("%-8.8s", utbufp->ut_user); /* The user name */
printf(" ");
printf("%-8.8s", utbufp->ut_line); /* The tty name */
printf(" ");
showtime(utbufp->ut_time); /* utime */
#ifdef SHOWHOST
if (utbufp->ut_host[0] != '\0')
printf(" (%s)", utbufp->ut_host); /* the host */
#endif
printf("\n");
}
/* displays time in a format */
void showtime(long timeval)
{
char *cp;
cp = ctime(&timeval); /* convert time to string */
printf("%20.20s", cp+4); /* %12.12s prints a string 20 chars wide and LIMITS it to 20 chars. cp+4是為了把最前面的星期去掉 */
}
#include <stdio.h>
#include <stdlib.h>
#include <utmp.h>
#include <fcntl.h>
#include <unistd.h>
#include <time.h>
void show_info(struct utmp *);
void showtime(long);
int main()
{
int fd;
struct utmp current_record;
int reclen = sizeof(struct utmp);
/* UTMP_FILE就是/var/run/utmp.在/usr/include/paths.h下 */
fd = open(UTMP_FILE, O_RDONLY);
if (fd == -1)
{
perror(UTMP_FILE);
exit(1);
}
while (read(fd, ¤t_record, reclen))
show_info(¤t_record);
close(fd);
return 0;
}
/* displays the contents of the utmp struct, display nothing if utmp has no user name */
void show_info(struct utmp *utbufp)
{
if (utbufp->ut_type != USER_PROCESS)
return;
printf("%-8.8s", utbufp->ut_user); /* The user name */
printf(" ");
printf("%-8.8s", utbufp->ut_line); /* The tty name */
printf(" ");
showtime(utbufp->ut_time); /* utime */
#ifdef SHOWHOST
if (utbufp->ut_host[0] != '\0')
printf(" (%s)", utbufp->ut_host); /* the host */
#endif
printf("\n");
}
/* displays time in a format */
void showtime(long timeval)
{
char *cp;
cp = ctime(&timeval); /* convert time to string */
printf("%20.20s", cp+4); /* %12.12s prints a string 20 chars wide and LIMITS it to 20 chars. cp+4是為了把最前面的星期去掉 */
}
增加了緩沖機制的who命令實現:這樣會減少read()函數調用的次數,提高程序效率和性能。
主函數為:who1.c
[cpp] #include <stdio.h>
#include <stdlib.h>
#include <utmp.h>
#include <fcntl.h>
#include <unistd.h>
#include <time.h>
#include </root/utmplib.c> /* 包含實現緩沖的文件 */
void show_info(struct utmp *);
void showtime(long);
int main()
{
int fd;
struct utmp *utbufp;
int reclen = sizeof(struct utmp);
/* UTMP_FILE就是/var/run/utmp.在/usr/include/paths.h下 */
if (utmp_open(UTMP_FILE) == -1)
{
perror(UTMP_FILE);
exit(1);
}
while((utbufp = utmp_next()) != ((struct utmp *)NULL))
show_info(utbufp);
utmp_close();
return 0;
}
/* displays the contents of the utmp struct, display nothing if utmp has no user name */
void show_info(struct utmp *utbufp)
{
if (utbufp->ut_type != USER_PROCESS)
return;
printf("%-8.8s", utbufp->ut_user); /* The user name */
printf(" ");
printf("%-8.8s", utbufp->ut_line); /* The tty name */
printf(" ");
showtime(utbufp->ut_time); /* utime */
#ifdef SHOWHOST
if (utbufp->ut_host[0] != '\0')
printf(" (%s)", utbufp->ut_host); /* the host */
#endif
printf("\n");
}
/* displays time in a format */
void showtime(long timeval)
{
char *cp;
cp = ctime(&timeval); /* convert time to string */
printf("%20.20s", cp+4); /* %12.12s prints a string 20 chars wide and LIMITS it to 20 chars. cp+4是為了把最前面的星期去掉 */
}
#include <stdio.h>
#include <stdlib.h>
#include <utmp.h>
#include <fcntl.h>
#include <unistd.h>
#include <time.h>
#include </root/utmplib.c> /* 包含實現緩沖的文件 */
void show_info(struct utmp *);
void showtime(long);
int main()
{
int fd;
struct utmp *utbufp;
int reclen = sizeof(struct utmp);
/* UTMP_FILE就是/var/run/utmp.在/usr/include/paths.h下 */
if (utmp_open(UTMP_FILE) == -1)
{
perror(UTMP_FILE);
exit(1);
}
while((utbufp = utmp_next()) != ((struct utmp *)NULL))
show_info(utbufp);
utmp_close();
return 0;
}
/* displays the contents of the utmp struct, display nothing if utmp has no user name */
void show_info(struct utmp *utbufp)
{
if (utbufp->ut_type != USER_PROCESS)
return;
printf("%-8.8s", utbufp->ut_user); /* The user name */
printf(" ");
printf("%-8.8s", utbufp->ut_line); /* The tty name */
printf(" ");
showtime(utbufp->ut_time); /* utime */
#ifdef SHOWHOST
if (utbufp->ut_host[0] != '\0')
printf(" (%s)", utbufp->ut_host); /* the host */
#endif
printf("\n");
}
/* displays time in a format */
void showtime(long timeval)
{
char *cp;
cp = ctime(&timeval); /* convert time to string */
printf("%20.20s", cp+4); /* %12.12s prints a string 20 chars wide and LIMITS it to 20 chars. cp+4是為了把最前面的星期去掉 */
}實現緩沖的文件:utmplib.c
[cpp] #include <stdio.h>
#include <fcntl.h>
#include <sys/types.h>
#include <utmp.h>
#define NRECS 16
#define NULLUT ((struct utmp *)NULL)
#define UTSIZE ((sizeof(struct utmp)))
static char utmpbuf[NRECS * UTSIZE]; /* storage */
static int num_recs; /* num stored */
static int cur_rec; /* next to go */
static int fd_utmp = -1; /* read from */
utmp_open(char *filename)
{
fd_utmp = open(filename, O_RDONLY);
cur_rec = num_recs = 0;
return fd_utmp;
}
struct utmp *utmp_next()
{
struct utmp *recp;
if (fd_utmp == -1)
return NULLUT;
if (cur_rec == num_recs && utmp_reload() == 0)
return NULLUT;
recp = (struct utmp *)&utmpbuf[cur_rec * UTSIZE]; /* 依次獲取下一個記錄的地址 */
cur_rec++;
return recp;
}
int utmp_reload()
{
int amt_read;
/* 不是第一次讀時都是從上次讀到的位置繼續讀 */
amt_read = read(fd_utmp, utmpbuf, NRECS * UTSIZE);
num_recs = amt_read/UTSIZE; /* 讀到的真實個數 */
cur_rec = 0; /* 重置為0 */
return num_recs;
}
utmp_close()
{
if (fd_utmp != -1) /* 只有在打開之後才關閉 */
close(fd_utmp);
}
#include <stdio.h>
#include <fcntl.h>
#include <sys/types.h>
#include <utmp.h>
#define NRECS 16
#define NULLUT ((struct utmp *)NULL)
#define UTSIZE ((sizeof(struct utmp)))
static char utmpbuf[NRECS * UTSIZE]; /* storage */
static int num_recs; /* num stored */
static int cur_rec; /* next to go */
static int fd_utmp = -1; /* read from */
utmp_open(char *filename)
{
fd_utmp = open(filename, O_RDONLY);
cur_rec = num_recs = 0;
return fd_utmp;
}
struct utmp *utmp_next()
{
struct utmp *recp;
if (fd_utmp == -1)
return NULLUT;
if (cur_rec == num_recs && utmp_reload() == 0)
return NULLUT;
recp = (struct utmp *)&utmpbuf[cur_rec * UTSIZE]; /* 依次獲取下一個記錄的地址 */
cur_rec++;
return recp;
}
int utmp_reload()
{
int amt_read;
/* 不是第一次讀時都是從上次讀到的位置繼續讀 */
amt_read = read(fd_utmp, utmpbuf, NRECS * UTSIZE);
num_recs = amt_read/UTSIZE; /* 讀到的真實個數 */
cur_rec = 0; /* 重置為0 */
return num_recs;
}
utmp_close()
{
if (fd_utmp != -1) /* 只有在打開之後才關閉 */
close(fd_utmp);
}