在操作文件时时常要获取文件的属性,比如类型、大小、权限、所有者等等信息,这些信息对于文件的传输管理等非常重要,而这些信息则可以通过下面这些函数获取。
这三个函数功能相同,区别在于,stat参数是文件名字,fstat参数则是一个被打开的文件描述符,而lstat则可以获取链接文件本身的属性
该结构体中有很多成员的含义和作用是一目了然的,比如:
1,文件索引号:stio,实质上是一个无符号整形数据,用来唯一确定分区中的文件。
2,引用计数:st nlink,记录该文件的名字(或叫硬链接)总数,文件的别名可以用
命令ink或者函数ink()来创建。当一个文件的引用计数st_nlink为零时,系统将会释放
清空该文件锁占用的一切系统资源。
3,文件所有者UID和所属组GID。
4,文件的大小。这个属性对只对普通文件有效。
5,文件所占数据块数目st blocks,表明该文件实际占用存储器空间。一个数据块一
般为512字节。
6,st atime、st_mtime和st ctime都是一个文件的时间戳,st atime代表文件
被访问了但是没有被修改的最近时间,st_mtime代表文件内容被修改的最近时间,
st ctime则代表了文件属性更改的最近时间。文件的时间戳对于某些场合来讲是至关重要
的属性,比如工程管理器make,他的工作原理就完全基于文件的时间戳上,判断文件的被
修改时间,决定其是否参与编译。
7,st blksize是所谓的“写数据块”的建议值,因为当应用程序频繁地往存储器写入
小块数据的时候,可能会导致效率的低下。
除此之外,st_dev、st_rdev和st_mode就没那么一目了然了,他们详细情况如下:
1,文件设备号。
属性结构体stat中有两个成员涉及文件的设备号,他们分别是 st_dev和 st_rdev,前者只对普通文件有效,它包含了普通文件所在的设备的设备号,因此这个成员对于特殊文件而言是无意义的。而st_rdev恰好相反,他储存的是特殊设备文件本身的设备号,因此st_rdev对于普通文件而言是无效的。
那什么是设备号呢?我们在系统/dev目录下执行一下ls—l一看究竟:
从上面的执行结果看到,在/dev下的文件没有“大小”的属性,而只有两个号码,比如文件tty,设备号为5,0,其中前面的5是所谓的主设备号,用来标识一种设备的类型,后面的0是所谓的次设备号,用来区分本系统中的多个同类设备。
设备号在编写设备文件的驱动程序中才需要用到,在应用编程中不需要关注。st_dev和st_rdev里面都包含了主次设备号,需要用到下面的函数来获取:
2,文件类型和权限
属性成员中的st_mode里面包含了文件类型和权限,st_mode实质上是一个无符号16位短整型数,各个位域所包含的含义如下:
st_mode[0:8]一一对应地代表了文件的各个用户的权限。
st_mode[9]存储了所谓的黏住位(只对目录有效),在拥有该目录的写权限的情况下,如果这一位被设置为1,那么某一用户也只能删除在本目录下属于自己的文件,否则可以删除任意文件。
st_mode[10]和 st_mode[11]分别用来设置文件的suid(只对普通文件有效)和sgid(只对目录有效)。如果suid被设置为1,则任何用户在执行该文件的时候均会获得该文件所有者的临时授权,即其有效UID将等于文件所有者的UID。如果sgid被设置为1,则任何在该目录下执行的程序均会获得该目录所属组成员的临时授权,即其有效GID将等于该目录的所属组成员的GID。
st_mode[12:15]用以标识Linux下不同的文件类型,由于Linux总共只有7种文件类型,因此4位足以表达。
下面的表格是 st_mode的详细信息:
可以将st_mode与S_IFMT相与得到的数据用于判断文件类型
同时判断文件的类型不是必须读取st_mode高四位,也可以使用一些宏定义