- 論壇徽章:
- 2
|
文件系統(tǒng)的實(shí)現(xiàn)還需要對(duì)超級(jí)塊的操作,對(duì)文件的操作,索引節(jié)點(diǎn)操作等等
我們就先從掛載一個(gè)文件系統(tǒng)開始
掛載文件系統(tǒng)時(shí)候,VFS會(huì)通過mount命令中的文件系統(tǒng)類型或超級(jí)塊魔數(shù)來尋找file_system_type結(jié)構(gòu)
下面就是GTFS的file_system_type結(jié)構(gòu)(定義在super.c中)- static struct file_system_type gt_fs_type ={
- .owner =THIS_MODULE,
- .name ="gt",//文件系統(tǒng)名稱
- .get_sb =gt_get_sb,//讀取超級(jí)塊方法
- .kill_sb =kill_block_super,
- .fs_flags =FS_REQUIRES_DEV,
- };
復(fù)制代碼 我們只需要完成gt_get_sb(定義在super.c中)方法即可- static int gt_get_sb(struct file_system_type *fs_type,
- int flags,const char *dev_name,void *data,struct vfsmount *mnt){
- return get_sb_bdev(fs_type,flags,dev_name,data,gt_fill_super,mnt);
- }
復(fù)制代碼 從gt_get_sb函數(shù)可以看出,這個(gè)函數(shù)調(diào)用了get_sb_bdev函數(shù),get_sb_bdev又調(diào)用了gt_fill_super函數(shù)
gt_fill_super函數(shù)才是正真用來讀取超級(jí)塊的方法- static int gt_fill_super(struct super_block *sb,void *data,int silent){
- struct buffer_head *bh;
- struct gt_super_block *gs;
- struct gt_sb_info *sbi;
- struct inode *root;//設(shè)備的根目錄
-
- unsigned long sb_block=1;//超級(jí)塊的塊號(hào)為1,第0塊為啟動(dòng)塊
- long ret=-EINVAL;
-
- int blocksize=BLOCK_SIZE;//BLOCK_SIZE為1024
- sbi=kzalloc(sizeof(struct gt_sb_info),GFP_KERNEL);
- if(!sbi)
- return -ENOMEM;
- if(!sb_set_blocksize(sb,BLOCK_SIZE))//設(shè)置VFS超級(jí)塊的塊大小
- goto out_bad_hblock;
- if(!(bh=sb_bread(sb,sb_block))){//將GTFS超級(jí)塊所在的塊讀入內(nèi)存
- printk("GT-fs:unable to read superblock\n");
- goto failed_sbi;
- }
- gs=(struct gt_super_block *)(bh->b_data);
- sbi->s_sbh=bh;//指向從磁盤讀入的GTFS超級(jí)塊所在的緩沖區(qū)
- sbi->s_gs=gs;//將內(nèi)存中的GTFS超級(jí)塊和從磁盤讀入的GTFS超級(jí)塊聯(lián)系起來
- sb->s_fs_info=sbi;//將VFS超級(jí)塊和GTFS的超級(jí)塊聯(lián)系起來
- sb->s_magic=gs->s_magic;//設(shè)置魔數(shù)
- if(sb->s_magic !=GT_SUPER_MAGIC)
- goto cantfind_gt;
- blocksize=GT_BLOCK_SIZE;
- sb->s_op=>_sops;
-
- root=gt_iget(sb,GT_ROOT_INO);//GT_ROOT_INO為1,讀入文件系統(tǒng)的根目錄
- if(IS_ERR(root)){
- ret=PTR_ERR(root);
- printk(KERN_ERR "GT-fs: can't find root inode\n");
- goto failed_mount;
- }
- if (!S_ISDIR(root->i_mode) || !root->i_blocks || !root->i_size) {
- iput(root);
- printk(KERN_ERR "isdir?%d,root->i_blocks=%d,root->i_size=%d\n",S_ISDIR(root->i_mode) , root->i_blocks, root->i_size);
- printk(KERN_ERR "GT-fs: corrupt root inode\n");
- goto failed_mount;
- }
- sb->s_root = d_alloc_root(root);//設(shè)置超級(jí)塊的根目錄
- if (!sb->s_root) {
- iput(root);
- printk(KERN_ERR "GT: get root inode failed\n");
- ret = -ENOMEM;
- goto failed_mount;
- }
-
- return 0;
- cantfind_gt:
- printk("VFS: Can't find an gt filesystem on dev %s.\nmagic on dev is %d and magic of GT is %d\n",sb->s_id,sb->s_magic,GT_SUPER_MAGIC);
- failed_mount:
- brelse(bh);
- out_bad_hblock:
- printk("GT-fs:blocksize too small for device\n");
- failed_sbi:
- sb->s_fs_info=NULL;
- kfree(sbi);
- return ret;
- }
復(fù)制代碼 這段函數(shù)主要是從磁盤讀入文件系統(tǒng)的超級(jí)塊,用來填充內(nèi)存中的GTFS超級(jí)塊,和VFS超級(jí)塊
調(diào)用gt_iget函數(shù)讀入指定文件系統(tǒng)的根目錄。 |
|