Linux中文件和目录使用的几个结构体--DIR, dirent, stat

1. struct stat结构体

在linux文件IO中,我们可能会用到struct stat结构体, 如下:

struct stat {
    mode_t     st_mode;       //文件访问权限
    ino_t      st_ino;        //索引节点号
    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;    //包含该文件的磁盘块的大小
    blkcnt_t   st_blocks;    //该文件所占的磁盘块
};

依赖的头文件是:



struct stat这个结构体是用来描述一个linux系统文件系统中的文件属性的结构.

一般通过如下API获取:

int stat(const char *path, struct stat *struct_stat);
int lstat(const char *path,struct stat *struct_stat);
int fstat(int fdp, struct stat *struct_stat);

前两个函数的第一个参数都是文件的路径,第二个参数是struct stat的指针, 第三个函数通过文件描述符获取文件对应的属性, fdp为文件描述符.

我们可以认为ls -al输出的大多数属性都可以由struct stat得到, 其中比较关键的有:

stat结构体中的st_mode 则定义了下列数种情况:
    S_IFMT   0170000    文件类型的位遮罩
    S_IFSOCK 0140000    scoket
    S_IFLNK 0120000     符号连接
    S_IFREG 0100000     一般文件
    S_IFBLK 0060000     区块装置
    S_IFDIR 0040000     目录
    S_IFCHR 0020000     字符装置
    S_IFIFO 0010000     先进先出

2 DIR 和 struct dirent

其中DIR如下:

struct __dirstream {
    void *__fd; /* `struct hurd_fd' pointer for descriptor.   */
    char *__data;
    int __entry_data;
    char *__ptr;
    int __entry_ptr;
    size_t __allocation;
    size_t __size;
    __libc_lock_define (, __lock)
};
typedef struct __dirstream DIR;

可以看出DIR 类似于FILE(标准IO中常用FILE ), 底层包装了目录的文件描述符*!!!

APUE上给目录文件(directory file)概念的定义如下: 这种文件包含了其他文件的名字以及指向与这些文件有关的信息的指针.

常用DIR *相关的API如下:

DIR *opendir(const char *name);
int closedir(DIR *dp);

void rewinddir(DIR *dp);/// reset directory stream
long telldir(DIR *dp);/// return current location in directory stream
void seekdir(DIR *dp, long loc);

struct dirent *readdir(DIR *dp);

其中DIR *opendir(const char *name)的解释如下:

opens a directory stream corresponding to the directory name, and returns a pointer to the directory stream. The stream is positioned at the first entry in the directory.

后面是struct dirent结构体, 可以使用struct dirent *readdir(DIR *dp);获取, 具体的结构体表示:

struct dirent
{
  long d_ino; /* inode number 索引节点号 */
    off_t d_off; /* offset to this dirent 在目录文件中的偏移 */
    unsigned short d_reclen; /* length of this d_name 文件名长 */
    unsigned char d_type; /* the type of d_name 文件类型 */
    char d_name [NAME_MAX+1]; /* file name (null-terminated) 文件名,最长255字符 */
}

从上述定义也能够看出来,dirent结构体存储的关于文件的信息很少,所以dirent同样也是起着一个索引的作用,能看到其中最关键的是d_name信息.

下面是一个实例, 遍历文件夹:

#define MAX_SIZE 256
char filename[256][256];
int len = 0;
int trave_dir(char *path, int depth) {
  DIR *d;// dir handle
  struct dirent *file;
  struct stat sb;

  if(!(d = opendir(path))) {
    printf("error opendir: %s!!!\n", path);
    return -1;
  }
  while((file = readdir(d)) != NULL) {
    // hide . ..
    if(strncmp(file->d_name, ".", 1) == 0) {
      continue;
    }
    strcpy(filename[len++], file->d_name);//save filename
    if(stat(file->d_name, &sb) >= 0 && S_ISDIR)
  }
}

你可能感兴趣的:(Linux中文件和目录使用的几个结构体--DIR, dirent, stat)