《unix/linux编程实践教程》学习笔记:第四章 文件系统:编写pwd

来源:互联网 发布:rpc java 编辑:程序博客网 时间:2024/05/01 20:12

文件系统的内部结构
Unix文件系统由三个部分组成:
(1)超级块,存放文件系统本身的结构信息。
(2)inode表,每个文件都有一个inode,用来保存文件的属性,inode的位置被称为文件的inode号,inode号是文件的唯一标识
(3)数据区,存放文件的内容。

对目录的理解:
目录是一种特殊的文件,目录是名字和指针的列表,目录中的每个入口指向一个文件或目录,目录包含了父目录和子目录的入口。
这里写图片描述
通过 ls -iaR dirname 我们可以查看该目录下目录树中的所有文件的inode号。

所以,以上图为例tests文件在目录flasky中的真正含义是tests文件的inode号1066572保存在flasky目录文件中,且该inode号对应的文件名字符串是tests。目录app在目录flasky中的含义是,app文件中‘..’的inode号(929418)与flasky中‘.’的inode号相同,且flasky中app项的inode号与app文件中‘.’项的inode号(941640)相同。

对链接的理解:
连接可以分为硬链接和软链接(符号链接)。
硬链接:同一个inode号在不同的目录文件中有不同的文件名,即不同目录下的不同文件名的文件共享同一个inode号,也就是本质是同一个文件,但是为了共享被放到不同的目录下。
软连接:通过名字引用文件,即引用的是目录。

文件相关命令的理解:
所有从文件读取数据的命令,例如:cat,cp,more,who等,都是将文件名传给open来访问文件内容。对open的每次调用都是先在目录中寻找文件名,然后根据目录中的inode号来获取文件的属性,最终找到文件的内容。

pwd编写:

#include <stdio.h>#include <sys/types.h>#include <sys/stat.h>#include <dirent.h>ino_t get_inode(char *);void printpathto(ino_t);void inum_to_name(ino_t,char *,int);int main(){    printpathto(get_inode("."));//递归入口    putchar('\n');    return 0;}void printpathto(ino_t this_inode){    ino_t my_inode;    char its_name[BUFSIZ];    if(get_inode("..")!=this_inode)        {        chdir("..");        inum_to_name(this_inode,its_name,BUFSIZ);        my_inode = get_inode(".");        printpathto(my_inode);//递归查找,直到根目录返回        printf("/%s",its_name);        }}void inum_to_name(ino_t inode_to_find,char * namebuf,int buflen){    DIR *dir_ptr;    struct dirent *direntp;    dir_ptr = opendir(".");    if(dir_ptr == NULL)    {        perror(".");        exit(1);    }    while((direntp = readdir(dir_ptr)) != NULL)            if(direntp -> d_ino == inode_to_find)//注意readdir会一条一条读取            {                strncpy(namebuf,direntp->d_name,buflen);                namebuf[buflen - 1] = '\0';                closedir(dir_ptr);                return;            }    fprintf(stderr,"error looking for inum %d\n",inode_to_find);    exit(1);}ino_t get_inode(char *fname){    struct stat info;    if(stat(fname,&info) == -1){        fprintf(stderr,"Cannot stat");        perror(fname);        exit(1);    }       return info.st_ino;}
0 0