namei: allow nd_jump_link() to produce errors
In preparation for LOOKUP_NO_MAGICLINKS, it's necessary to add the ability for nd_jump_link() to return an error which the corresponding get_link() caller must propogate back up to the VFS. Suggested-by: Al Viro <viro@zeniv.linux.org.uk> Signed-off-by: Aleksa Sarai <cyphar@cyphar.com> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
parent
ce623f8987
commit
1bc82070fa
|
@ -859,7 +859,7 @@ static int nd_jump_root(struct nameidata *nd)
|
|||
* Helper to directly jump to a known parsed path from ->get_link,
|
||||
* caller must have taken a reference to path beforehand.
|
||||
*/
|
||||
void nd_jump_link(struct path *path)
|
||||
int nd_jump_link(struct path *path)
|
||||
{
|
||||
struct nameidata *nd = current->nameidata;
|
||||
path_put(&nd->path);
|
||||
|
@ -867,6 +867,7 @@ void nd_jump_link(struct path *path)
|
|||
nd->path = *path;
|
||||
nd->inode = nd->path.dentry->d_inode;
|
||||
nd->flags |= LOOKUP_JUMPED;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void put_link(struct nameidata *nd)
|
||||
|
|
|
@ -1626,8 +1626,7 @@ static const char *proc_pid_get_link(struct dentry *dentry,
|
|||
if (error)
|
||||
goto out;
|
||||
|
||||
nd_jump_link(&path);
|
||||
return NULL;
|
||||
error = nd_jump_link(&path);
|
||||
out:
|
||||
return ERR_PTR(error);
|
||||
}
|
||||
|
|
|
@ -51,11 +51,15 @@ static const char *proc_ns_get_link(struct dentry *dentry,
|
|||
if (!task)
|
||||
return ERR_PTR(-EACCES);
|
||||
|
||||
if (ptrace_may_access(task, PTRACE_MODE_READ_FSCREDS)) {
|
||||
error = ns_get_path(&ns_path, task, ns_ops);
|
||||
if (!error)
|
||||
nd_jump_link(&ns_path);
|
||||
}
|
||||
if (!ptrace_may_access(task, PTRACE_MODE_READ_FSCREDS))
|
||||
goto out;
|
||||
|
||||
error = ns_get_path(&ns_path, task, ns_ops);
|
||||
if (error)
|
||||
goto out;
|
||||
|
||||
error = nd_jump_link(&ns_path);
|
||||
out:
|
||||
put_task_struct(task);
|
||||
return ERR_PTR(error);
|
||||
}
|
||||
|
|
|
@ -69,7 +69,7 @@ extern int follow_up(struct path *);
|
|||
extern struct dentry *lock_rename(struct dentry *, struct dentry *);
|
||||
extern void unlock_rename(struct dentry *, struct dentry *);
|
||||
|
||||
extern void nd_jump_link(struct path *path);
|
||||
extern int __must_check nd_jump_link(struct path *path);
|
||||
|
||||
static inline void nd_terminate_link(void *name, size_t len, size_t maxlen)
|
||||
{
|
||||
|
|
|
@ -2573,16 +2573,18 @@ static const char *policy_get_link(struct dentry *dentry,
|
|||
{
|
||||
struct aa_ns *ns;
|
||||
struct path path;
|
||||
int error;
|
||||
|
||||
if (!dentry)
|
||||
return ERR_PTR(-ECHILD);
|
||||
|
||||
ns = aa_get_current_ns();
|
||||
path.mnt = mntget(aafs_mnt);
|
||||
path.dentry = dget(ns_dir(ns));
|
||||
nd_jump_link(&path);
|
||||
error = nd_jump_link(&path);
|
||||
aa_put_ns(ns);
|
||||
|
||||
return NULL;
|
||||
return ERR_PTR(error);
|
||||
}
|
||||
|
||||
static int policy_readlink(struct dentry *dentry, char __user *buffer,
|
||||
|
|
Loading…
Reference in New Issue