unix/linux程式設計實踐教程:who命令
阿新 • • 發佈:2019-01-10
1. who命令的編寫
1) 通過man命令的幫助,找到who命令的儲存檔案
man who
2) 在man who的幫助下,找到utmp這個資訊
man -k utmp
3) 看man -k utmp的輸出,找到以下這條資訊:
utmp (5) - login records
4) 然後通過指令:
man 5 utmp
裡面就有我們需要的一切資訊了。
程式碼如下:
#include <stdio.h> #include <utmp.h> #include <fcntl.h> #include <unistd.h> #include <time.h> void showtime( long ); void show_info( struct utmp * utbufp ); int main() { struct utmp current_record; int utmpfd; int reclen = sizeof( current_record ); if ( ( utmpfd = open( UTMP_FILE, O_RDONLY ) ) == -1 ){ perror( UTMP_FILE ); exit( 1 ); } while ( read( utmpfd, ¤t_record, reclen ) == reclen ) show_info( ¤t_record ); close( utmpfd ); return 0; } void show_info( struct utmp *utbufp ) { if ( utbufp->ut_type != USER_PROCESS ) return; printf("%-8.8s ", utbufp->ut_name ); printf("%-8.8s ", utbufp->ut_line ); showtime( utbufp->ut_time ); #ifdef SHOWHOST if ( utbufp->ut_host[ 0 ] != '\0' ) printf("(%s)", utbufp->ut_host); #endif printf("\n"); } void showtime( long timeval ) { char *cp; cp = ctime( &timeval ); printf("%12.12s", cp + 4 ); }
程式輸出:
[email protected]:~$ ./a.out
leichaoj :0 Aug 25 21:39
leichaoj pts/0 Aug 25 21:43
2. who原始碼的學習
核心程式碼用到了快取的技術(即一次讀取多個使用者,然後輸出):
static void who (const char *filename, int options) { size_t n_users; STRUCT_UTMP *utmp_buf; if (read_utmp (filename, &n_users, &utmp_buf, options) != 0) error (EXIT_FAILURE, errno, "%s", filename); if (short_list) list_entries_who (n_users, utmp_buf); else scan_entries (n_users, utmp_buf); free (utmp_buf); }
static void list_entries_who (size_t n, const STRUCT_UTMP *utmp_buf) { unsigned long int entries = 0; char const *separator = ""; while (n--) { if (IS_USER_PROCESS (utmp_buf)) { char *trimmed_name; trimmed_name = extract_trimmed_name (utmp_buf); printf ("%s%s", separator, trimmed_name); free (trimmed_name); separator = " "; entries++; } utmp_buf++; } printf (_("\n# users=%lu\n"), entries); }
3. 編寫終端登出程式碼
將登入記錄從UTMP檔案中刪除即可。
#include <stdio.h>
#include <utmp.h>
#include <unistd.h>
#include <fcntl.h>
int logout_tty( char *line );
int main( int argc, char **argv )
{
if ( 2 != argc ){
printf("please enter the logout name\n");
return -1;
}
if ( logout_tty( argv[ 1 ] ) == 0 )
printf("success\n");
else{
printf("fail\n");
}
return 0;
}
int logout_tty( char *line )
{
int fd;
struct utmp rec;
int len = sizeof( struct utmp );
int retval = -1;
if ( ( fd = open( UTMP_FILE, O_RDWR ) ) == -1 )
return -1;
while ( read( fd, &rec, len ) == len )
if ( strncmp( rec.ut_line, line, sizeof( rec.ut_line ) ) == 0 ){
rec.ut_type = DEAD_PROCESS;
if ( time( &rec.ut_time ) != -1 )
if ( lseek( fd, -len, SEEK_CUR ) != -1 )
if ( write( fd, &rec, len ) == len )
return 0;
break;
}
if ( close( fd ) == -1 )
retval = -1;
return retval;
}
切換到管理員許可權進行執行:
[email protected]:/home/leichaojian# who
leichaojian :0 2014-08-25 21:39 (:0)
leichaojian pts/0 2014-08-25 21:43 (:0)
[email protected]:/home/leichaojian# ./a.out :0
success
[email protected]:/home/leichaojian# who
leichaojian pts/0 2014-08-25 21:43 (:0)
4. whoami的編寫
1)
#include<stdio.h>
#include<unistd.h>
int main()
{
printf("%s\n", getlogin() );
return 0;
}
2)
#include<stdio.h>
#include<unistd.h>
#include <pwd.h>
#include <sys/types.h>
int main()
{
struct passwd *p;
p = getpwuid( geteuid() );
printf("%s\n", p->pw_name );
return 0;
}
5. cp命令的編寫
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#define MAXLINE 4096
int main( int argc, char **argv )
{
int n;
int fd1;
int fd2;
char buf[ MAXLINE ];
if ( argc != 3 ){
printf("argument should be 3\n");
return -1;
}
if ( strcmp( argv[ 1 ], argv[ 2 ] ) == 0 ){
printf("same file\n");
return -1;
}
if ( ( fd1 = open( argv[ 1 ], O_RDONLY ) ) == -1 ){
printf("open file error\n");
return -1;
}
if ( ( fd2 = open( argv[ 2 ], O_WRONLY | O_CREAT | O_TRUNC ) ) == -1 ){
printf("create file error\n");
return -1;
}
while ( ( n = read( fd1, buf, MAXLINE ) ) > 0 ){
if ( write( fd2, buf, n ) != n ){
printf("write error\n");
return -1;
}
}
if (n == -1 ){
printf("read error\n");
return -1;
}
if ( close( fd1 ) == -1 || close( fd2 ) == -1 ){
printf("error close\n");
return -1;
}
return 0;
}
程式輸出:
[email protected]:~$ cc cp.c
[email protected]:~$ ./a.out cp.c cp.c
same file
[email protected]:~$ ./a.out cp.c foo
[email protected]:~$ chmod 777 foo
有三條命令不知道如何進行編寫:ac,last,od