关于stat()这个函数以前也有所了解,但是没有使用过,最近在看v4l2程序是其在打开设备之前进行检查该设备是否为字符设备,感觉这点十分的重要,查看了一下《Unix环境高级编程》在这对stat()函数进行总结一下;
有三个函数可以实现查看文件属性的功能:
-
#include <sys/stat.h>
-
int stat(const char *restrict pathname,struct stat *restrict buf);
-
-
int fstat(int fields,struct stat *restrict buf);
-
-
int lstat(const char *restrict pathname,struct stat *restrict buf);
-
-
三个函数返回值都是:成功返回0;出错返回-1;
功能:
stat:返回与pathname所表示的文件有关的信息结构;
fstat:获取已在描述符filedes上打开文件的有关信息结构;
lstat:该函数功能和stat基本相同,区别只在符号链接文件,对应符号链接文件lstat()返回该符号链接的有关信息,而stat()返回符号链接引用文件的信息。
参数说明:三个函数的第一个参数很好理解,它们相同的参数buf指针,是指向的一个结构stat,其基本形式为:
-
struct stat {
-
mode_t st_mode; //文件类型,即权限
-
ino_t st_ino; //inode节点号
-
dev_t st_dev; //设备号码(文件系统)
-
dev_t st_rdev; //特殊设备号码
-
nlink_t st_nlink; //文件的连接数
-
uid_t st_uid; //文件所有者
-
gid_t st_gid; //文件所有者对应的组
-
off_t st_size; //普通文件,对应的文件字节数,即普通文件的大小
-
time_t st_atime; //文件最后被访问的时间
-
time_t st_mtime; //文件内容最后被修改的时间
-
time_t st_ctime; //文件状态改变的最后时间
-
blksize_t st_blksize; //最佳的I/O块大小
-
blkcnt_t st_blocks; //分配的磁盘块的数量
-
};
七种文件类型:
1、普通文件(regular file):最常用的文件类型。
2、目录文件(directory file)
3、块特殊文件(block special file):该类文件提供对设备(如:磁盘)带缓冲的访问,每次访问以固定的长度为单位进行;
4、字符特殊文件(character special file):不带缓冲的访问,每次访问长度可变。
5、FIFO(有名管道):用于进程间通信
6、套接字(socket):用于进程间网络通信。
7、符号链接(symbolic link):该类文件指向另一个文件,(使用stat和lstat有区别);
文件类型的信息包含在stat结构体中的st_mode成员中。用中的宏可以进行判断。
S_ISREG() 普通文件
S_ISDIR() 目录文件
S_ISCHR() 字符特殊文件
S_ISBLK() 块特殊文件
S_ISFIFO() 有名管道文件
S_ISLNK() 符号链接文件
S_ISSOCK() 套接字
在中提供了一个例子:
-
#include <stdio.h>
-
#include <errno.h>
-
#include <stdlib.h>
-
#include <sys/stat.h>
-
int
-
main(int argc,char *argv[])
-
{
-
int i;
-
struct stat buf;
-
char *ptr;
-
for (i= 1; i < argc; i++){
-
printf("%s: ",argv[i]);
-
if (stat(argv[i],&buf) < 0){ //可以换成lstat试试效果
-
printf("lstat error\n");
-
continue;
-
}
-
if (S_ISREG(buf.st_mode)){
-
ptr = "regular";
-
}
-
else if (S_ISDIR(buf.st_mode)){
-
ptr = "directory";
-
}
-
else if (S_ISCHR(buf.st_mode)){
-
ptr = "character special";
-
}
-
else if (S_ISBLK(buf.st_mode)){
-
ptr = "block";
-
}
-
else if (S_ISFIFO(buf.st_mode)){
-
ptr = "fifo";
-
}
-
else if (S_ISLNK(buf.st_mode)){
-
ptr = "symbolic link";
-
}
-
else if (S_ISSOCK(buf.st_mode)){
-
ptr = "socked";
-
}
-
else
-
ptr = "**unkown node**";
-
printf("%s\n",ptr);
-
}
-
return 0;
-
}
我创建了一个'test_stat.c'文件,再创建了一个指向它的符号链接‘test_stat.so’
[root@localhost /test]#ls -l
-rwxr-xr-x 1 root root 771 Nov 10 09:54 test_stat.c
lrwxrwxrwx 1 root root 11 Nov 10 09:54 test_stat.so -> test_stat.c
[root@localhost /test]#./stat test_stat.so
test_stat.so:regular
将程序中的stat()换成lstat(),生成可执行文件lstat:
[root@localhost /test]#./lstat test_stat.so
test_stat.so:symbolic link
参考书:《Unix 环境高级编程》
阅读(2186) | 评论(0) | 转发(0) |