功能:获取文件元数据
- #include <sys/types.h>
- #include <sys/stat.h>
- #include <unistd.h>
- int stat(const char *path, struct stat *buf);
- int fstat(int fd, struct stat *buf);
- int lstat(const char *path, struct stat *buf);
stat结构体
- struct stat
- {
- dev_t st_dev; /* ID of device containing file */
- ino_t st_ino; /* inode number */
- mode_t st_mode; /* protection */
- nlink_t st_nlink; /* number of hard links */
- uid_t st_uid; /* user ID of owner */
- gid_t st_gid; /* group ID of owner */
- dev_t st_rdev; /* device ID (if special file) */
- off_t st_size; /* total size, in bytes */
- blksize_t st_blksize; /* blocksize for filesystem I/O */
- blkcnt_t st_blocks; /* number of 512B blocks allocated */
- time_t st_atime; /* time of last access */
- time_t st_mtime; /* time of last modification */
- time_t st_ctime; /* time of last status change */
- };
- //示例 - err_exit函数如前
- // 其实可以通过Linux 系统调用major, minor来替换(如下)
- #define MAJOR(a) (int)((unsigned short)a >> 8) //主设备号: 获取高8位
- #define MINOR(a) (int)((unsigned short)a & 0xFF)//次设备号: 获取低8位
- bool fileType(const struct stat &fileStat);
- void filePerm(const struct stat &fileStat, char *perm);
- int main(int argc, char *argv[])
- {
- if (argc != 2)
- {
- cerr << "Usage: " << argv[0] << " <file-name>" << endl;
- exit(EXIT_FAILURE);
- }
- struct stat fileStat;
- if (lstat(argv[1], &fileStat) == -1)
- err_exit("stat error");
- cout << "file-name: " << argv[1] << endl;
- cout << "st_ino = " << fileStat.st_ino << endl;
- cout << "device major: " << major(fileStat.st_dev)
- << ", minor: " << minor(fileStat.st_dev) << endl;
- if (fileType(fileStat))
- {
- cout << "----------------------------" << endl;
- cout << "major: " << MAJOR(fileStat.st_dev)
- << ", minor: " << MINOR(fileStat.st_rdev) << endl;
- // cout << "major: " << major(fileStat.st_dev)
- // << ", minor: " << minor(fileStat.st_rdev) << endl;
- }
- //获取文件的权限: 但要注意需要&上07777
- fprintf(stdout, "file permission: %o", fileStat.st_mode&07777);
- char perm[11];
- filePerm(fileStat, perm);
- cout << ", msg: " << perm << endl;
- cout << "st_nlink = " << fileStat.st_nlink << endl;
- cout << "st_uid = " << fileStat.st_uid << endl;
- cout << "st_gid = " << fileStat.st_gid << endl;
- cout << "st_size = " << fileStat.st_size << endl;
- cout << "st_blksize = " << fileStat.st_blksize << endl;
- cout << "st_blocks = " << fileStat.st_blocks << endl;
- cout << "st_atime = " << fileStat.st_atime << endl;
- cout << "st_ctime = " << fileStat.st_ctime << endl;
- cout << "st_mtime = " << fileStat.st_mtime << endl;
- }
- bool fileType(const struct stat &fileStat)
- {
- cout << "file-type: ";
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFSOCK:
- cout << "socket";
- break;
- case S_IFLNK:
- cout << "symbolic link";
- break;
- case S_IFREG:
- cout << "regular file";
- break;
- case S_IFBLK:
- cout << "block device" << endl;
- return true;
- break;
- case S_IFDIR:
- cout << "directory";
- break;
- case S_IFCHR:
- cout << "character device" << endl;
- return true;
- break;
- case S_IFIFO:
- cout << "FIFO" << endl;
- break;
- default:
- cout << "unknown?";
- break;
- }
- cout << endl;
- return false;
- }
- void filePerm(const struct stat &fileStat, char *perm)
- {
- strcpy(perm, "----------");
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFSOCK:
- perm[0] = 's';
- break;
- case S_IFLNK:
- perm[0] = 'l';
- break;
- case S_IFREG:
- perm[0] = '-';
- break;
- case S_IFBLK:
- perm[0] = 'b';
- break;
- case S_IFDIR:
- perm[0] = 'd';
- break;
- case S_IFCHR:
- perm[0] = 'c';
- break;
- case S_IFIFO:
- perm[0] = 'p';
- break;
- default:
- perm[0] = '?';
- break;
- }
- if (fileStat.st_mode & S_IRUSR)
- perm[1] = 'r';
- if (fileStat.st_mode & S_IWUSR)
- perm[2] = 'w';
- if (fileStat.st_mode & S_IXUSR)
- perm[3] = 'x';
- if (fileStat.st_mode & S_IRGRP)
- perm[4] = 'r';
- if (fileStat.st_mode & S_IWGRP)
- perm[5] = 'w';
- if (fileStat.st_mode & S_IXGRP)
- perm[6] = 'x';
- if (fileStat.st_mode & S_IROTH)
- perm[7] = 'r';
- if (fileStat.st_mode & S_IWOTH)
- perm[8] = 'w';
- if (fileStat.st_mode & S_IXOTH)
- perm[9] = 'x';
- }
实现ls -l的功能:
【拓展函数】
1.getpwuid
- struct passwd *getpwuid(uid_t uid);
- //passwd结构体
- struct passwd
- {
- char *pw_name; /* username */
- char *pw_passwd; /* user password */
- uid_t pw_uid; /* user ID */
- gid_t pw_gid; /* group ID */
- char *pw_gecos; /* user information */
- char *pw_dir; /* home directory */
- char *pw_shell; /* shell program */
- };
2.getgrgid
- struct group *getgrgid(gid_t gid);
- //group结构体
- struct group
- {
- char *gr_name; /* group name */
- char *gr_passwd; /* group password */
- gid_t gr_gid; /* group ID */
- char **gr_mem; /* group members */
- };
3. readlink
- ssize_t readlink(const char *path, char *buf, size_t bufsiz);
4. localtime
- struct tm *localtime(const time_t *timep);
- //tm结构体
- struct tm
- {
- int tm_sec; /* seconds */
- int tm_min; /* minutes */
- int tm_hour; /* hours */
- int tm_mday; /* day of the month */
- int tm_mon; /* month */
- int tm_year; /* year */
- int tm_wday; /* day of the week */
- int tm_yday; /* day in the year */
- int tm_isdst; /* daylight saving time */
- };
- //示例: 实现简单的ls -l功能
- #include <iostream>
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <string.h>
- #include <sys/types.h>
- #include <sys/stat.h>
- #include <fcntl.h>
- #include <unistd.h>
- #include <grp.h>
- #include <pwd.h>
- #include <time.h>
- using namespace std;
- inline void err_exit(std::string message);
- bool isDevice(const struct stat &fileStat);
- bool isLink(const struct stat &fileStat);
- void filePerm(const struct stat &fileStat, char *perm);
- int main(int argc, char *argv[])
- {
- if (argc != 2)
- {
- cerr << "Usage: " << argv[0] << " <file-name>" << endl;
- exit(EXIT_FAILURE);
- }
- struct stat fileStat;
- if (lstat(argv[1], &fileStat) == -1)
- err_exit("lstat error");
- //获取权限
- char perm[11];
- filePerm(fileStat, perm);
- cout << perm << ' ';
- //获取文件链接数
- cout << fileStat.st_nlink << ' ';
- //获取文件所有者
- struct passwd *ps = getpwuid(fileStat.st_uid);
- cout << ps->pw_name << ' ';
- //获取文件所属组
- struct group *gp = getgrgid(fileStat.st_gid);
- cout << gp->gr_name << ' ';
- if (isDevice(fileStat))
- cout << major(fileStat.st_dev) << ", "
- << minor(fileStat.st_rdev) << ' ';
- else
- cout << fileStat.st_size << ' ';
- // 打印最后一次修改时间
- time_t mtime = fileStat.st_mtime;
- struct tm *pTime = localtime(&mtime);
- cout << pTime->tm_mon+1 << "月 " << pTime->tm_mday << ' '
- << pTime->tm_hour << ':' << pTime->tm_min << ' ';
- // 打印文件名
- cout << argv[1];
- if (isLink(fileStat))
- {
- cout << " -> ";
- char name[1024] = {0};
- if (readlink(argv[1], name, sizeof(name)) == -1)
- err_exit("readlink error");
- cout << name;
- }
- cout << endl;
- }
- inline void err_exit(std::string message)
- {
- perror(message.c_str());
- exit(EXIT_FAILURE);
- }
- bool isDevice(const struct stat &fileStat)
- {
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFBLK:
- case S_IFCHR:
- return true;
- break;
- default:
- return false;
- break;
- }
- return false;
- }
- bool isLink(const struct stat &fileStat)
- {
- if ((fileStat.st_mode & S_IFMT) == S_IFLNK)
- return true;
- return false;
- }
- void filePerm(const struct stat &fileStat, char *perm)
- {
- strcpy(perm, "----------");
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFSOCK:
- perm[0] = 's';
- break;
- case S_IFLNK:
- perm[0] = 'l';
- break;
- case S_IFREG:
- perm[0] = '-';
- break;
- case S_IFBLK:
- perm[0] = 'b';
- break;
- case S_IFDIR:
- perm[0] = 'd';
- break;
- case S_IFCHR:
- perm[0] = 'c';
- break;
- case S_IFIFO:
- perm[0] = 'p';
- break;
- default:
- perm[0] = '?';
- break;
- }
- if (fileStat.st_mode & S_IRUSR)
- perm[1] = 'r';
- if (fileStat.st_mode & S_IWUSR)
- perm[2] = 'w';
- if (fileStat.st_mode & S_IXUSR)
- perm[3] = 'x';
- if (fileStat.st_mode & S_IRGRP)
- perm[4] = 'r';
- if (fileStat.st_mode & S_IWGRP)
- perm[5] = 'w';
- if (fileStat.st_mode & S_IXGRP)
- perm[6] = 'x';
- if (fileStat.st_mode & S_IROTH)
- perm[7] = 'r';
- if (fileStat.st_mode & S_IWOTH)
- perm[8] = 'w';
- if (fileStat.st_mode & S_IXOTH)
- perm[9] = 'x';
- }
功能:获取文件元数据
- #include <sys/types.h>
- #include <sys/stat.h>
- #include <unistd.h>
- int stat(const char *path, struct stat *buf);
- int fstat(int fd, struct stat *buf);
- int lstat(const char *path, struct stat *buf);
stat结构体
- struct stat
- {
- dev_t st_dev; /* ID of device containing file */
- ino_t st_ino; /* inode number */
- mode_t st_mode; /* protection */
- nlink_t st_nlink; /* number of hard links */
- uid_t st_uid; /* user ID of owner */
- gid_t st_gid; /* group ID of owner */
- dev_t st_rdev; /* device ID (if special file) */
- off_t st_size; /* total size, in bytes */
- blksize_t st_blksize; /* blocksize for filesystem I/O */
- blkcnt_t st_blocks; /* number of 512B blocks allocated */
- time_t st_atime; /* time of last access */
- time_t st_mtime; /* time of last modification */
- time_t st_ctime; /* time of last status change */
- };
- //示例 - err_exit函数如前
- // 其实可以通过Linux 系统调用major, minor来替换(如下)
- #define MAJOR(a) (int)((unsigned short)a >> 8) //主设备号: 获取高8位
- #define MINOR(a) (int)((unsigned short)a & 0xFF)//次设备号: 获取低8位
- bool fileType(const struct stat &fileStat);
- void filePerm(const struct stat &fileStat, char *perm);
- int main(int argc, char *argv[])
- {
- if (argc != 2)
- {
- cerr << "Usage: " << argv[0] << " <file-name>" << endl;
- exit(EXIT_FAILURE);
- }
- struct stat fileStat;
- if (lstat(argv[1], &fileStat) == -1)
- err_exit("stat error");
- cout << "file-name: " << argv[1] << endl;
- cout << "st_ino = " << fileStat.st_ino << endl;
- cout << "device major: " << major(fileStat.st_dev)
- << ", minor: " << minor(fileStat.st_dev) << endl;
- if (fileType(fileStat))
- {
- cout << "----------------------------" << endl;
- cout << "major: " << MAJOR(fileStat.st_dev)
- << ", minor: " << MINOR(fileStat.st_rdev) << endl;
- // cout << "major: " << major(fileStat.st_dev)
- // << ", minor: " << minor(fileStat.st_rdev) << endl;
- }
- //获取文件的权限: 但要注意需要&上07777
- fprintf(stdout, "file permission: %o", fileStat.st_mode&07777);
- char perm[11];
- filePerm(fileStat, perm);
- cout << ", msg: " << perm << endl;
- cout << "st_nlink = " << fileStat.st_nlink << endl;
- cout << "st_uid = " << fileStat.st_uid << endl;
- cout << "st_gid = " << fileStat.st_gid << endl;
- cout << "st_size = " << fileStat.st_size << endl;
- cout << "st_blksize = " << fileStat.st_blksize << endl;
- cout << "st_blocks = " << fileStat.st_blocks << endl;
- cout << "st_atime = " << fileStat.st_atime << endl;
- cout << "st_ctime = " << fileStat.st_ctime << endl;
- cout << "st_mtime = " << fileStat.st_mtime << endl;
- }
- bool fileType(const struct stat &fileStat)
- {
- cout << "file-type: ";
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFSOCK:
- cout << "socket";
- break;
- case S_IFLNK:
- cout << "symbolic link";
- break;
- case S_IFREG:
- cout << "regular file";
- break;
- case S_IFBLK:
- cout << "block device" << endl;
- return true;
- break;
- case S_IFDIR:
- cout << "directory";
- break;
- case S_IFCHR:
- cout << "character device" << endl;
- return true;
- break;
- case S_IFIFO:
- cout << "FIFO" << endl;
- break;
- default:
- cout << "unknown?";
- break;
- }
- cout << endl;
- return false;
- }
- void filePerm(const struct stat &fileStat, char *perm)
- {
- strcpy(perm, "----------");
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFSOCK:
- perm[0] = 's';
- break;
- case S_IFLNK:
- perm[0] = 'l';
- break;
- case S_IFREG:
- perm[0] = '-';
- break;
- case S_IFBLK:
- perm[0] = 'b';
- break;
- case S_IFDIR:
- perm[0] = 'd';
- break;
- case S_IFCHR:
- perm[0] = 'c';
- break;
- case S_IFIFO:
- perm[0] = 'p';
- break;
- default:
- perm[0] = '?';
- break;
- }
- if (fileStat.st_mode & S_IRUSR)
- perm[1] = 'r';
- if (fileStat.st_mode & S_IWUSR)
- perm[2] = 'w';
- if (fileStat.st_mode & S_IXUSR)
- perm[3] = 'x';
- if (fileStat.st_mode & S_IRGRP)
- perm[4] = 'r';
- if (fileStat.st_mode & S_IWGRP)
- perm[5] = 'w';
- if (fileStat.st_mode & S_IXGRP)
- perm[6] = 'x';
- if (fileStat.st_mode & S_IROTH)
- perm[7] = 'r';
- if (fileStat.st_mode & S_IWOTH)
- perm[8] = 'w';
- if (fileStat.st_mode & S_IXOTH)
- perm[9] = 'x';
- }
实现ls -l的功能:
【拓展函数】
1.getpwuid
- struct passwd *getpwuid(uid_t uid);
- //passwd结构体
- struct passwd
- {
- char *pw_name; /* username */
- char *pw_passwd; /* user password */
- uid_t pw_uid; /* user ID */
- gid_t pw_gid; /* group ID */
- char *pw_gecos; /* user information */
- char *pw_dir; /* home directory */
- char *pw_shell; /* shell program */
- };
2.getgrgid
- struct group *getgrgid(gid_t gid);
- //group结构体
- struct group
- {
- char *gr_name; /* group name */
- char *gr_passwd; /* group password */
- gid_t gr_gid; /* group ID */
- char **gr_mem; /* group members */
- };
3. readlink
- ssize_t readlink(const char *path, char *buf, size_t bufsiz);
4. localtime
- struct tm *localtime(const time_t *timep);
- //tm结构体
- struct tm
- {
- int tm_sec; /* seconds */
- int tm_min; /* minutes */
- int tm_hour; /* hours */
- int tm_mday; /* day of the month */
- int tm_mon; /* month */
- int tm_year; /* year */
- int tm_wday; /* day of the week */
- int tm_yday; /* day in the year */
- int tm_isdst; /* daylight saving time */
- };
- //示例: 实现简单的ls -l功能
- #include <iostream>
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <string.h>
- #include <sys/types.h>
- #include <sys/stat.h>
- #include <fcntl.h>
- #include <unistd.h>
- #include <grp.h>
- #include <pwd.h>
- #include <time.h>
- using namespace std;
- inline void err_exit(std::string message);
- bool isDevice(const struct stat &fileStat);
- bool isLink(const struct stat &fileStat);
- void filePerm(const struct stat &fileStat, char *perm);
- int main(int argc, char *argv[])
- {
- if (argc != 2)
- {
- cerr << "Usage: " << argv[0] << " <file-name>" << endl;
- exit(EXIT_FAILURE);
- }
- struct stat fileStat;
- if (lstat(argv[1], &fileStat) == -1)
- err_exit("lstat error");
- //获取权限
- char perm[11];
- filePerm(fileStat, perm);
- cout << perm << ' ';
- //获取文件链接数
- cout << fileStat.st_nlink << ' ';
- //获取文件所有者
- struct passwd *ps = getpwuid(fileStat.st_uid);
- cout << ps->pw_name << ' ';
- //获取文件所属组
- struct group *gp = getgrgid(fileStat.st_gid);
- cout << gp->gr_name << ' ';
- if (isDevice(fileStat))
- cout << major(fileStat.st_dev) << ", "
- << minor(fileStat.st_rdev) << ' ';
- else
- cout << fileStat.st_size << ' ';
- // 打印最后一次修改时间
- time_t mtime = fileStat.st_mtime;
- struct tm *pTime = localtime(&mtime);
- cout << pTime->tm_mon+1 << "月 " << pTime->tm_mday << ' '
- << pTime->tm_hour << ':' << pTime->tm_min << ' ';
- // 打印文件名
- cout << argv[1];
- if (isLink(fileStat))
- {
- cout << " -> ";
- char name[1024] = {0};
- if (readlink(argv[1], name, sizeof(name)) == -1)
- err_exit("readlink error");
- cout << name;
- }
- cout << endl;
- }
- inline void err_exit(std::string message)
- {
- perror(message.c_str());
- exit(EXIT_FAILURE);
- }
- bool isDevice(const struct stat &fileStat)
- {
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFBLK:
- case S_IFCHR:
- return true;
- break;
- default:
- return false;
- break;
- }
- return false;
- }
- bool isLink(const struct stat &fileStat)
- {
- if ((fileStat.st_mode & S_IFMT) == S_IFLNK)
- return true;
- return false;
- }
- void filePerm(const struct stat &fileStat, char *perm)
- {
- strcpy(perm, "----------");
- switch(fileStat.st_mode & S_IFMT)
- {
- case S_IFSOCK:
- perm[0] = 's';
- break;
- case S_IFLNK:
- perm[0] = 'l';
- break;
- case S_IFREG:
- perm[0] = '-';
- break;
- case S_IFBLK:
- perm[0] = 'b';
- break;
- case S_IFDIR:
- perm[0] = 'd';
- break;
- case S_IFCHR:
- perm[0] = 'c';
- break;
- case S_IFIFO:
- perm[0] = 'p';
- break;
- default:
- perm[0] = '?';
- break;
- }
- if (fileStat.st_mode & S_IRUSR)
- perm[1] = 'r';
- if (fileStat.st_mode & S_IWUSR)
- perm[2] = 'w';
- if (fileStat.st_mode & S_IXUSR)
- perm[3] = 'x';
- if (fileStat.st_mode & S_IRGRP)
- perm[4] = 'r';
- if (fileStat.st_mode & S_IWGRP)
- perm[5] = 'w';
- if (fileStat.st_mode & S_IXGRP)
- perm[6] = 'x';
- if (fileStat.st_mode & S_IROTH)
- perm[7] = 'r';
- if (fileStat.st_mode & S_IWOTH)
- perm[8] = 'w';
- if (fileStat.st_mode & S_IXOTH)
- perm[9] = 'x';
- }