• 企业400电话
  • 微网小程序
  • AI电话机器人
  • 电商代运营
  • 全 部 栏 目

    企业400电话 网络优化推广 AI电话机器人 呼叫中心 网站建设 商标✡知产 微网小程序 电商运营 彩铃•短信 增值拓展业务
    Unix文件系统和pwd命令实现详解

    1. 对于用户来讲Unix系统中硬盘上的文件组成一棵目录树。每个目录能包含文件和其他子目录。

    目录树的深度几乎没有限制,当然如果你所创建的目录树太深,系统就会提醒超过范围,并停止执行,以下脚本经测试有效

    while true

    do

    mkdir deep_well

    cd deep_well

    done

    我运行了几秒后,中断系统提示超过目录树范围。

    2. 一个磁盘可以划分为N多扇区,每个扇区有512字节 。扇区是磁盘上的基本存储单元,我们可以将每个扇区进行编号,这样磁盘就变为

    一系列编了号的块的组合。

    3. 磁盘块上存储文件时,按照一定的规律。

    每个文件系统分为3部分:超级块,i-节点表,数据区 。

    超级块 :存放文件系统本身的信息,比如记录了每个区域的大小,或未被使用的磁盘块的信息。(不同版本稍有差别)

    i-节点表 :每个文件都有其属性,大小,最近修改时间等等,这些被存储在ino_t 的结构体中,所有的i-节点都有一样的大小,i-节点表就是这样一些节点的列表。

    (表中的每个i-节点都通过位置来标志,例如标志为2的i-节点位于文件系统i-节点表中的第3个位置 )

    数据块 :存放文件内容,因为块的大小一定,所以有时一个文件会分布在多个磁盘上。

    4. 创建一个文件的4个步骤:

    存储属性:内核先找到一个空的i-节点,把文件的属性信息填入其中;

    存储数据:从磁盘上找出空闲块,把文件数据复制进去;

    记录分配情况:内核在i-节点的磁盘分布区记录了刚刚的磁盘编号

    添加文件名到目录:将(i-节点号,文件名)添加到目录。

    5. cat,more等一些命令的实现思想:

    cat name

    在目录中寻找文件名,

    定位到相应文件名的i-节点号;

    根据i-节点号里面获得文件属性,查看权限,若权限不够则open()函数返回1,打开失败,停止;

    根据i-节点里面磁盘位置访问文件位置的数据块

    一遍遍调用read读取数据(可以存放到缓冲区)

    6. 大文件的存储

    如果一个文件需要14个编号的磁盘块来存储,但是i-节点值包含13个项的分配链表,这时候,我们可以将前10个放到i-节点里,其他4个放到一个数据块里面,在i-节点的第

    11位写上指向存那4个编号的块。则我们实际用了10+4+1个数据块,那个多出来的叫:间接块 。

    同理,间接块饱和时,我们可以设置二级间接块,,,

    7. 文件在目录中的含义

    目录包含(i-节点号,文件名)的入口,即目录包含的是文件的引用,每个应用称为链接。

    8. 目录包含子目录的含义

    目录包含指向子目录i-节点的链接。

    9. 目录有个父目录的含义:

    目录包含..的链接,即指向父目录。

    10. 文件没有名字只有i-节点号,但是链接可以有名字 ,一个文件可以有多个链接(他们的名字也可以不同,但是他们指向一个文件,对他们的操作就是对源文件的操作)

    11. Unix系统可以包含多个文件系统,每个文件系统都是一棵独立的树,都有根目录,但是系统可以将他们整合成一棵大树,即一个树的根装载到另一个数的某个节点上。mount

    12 符号链接通过文件名引用文件,可以跨越文件系统,也可以指向目录。相当于windows中快捷方式。

    硬链接是将目录链接到树的指针,同时也是将文件名和文件本身链接起来的指针。通过对i-节点号引用文件。

    13 .与目录树相关的命令和系统调用

    命令 mkdir

    实现 头文件 #include sys/stat.h> #include sys/types.h>

    函数原型 int res=mkdir (char *path,mode_t mode);

    命令 rmdir 删除一个目录,这个目录必须是空的

    实现 头文件#include unistd.h>

    函数原型int res=rmdir (const char* path);

    命令 rm 减少相应i-节点连接数,若此时节点书减为0,就释放数据块和节点。不能用来删除目录

    实现 头文件#include unistd.h>

    函数原型int res=unlink (const char *path);

    命令 ln 不能用来生成目录的链接。

    实现 头文件#include unistd.h>

    函数原型 int res=link (const char *old,const char *new);

    命令 mv 删除原来的目录,复制到新的里面

    实现 头文件#include unistd.h>

    函数原型int res=rename (const char* from,const char *to);

    原理:复制链接到新的名字/位置再删除原来的链接

    if(link("x","z")!=-1)

    unlink("x");

    命令 cd 对进程有影响,对目录本身没有影响

    实现 头文件 #include unistd.h>

    函数原型 int res=chdir (const char *path);

    14. pwd 命令的实现

    #include stdio.h>

    #include sys/types.h>

    #include sys/stat.h>

    #include dirent.h>

    #include string.h>

    #include unistd.h>

    ino_t get_inode(char *);//get the inode number

    void printpathto(ino_t);

    void inum_to_name(ino_t,char *,int);//get the node name by its inode number

    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(".."); //up one dir

    inum_to_name(this_inode,its_name,BUFSIZ); //get its name

    my_inode=get_inode(".");

    printpathto(my_inode); //itorater

    printf("/%s",its_name);

    }

    }

    void inum_to_name(ino_t inode_to_find,char *namebuf,int buflen)

    {

    DIR *dir_ptr; //the directory

    struct dirent *direntp; //each entry

    dir_ptr=opendir(".");

    if(dir_ptr==NULL)

    {

    perror(".");

    return;

    }

    while((direntp=readdir(dir_ptr))!=NULL)

    {

    if(direntp->d_ino==inode_to_find)

    {

    strncpy(namebuf,direntp->d_name,buflen);

    namebuf[buflen-1]='\0';

    closedir(dir_ptr);

    return;

    }

    }

    fprintf(stderr,"error looking for inum %d\n",(int)inode_to_find);

    return;

    }

    ino_t get_inode(char *fname)

    {

    struct stat info;

    if(stat(fname,info)==-1)

    {

    fprintf(stderr,"Can not stat");

    perror(fname);

    return 1;

    }

    return info.st_ino;

    }

    运行结果:

    caoli@caoli-laptop:~/workspace/test$ ./pwd1

    /home/caoli/workspace/test

    caoli@caoli-laptop:~/workspace/test$

    上一篇:Unix中的dot命令详解
    下一篇:FreeBSD下zfs: failed with error 6错误如何解决?
  • 相关文章
  • 

    © 2016-2020 巨人网络通讯 版权所有

    《增值电信业务经营许可证》 苏ICP备15040257号-8

    Unix文件系统和pwd命令实现详解 Unix,文件,系,统和,pwd,命令,