根据路径名查找目标节点的第一步,就是确定起始路径。这个工作就是
path_init来完成的。
path_init的主要目的就是为了确定path lookup的起始位置。当然是要确定起始位置的dentry和vfsmount。
分三种情形:
1. 从"/"开始
2. 从当前路径开始
3. 从进程某个已经打开的目录路径开始。
-
static int path_init(int dfd, const char *name, unsigned int flags, struct nameidata *nd)
-
{
-
int retval = 0;
-
int fput_needed;
-
struct file *file;
-
-
nd->last_type = LAST_ROOT; /* if there are only slashes... */
-
nd->flags = flags;
-
nd->depth = 0;
-
nd->root.mnt = NULL;
-
-
if (*name=='/') {
-
/* 从"/"开始 */
-
set_root(nd);
-
nd->path = nd->root;/* 直接使用进程的根路径 */
-
path_get(&nd->root);
-
} else if (dfd == AT_FDCWD) {
-
/* 从当前路径开始 */
-
struct fs_struct *fs = current->fs;
-
read_lock(&fs->lock);
-
nd->path = fs->pwd;/* 使用进程的当前路径 */
-
path_get(&fs->pwd);
-
read_unlock(&fs->lock);
-
} else {
-
/* 如果某目录已经被当前进程打开,则根据文件描述符fd,
-
找到file=current->files->fdt[fd]
-
file->f_path就是要找的起始路径 */
-
struct dentry *dentry;
-
-
file = fget_light(dfd, &fput_needed);
-
retval = -EBADF;
-
if (!file)
-
goto out_fail;
-
-
dentry = file->f_path.dentry;
-
-
retval = -ENOTDIR;
-
if (!S_ISDIR(dentry->d_inode->i_mode))
-
goto fput_fail;
-
-
retval = file_permission(file, MAY_EXEC);
-
if (retval)
-
goto fput_fail;
-
-
nd->path = file->f_path;/* 根据fd找到file,使用file的path */
-
path_get(&file->f_path);
-
-
fput_light(file, fput_needed);
-
}
-
return 0;
-
-
fput_fail:
-
fput_light(file, fput_needed);
-
out_fail:
-
return retval;
-
}
阅读(2463) | 评论(0) | 转发(0) |