diff options
Diffstat (limited to 'fs/namei.c')
| -rw-r--r-- | fs/namei.c | 21 |
1 files changed, 15 insertions, 6 deletions
diff --git a/fs/namei.c b/fs/namei.c index bf0f66f0e9b9..cf16b6822dd3 100644 --- a/fs/namei.c +++ b/fs/namei.c @@ -830,11 +830,9 @@ static inline bool legitimize_path(struct nameidata *nd, static bool legitimize_links(struct nameidata *nd) { int i; - if (unlikely(nd->flags & LOOKUP_CACHED)) { - drop_links(nd); - nd->depth = 0; - return false; - } + + VFS_BUG_ON(nd->flags & LOOKUP_CACHED); + for (i = 0; i < nd->depth; i++) { struct saved *last = nd->stack + i; if (unlikely(!legitimize_path(nd, &last->link, last->seq))) { @@ -883,6 +881,11 @@ static bool try_to_unlazy(struct nameidata *nd) BUG_ON(!(nd->flags & LOOKUP_RCU)); + if (unlikely(nd->flags & LOOKUP_CACHED)) { + drop_links(nd); + nd->depth = 0; + goto out1; + } if (unlikely(nd->depth && !legitimize_links(nd))) goto out1; if (unlikely(!legitimize_path(nd, &nd->path, nd->seq))) @@ -918,6 +921,11 @@ static bool try_to_unlazy_next(struct nameidata *nd, struct dentry *dentry) int res; BUG_ON(!(nd->flags & LOOKUP_RCU)); + if (unlikely(nd->flags & LOOKUP_CACHED)) { + drop_links(nd); + nd->depth = 0; + goto out2; + } if (unlikely(nd->depth && !legitimize_links(nd))) goto out2; res = __legitimize_mnt(nd->path.mnt, nd->m_seq); @@ -2836,10 +2844,11 @@ static int filename_parentat(int dfd, struct filename *name, } /** - * start_dirop - begin a create or remove dirop, performing locking and lookup + * __start_dirop - begin a create or remove dirop, performing locking and lookup * @parent: the dentry of the parent in which the operation will occur * @name: a qstr holding the name within that parent * @lookup_flags: intent and other lookup flags. + * @state: task state bitmask * * The lookup is performed and necessary locks are taken so that, on success, * the returned dentry can be operated on safely. |
