模拟linux下的ls -l命令
#include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h> #include <errno.h> #include <dirent.h> #include <sys/types.h> #include <sys/stat.h> #include <time.h> #define ERR_EXIT(m) do { perror(m); exit(EXIT_FAILURE); }while(0) const char *statbuf_get_perms(struct stat *sbuf); const char *statbuf_get_date(struct stat *sbuf); const char *statbuf_get_filename(struct stat *sbuf, const char *name); const char *statbuf_get_user_info(struct stat *sbuf); const char *statbuf_get_size(struct stat *sbuf); int main(int argc, const char *argv[]) { DIR *dir = opendir("."); if(dir == NULL) ERR_EXIT("opendir"); struct dirent *dr; while((dr = readdir(dir))) { const char *filename = dr->d_name; if(filename[0] == '.') continue; char buf[1024] = {0}; struct stat sbuf; if(lstat(filename, &sbuf) == -1) ERR_EXIT("lstat"); strcpy(buf, statbuf_get_perms(&sbuf)); strcat(buf, " "); strcat(buf, statbuf_get_user_info(&sbuf)); strcat(buf, " "); strcat(buf, statbuf_get_size(&sbuf)); strcat(buf, " "); strcat(buf, statbuf_get_date(&sbuf)); strcat(buf, " "); strcat(buf, statbuf_get_filename(&sbuf, filename)); printf("%s\n", buf); } closedir(dir); return 0; } const char *statbuf_get_perms(struct stat *sbuf) { static char perms[] = "----------"; mode_t mode = sbuf->st_mode; //文件类型 switch(mode & S_IFMT) { case S_IFSOCK: perms[0] = 's'; break; case S_IFLNK: perms[0] = 'l'; break; case S_IFREG: perms[0] = '-'; break; case S_IFBLK: perms[0] = 'b'; break; case S_IFDIR: perms[0] = 'd'; break; case S_IFCHR: perms[0] = 'c'; break; case S_IFIFO: perms[0] = 'p'; break; } //权限 if(mode & S_IRUSR) perms[1] = 'r'; if(mode & S_IWUSR) perms[2] = 'w'; if(mode & S_IXUSR) perms[3] = 'x'; if(mode & S_IRGRP) perms[4] = 'r'; if(mode & S_IWGRP) perms[5] = 'w'; if(mode & S_IXGRP) perms[6] = 'x'; if(mode & S_IROTH) perms[7] = 'r'; if(mode & S_IWOTH) perms[8] = 'w'; if(mode & S_IXOTH) perms[9] = 'x'; if(mode & S_ISUID) perms[3] = (perms[3] == 'x') ? 's' : 'S'; if(mode & S_ISGID) perms[6] = (perms[6] == 'x') ? 's' : 'S'; if(mode & S_ISVTX) perms[9] = (perms[9] == 'x') ? 't' : 'T'; return perms; } const char *statbuf_get_date(struct stat *sbuf) { static char datebuf[1024] = {0}; struct tm *ptm; time_t ct = sbuf->st_ctime; if((ptm = localtime(&ct)) == NULL) ERR_EXIT("localtime"); const char *format = "%b %e %H:%M"; //时间格式 if(strftime(datebuf, sizeof datebuf, format, ptm) == 0) { fprintf(stderr, "strftime error\n"); exit(EXIT_FAILURE); } return datebuf; } const char *statbuf_get_filename(struct stat *sbuf, const char *name) { static char filename[1024] = {0}; //name 处理链接名字 if(S_ISLNK(sbuf->st_mode)) { char linkfile[1024] = {0}; if(readlink(name, linkfile, sizeof linkfile) == -1) ERR_EXIT("readlink"); snprintf(filename, sizeof filename, " %s -> %s", name, linkfile); }else { strcpy(filename, name); } return filename; } const char *statbuf_get_user_info(struct stat *sbuf) { static char info[1024] = {0}; snprintf(info, sizeof info, " %3d %8d %8d", sbuf->st_nlink, sbuf->st_uid, sbuf->st_gid); return info; } const char *statbuf_get_size(struct stat *sbuf) { static char buf[100] = {0}; snprintf(buf, sizeof buf, "%8lu", (unsigned long)sbuf->st_size); return buf; }
郑重声明:本站内容如果来自互联网及其他传播媒体,其版权均属原媒体及文章作者所有。转载目的在于传递更多信息及用于网络分享,并不代表本站赞同其观点和对其真实性负责,也不构成任何其他建议。