Linux VFS

to be continued ....

digraph VFS
{
graph [rankdir = "LR", bgcolor = "white:lightblue", style="filled", gradientangle = 270];

node [fontsize = "16", shape = "ellipse", style="filled", gradientangle=90];

edge [];


/*

*/
"task_struct" [
label = "<struct>struct task_struct | ... | 
	volatile long state | ... | 
	sched_class *sched_class | sched_entity  se | sched_rt_entity  rt | ... |
	task_struct *parent | ...|
	list_head  tasks | ...| 
	int prio | int static_prio | int normal_prio | ... |
	unsigned int policy | ... |
	mm_struct *mm | mm_struct *active_mm | ... |
	<fs> fs_struct  *fs| <files> files_struct  *files | ... |
	pid_t  pid | pid_t  tgid | ... |
	css_set *cgroups | list_head  cg_list | ... |
	rcu_head  rcu | ... |
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.035"
];

/*
  All per-process information about open files and file descriptors is contained therein.
*/
"files_struct" [
label="<struct>struct files_struct | ... |
	atomic_t count | <fdt>fdtable *fdt | fdtable fdtab | int next_fd | ... |
	embedded_fd_set close_on_exec_init | embedded_fd_set open_fds_init | ... |
	<fd_array>file * fd_array[NR_OPEN_DEFAULT] | ...
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.08"
]

/*
  fdtable结构的fd字段指向文件对象的指针数组。该数组的长度存放在max_fds字段中。通常,fd字段指向files_struct结构的fd_array字段,该字段包括32个文件对象指针。如果进程打开的文件数目多于32,内核就分配一个新的、更大的文件指针数组,并将其地址存放在fd字段中,内核同时也更新max_fds字段的值。
  对于在fd数组中所有元素的每个文件来说,数组的索引就是文件描述符(file descriptor)。
*/
"fdtable" [
label="<struct>struct fdtable |
	unsigned int max_fds | 
	{<fd>file ** fd | {<fd0>fd\[0\] | fd\[1\] | ...| fd\[max_fds-1\] ?}} | 
	fd_set *close_on_exec | fd_set *open_fds |
	rcu_head rcu|
	<next>fdtable *next
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.1"
]

/*
  The fs_struct contains filesystem information related to a process.
*/
"fs_struct" [
label="<struct>struct fs_struct | 
	int users | rwlock_t lock | int umask | int in_exec | 
	<root>path root | 
	<pwd> path pwd
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.14"
]

/*

*/
"path" [
label="<struct>struct path | 
	<mnt>vfsmount *mnt |
	<dentry>dentry *dentry
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.32"
]

/*
  The vfsmount represents a specific instance of a filesystem - a mount point
*/
"vfsmount" [
label="<struct>vfsmount |
	list_head mnt_hash |
	vfsmount *mnt_parent |
	dentry *mnt_mountpoint |
	dentry *mnt_root |
	super_block *mnt_sb |
	list_head mnt_mounts |
	list_head mnt_child |
	int mnt_flags |
	const char *mnt_devname |
	struct list_head mnt_list | ...|
	atomic_t mnt_count | ...

"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.07"
]

/* 
  The dentry object, which represents a directory entry, which is a single component of a path. 
  The dentry object does not correspond to any sort of on-disk data struct.

  一个有效的dentry结构必定有一个inode结构,这是因为一个目录项要么代表着一个文件,要么代表着一个目录,而目录实际上也是文件。所以,只要dentry结构是有效的,则其指针d_inode必定指向一个inode结构。可是,反过来则不然,一个inode却可能对应着不止一个dentry结构;也就是说,一个文件可以有不止一个文件名或路径名。这是因为一个已经建立的文件可以被连接(link)到其他文件名。所以在inode结构中有一个队列i_dentry,凡是代表着同一个文件的所有目录项都通过其dentry结构中的d_alias域挂入相应inode结构中的i_dentry队列。
    在内核中有一个哈希表dentry_hashtable ,是一个list_head的指针数组。一旦在内存中建立起一个目录节点的dentry 结构,该dentry结构就通过其d_hash域链入哈希表中的某个队列中。
    内核中还有一个队列dentry_unused,凡是已经没有用户(count域为0)使用的dentry结构就通过其d_lru域挂入这个队列。
    Dentry结构中除了d_alias 、d_hash、d_lru三个队列外,还有d_vfsmnt、d_child及d_subdir三个队列。其中d_vfsmnt仅在该dentry为一个安装点时才使用。另外,当该目录节点有父目录时,则其dentry结构就通过d_child挂入其父节点的d_subdirs队列中,同时又通过指针d_parent指向其父目录的dentry结构,而它自己各个子目录的dentry结构则挂在其d_subdirs域指向的队列中。
     从上面的叙述可以看出,一个文件系统中所有目录项结构或组织为一个哈希表,或组织为一颗树,或按照某种需要组织为一个链表,这将为文件访问和文件路径搜索奠定下良好的基础。
*/
"dentry" [
label="<struct>dentry | 
	atomic_t d_count | int d_mounted | ... |
	<d_inode>inode *d_inode |
	hlist_node d_hash |
	dentry *d_parent |
	list_head d_lru |
	{d_u | {list_head d_child | rcu_head d_rcu}} |
	list_head d_subdirs |
	<d_alias>list_head d_alias | ... |
	<d_op>dentry_operations *d_op | 
	<d_sb>super_block *d_sb | ...|
	unsigned char d_iname
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.06"
]

/*
  The inode object represents all the inoformation needed by the kernel to manipulate a file or directory. Whaterver the case, the inode object is constructed in memory in whatever manner is applicable to the filesystem.
*/
"inode" [
label="<struct>inode |
	unsigned long	 i_ino |
	atomic_t i_count |
	<i_hash>hlist_node i_hash |
	<i_list>list_head i_list |
	<i_sb_list>list_head i_sb_list |
	<i_dentry>list_head i_dentry | ... |
	{union | {pipe_inode_info	*i_pipe | block_device *i_bdev | cdev *i_cdev}} |...|
	<i_devices>list_head i_devices | ... |
	blkcnt_t i_blocks | unsigned short i_bytes | ... |
	<i_op>inode_operations *i_op |
	<i_fop>file_operations *i_fop | ...
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.05"
]

/*
  Processes deal directly with files, not superblocks, inodes, or dentries.
  Because multiple processes can open and manipulate a file at the same time, there can be multiple file objects in existence for the same file. The fie object merely represents a process's view of an open file. The object points back to the dentry(which in turn points back to the inode) that actually represents the open file.
  Similar to the dentry object, the file object does not actually correspond to any on-disk data.
*/
"file" [
label="<struct>file | ... |
	{f_u | {<fu_list>list_head fu_list | rcu_head fu_rcuhead}} |
	<f_path>path f_path |	
	<f_vfsmnt>f_vfsmnt |
	<f_dentry>f_dentry |
	<f_op>file_operations *f_op | ... |
	<f_mapping>address_space *f_mapping | ...
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.09"
]

/*
  The superblock usually corresponds to the filesystem superblock or the filesystem control block, which is stored in a special sector on disk. Filesystems that are not disk-based generate the superblock on-the-fly and store it in memory.
  A superblock object is created and initialized via the alloc_super() function. When mounted, a filesystem invokes this function, reads its superblock off of the disk, and fills in its superblock object.
*/
"super_block" [
label="<struct>super_block |
	<s_list>list_head s_list |
	<s_dev>dev_t s_dev |
	<s_blocksize>unsigned long	 s_blocksize | ...| 
	unsigned char	 s_dirt | ...|
	<s_type>file_system_type *s_type |
	<s_op>super_operations *s_op | ...|
	<s_inodes>list_head s_inodes |
	<s_anon>hlist_head s_anon |
	<s_files>list_head s_files |
	<s_dentry_lru>list_head s_dentry_lru | ... |
	<s_bdev>block_device *s_bdev |
	<s_bdi>backing_dev_info *s_bdi |
	
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.055"
]

"super_operations" [
label="<struct>super_operations |
	alloc_inode() |
	destroy_inode() |
	dirty_inode() |
	write_inode() |
	drop_inode() |
	delete_inode() |
	put_super() |
	write_super() |
	sync_fs() |
	freeze_fs() |
	unfreeze_fs() |
	statfs() |
	remount_fs() |
	clear_inode() |
	umount_begin() |
	show_options() |
	show_stats() |
	quota_read() |
	quota_write() |
	bdev_try_to_free_page()
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.045"
]

/*
  The file_system_type describes the capabilities and behavior of each filesystem.
  There is only one file_system_type per filesystem, regardless of how many instances of the filesystem are mounted on the system, or whether the filesystem is enven mounted at all.
  The get_sb() function reads the superblock from the disk and populates the  superblock object when the filesystem is loaded.
*/
"file_system_type" [
label="<struct>file_system_type |
	const char *name |
	int fs_flags |
	<get_sb>get_sb() |
	<kill_sb>kill_sb() |
	<next>file_system_type * next |
	<fs_supers>list_head fs_supers | ...
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.13"
]

"file_operations" [
label="<struct>file_operations |
	llseek() |
	read() |
	write() |
	aio_read() |
	aio_write() |
	readdir() |
	poll() |
	ioctl() |
	open()|
	mmap() |
	flush() |
	release() |
	fsync() |
	aio_fsync() |  ...
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.065"
]

"inode_operations" [
label="<struct>inode_operations |
	create() |
	link() |
	unlink() |
	symlink() |
	mkdir() |
	rmdir() |
	mknod() |
	rename() |
	readlink() |
	follow_link() |
	put_link() |
	truncate() |
	permission() |
	check_acl() |
	setattr() |
	getattr() |
	setxattr() |
	getxattr() |
	listxattr() |
	removexattr() |
	truncate_range() |
	fallocate() |
	fiemap()
"
shape = "record"
gradientangle="90"
fillcolor = "pink:green;0.039"
]

/*
	int (*d_revalidate)(struct dentry *, struct nameidata *) |
	int (*d_hash) (struct dentry *, struct qstr *) |
	int (*d_compare) (struct dentry *, struct qstr *, struct qstr *) |
	int (*d_delete)(struct dentry *) |
	void (*d_release)(struct dentry *) |
	void (*d_iput)(struct dentry *, struct inode *) |
	char *(*d_dname)(struct dentry *, char *, int)
*/
"dentry_operations" [
label="<struct>dentry_operations |
	d_revalidate() |
	d_hash() |
	d_compare() |
	d_delete() |
	d_release() |
	d_iput() |
	d_dname()
"
shape = "record"
gradientangle="90"
fillcolor = "yellow:green;0.12"
]

"task_struct":files -> "files_struct":struct
"task_struct":fs -> "fs_struct":struct
"files_struct": fdt -> "fdtable" : struct
"fdtable" : next -> "fdtable" : next [style="dashed"]
"fdtable" : fd0 -> "file" : struct
"fdtable" : fd -> "files_struct" : fd_array [style="dashed", color="red", dir=none]
"fs_struct" : root -> "path" : struct
"fs_struct" : pwd -> "path" : struct
"path" : mnt -> "vfsmount" : struct
"path" : dentry -> "dentry" : struct
"dentry" : d_op -> "dentry_operations" : struct
"dentry" : d_inode -> "inode" : struct
"dentry" : d_sb -> "super_block" : struct
"dentry" : d_alias -> "inode" : i_dentry [style="dashed", color="red", dir=none]
"inode" : i_list -> "inode" : i_list [style="dashed"]
"inode" : i_op -> "inode_operations" : struct
"inode" : i_fop -> "file_operations" : struct
"inode" : i_dentry -> "dentry" : struct
"inode" : i_sb_list -> "super_block" : struct
"file" : fu_list -> "file" : fu_list [style="dashed"]
//"file" : f_path -> "path" :struct
"file" : f_dentry -> "path" : dentry
"file" : f_vfsmnt -> "path" : mnt
"file" :f_op -> "file_operations" : struct
"file_system_type" : next -> "file_system_type" : next [style="dashed"]
"super_block" : s_type -> "file_system_type" : struct
"super_block" : s_op -> "super_operations" : struct
//"fdtable" : fd -> "fdtable" : fd0
}





References:

http://www.cnblogs.com/biyeymyhjob/archive/2012/07/27/2610619.html



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值