sys文件系统----打开过程

这个文件系统主要作用是:在用户态展示设备的信息。

4.1 文件和目录的创建

4.1.1 文件系统的初始化。

sysfs_init()

int __init sysfs_init(void)
{
sysfs_dir_cachep = kmem_cache_create("sysfs_dir_cache",
________________      sizeof(struct sysfs_dirent),
________________      0, 0, NULL, NULL);
......
err = register_filesystem(&sysfs_fs_type);
if (!err) {
____sysfs_mount = kern_mount(&sysfs_fs_type);
......
}
......
}

4.1.2 sys文件系统目录的创建。

sysfs_create_dir->create_dir->lookup_one_len

                                                  ->sysfs_make_dirent->sysfs_new_dirent(parent_sd, element) /* 创建一个新的sysfs_dirent */

                                                  ->sysfs_create-> /* 1)为目录文件创建一个inode对象,

                                                                                 2)并初始化inode对应的两个操作函数

                                                                                 inode->i_op = &sysfs_dir_inode_operations;
                                                                                 inode->i_fop = &sysfs_dir_operations;
  */

4.1.3 普通文件的创建。

sysfs_create_file->sysfs_add_file->sysfs_make_dirent /* sys文件系统到目前为止,只为文件的创建了一个sysfs_dirent;而文件系统创建文件需要为文件创建一个inode和dentry,接下来在文件打开的过程中会创建需要的inode和dentry。 */

4.2 sysfs文件的打开过程。

在VFS虚拟文件系统文件的打开过程中,实际是将文件的整个路径名层层解析,最终找到文件的过程。如果文件曾经被打开过,则在dentry cache中可能保存文件的dentry结构,如果在dentry cache中找不到文件,则调用real_lookup,通过real_lookup函数再调用文件系统相关的lookup函数。

static int do_lookup(struct nameidata *nd, struct qstr *name,
________     struct path *path)
{
____struct vfsmount *mnt = nd->mnt;
____struct dentry *dentry = __d_lookup(nd->dentry, name);
                                                             
____if (!dentry)
________goto need_lookup;
____if (dentry->d_op && dentry->d_op->d_revalidate)
________goto need_revalidate;
done:
____path->mnt = mnt;
____path->dentry = dentry;
______follow_mount(path);
____return 0;

need_lookup:
____dentry = real_lookup(nd->dentry, name, nd);
____if (IS_ERR(dentry))
________goto fail;
____goto done;

need_revalidate:
____if (dentry->d_op->d_revalidate(dentry, nd))
________goto done;
____if (d_invalidate(dentry))
________goto done;
____dput(dentry);
____goto need_lookup;

fail:
____return PTR_ERR(dentry);
}
/*                                                                   
 * This is called when everything else fails, and we actually have   
 * to go to the low-level filesystem to find out what we should do.. 
....
*/
static struct dentry * real_lookup(struct dentry * parent, struct qstr * name, struct nameidata *nd)
{
mutex_lock(&dir->i_mutex);                               
/* 再次搜索一边dentry cache是为了防止在等信号量时,其他用户已经创建 */                                                                     
result = d_lookup(parent, name);                   
if (!result) {                                      
____struct dentry * dentry = d_alloc(parent, name); 
____result = ERR_PTR(-ENOMEM);                      
____if (dentry) {                                   
________result = dir->i_op->lookup(dir, dentry, nd);
________if (result)                                 
____________dput(dentry);                           
________else                                        
____________result = dentry;                        
____}                                               
____mutex_unlock(&dir->i_mutex);                    
____return result;                                  
}
mutex_unlock(&dir->i_mutex);
......
}                                                   

对于sysfs文件系统来说,lookup函数就是sysfs_lookup.在执行具体文件系统(sys)的相关的lookup之前会创建一个dentry,通过这个entry,sysfs_lookup会找到它的父sysfs_dirent,遍历父sysfs_dirent下的各个子sysfs_dirent,直到找到对应的子sysfs_dirent.接下来就是创建对应的inode,完成real_lookup的查找工作。

以上可以理解为VFS层对文件的处理,接下来才是sys文件系统真正的打开文件的函数sys_open_file->check_perm

static int sysfs_open_file(struct inode * inode, struct file * filp)
{                                                                   
____return check_perm(inode,filp);                                  
}                                                                   

check_perm分两部分:

1)文件权限的检查。

普通文件会有attribute结构,目录文件会有kobject结构,如果目录文件的kobject提供了文件的操作函数,普通文件要赋值为kobject结构提供的操作函数,如果没有文件的操作函数则复制为子系统的操作函数指针,然后根据文件的inode->imode进行文件的权限检查。

/* if the kobject has no ktype, then we assume that it is a subsystem
 * itself, and use ops for it.                                       
 */                                                                  
if (kobj->kset && kobj->kset->ktype)                                 
____ops = kobj->kset->ktype->sysfs_ops;                              
else if (kobj->ktype)                                                
____ops = kobj->ktype->sysfs_ops;                                    
else                                                                 
____ops = &subsys_sysfs_ops;                                         

2)创建文件的私有数据结构(file->private_data)。

这是文件对象中保存文件系统特殊信息的方式。

/* No error? Great, allocate a buffer for the file, and store it
 * it in file->private_data for easy access.                    
 */                                                             
buffer = kzalloc(sizeof(struct sysfs_buffer), GFP_KERNEL);      
if (buffer) {                                                   
____init_MUTEX(&buffer->sem);                                   
____buffer->needs_read_fill = 1;                                
____buffer->ops = ops;                                          
____file->private_data = buffer;                                
}                                                     

 

当你提到将C源文件(通常扩展名为.c)转换成sys文件,这听起来像是你在谈论嵌入式系统或者针对特定目标平台的开发。在许多嵌入式环境中,特别是那些使用GCC编译器的情况,源文件经过编译、链接等过程会生成可执行的目标文件(经常是.obj或者.elf),而sys文件并不是标准的生成物。 通常,C源文件通过下面的过程生成sys文件: 1. **编译** (gcc -c): 首先,你需要使用GCC编译器对C源文件进行预处理(cpp)、编译(cc1)和汇编(assembler)操作,生成一个中间的.o文件(对象文件)。 ```bash gcc -c your_c_file.c ``` 2. **链接** (ld): 然后,将对象文件和其他依赖项(如库文件)链接在一起,形成最终的可执行文件(通常是一个.elf文件)。 ```bash gcc -o your_executable your_object_file.o -lyour_library ``` 这里的-l选项是连接指定的库。 3. **针对特定平台优化**: 如果你要生成sys文件,那可能是某种特定环境下的目标文件格式,比如某些微控制器的固件或者RTOS(实时操作系统)。这种情况下,你可能需要使用专门针对该平台的工具链,如Keil uVision或者IAR Embedded Workbench等,它们有专门的命令行工具生成特定的sys或者其他平台相关的文件。 然而,"sys文件"这个词并不常见于常规的软件开发流程,它更像是特定项目或工具集中的术语。如果你能提供更多的上下文信息,我可以给出更准确的答案。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值