/*
* Name resolution.
* This is the basic name resolution function, turning a pathname into
* the final dentry. We expect 'base' to be positive and a directory.
*
* Returns 0 and nd will have valid dentry and mnt on success.
* Returns error and drops reference to input namei data on failure.
*/
//判断创建文件的路径的合法性
//根据name的算出的len长度配合 if (!name[len]) return 0; (合法的路径会在创建文件名之前跳出,不合法的名字会在之后walk_component中lookup_slow()查找之后在检查inode的时候报错该路径非法)
static int link_path_walk(const char *name, struct nameidata *nd)
{
struct path next;
int err;
while (*name=='/')
name++;
if (!*name)
return 0;
/* At this point we know we have a real path component. */
for(;;) {
struct qstr this;
long len;
int type;
err = may_lookup(nd);
if (err)
break;
len = hash_name(name, &this.hash);
this.name = name;
this.len = len;
type = LAST_NORM;
if (name[0] == '.') switch (len) {
case 2:
if (name[1] == '.') {
type = LAST_DOTDOT;
nd->flags |= LOOKUP_JUMPED;
}
break;
case 1:
type = LAST_DOT;
}
if (likely(type == LAST_NORM)) {
struct dentry *parent = nd->path.dentry;
nd->flags &= ~LOOKUP_JUMPED;
if (unlikely(parent->d_flags & DCACHE_OP_HASH)) {
err = parent->d_op->d_hash(parent, &this);
if (err < 0)
break;
}
}
nd->last = this;
nd->last_type = type;
if (!name[len])
return 0;
/*
* If it wasn't NUL, we know it was '/'. Skip that
* slash, and continue until no more slashes.
*/
do {
len++;
} while (unlikely(name[len] == '/'));
if (!name[len])
return 0;
name += len;
err = walk_component(nd, &next, LOOKUP_FOLLOW);
if (err < 0)
return err;
if (err) {
err = nested_symlink(&next, nd);
if (err)
return err;
}
if (!d_is_directory(nd->path.dentry)) {
err = -ENOTDIR;
break;
}
}
terminate_walk(nd);
return err;
}
Debug:kernel linux 3.13.1(debug创建文件夹对路径的识别)
(1)mkdir hjhsaaa
[ 421.172975] link_path_walk 1756 name = hjhsaaa and hash_name(hjhsaaa,&this.has) = 7 and this.hash = 1942604745!
(2)mkdir hjhsaaa/ccc
第一次循环:
[ 590.104017] link_path_walk 1756 name = hjhsaaa/ccc and hash_name(hjhsaaa/ccc,&this.has) = 7 and this.hash = 1942604745!
第二次循环:
[ 590.104024] link_path_walk 1756 name = ccc and hash_name(ccc,&this.has) = 3 and this.hash = 6513507!
(3)mkdir jkjkaaass/ddd/sss/aaa
[ 556.739818] link_path_walk 1756 name = jkjkaaass/ddd/sss/aaa and hash_name(jkjkaaass/ddd/sss/aaa,&this.has) = 9 and this.hash = -718654567!
阅读(2374) | 评论(0) | 转发(0) |