aboutsummaryrefslogtreecommitdiffstats
path: root/fs/namei.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/namei.c')
-rw-r--r--fs/namei.c22
1 files changed, 20 insertions, 2 deletions
diff --git a/fs/namei.c b/fs/namei.c
index 5abab9176903..6b29a51bef5d 100644
--- a/fs/namei.c
+++ b/fs/namei.c
@@ -1814,9 +1814,27 @@ static int do_path_lookup(int dfd, const char *name,
1814 return retval; 1814 return retval;
1815} 1815}
1816 1816
1817int kern_path_parent(const char *name, struct nameidata *nd) 1817/* does lookup, returns the object with parent locked */
1818struct dentry *kern_path_locked(const char *name, struct path *path)
1818{ 1819{
1819 return do_path_lookup(AT_FDCWD, name, LOOKUP_PARENT, nd); 1820 struct nameidata nd;
1821 struct dentry *d;
1822 int err = do_path_lookup(AT_FDCWD, name, LOOKUP_PARENT, &nd);
1823 if (err)
1824 return ERR_PTR(err);
1825 if (nd.last_type != LAST_NORM) {
1826 path_put(&nd.path);
1827 return ERR_PTR(-EINVAL);
1828 }
1829 mutex_lock_nested(&nd.path.dentry->d_inode->i_mutex, I_MUTEX_PARENT);
1830 d = lookup_one_len(nd.last.name, nd.path.dentry, nd.last.len);
1831 if (IS_ERR(d)) {
1832 mutex_unlock(&nd.path.dentry->d_inode->i_mutex);
1833 path_put(&nd.path);
1834 return d;
1835 }
1836 *path = nd.path;
1837 return d;
1820} 1838}
1821 1839
1822int kern_path(const char *name, unsigned int flags, struct path *path) 1840int kern_path(const char *name, unsigned int flags, struct path *path)