diff options
author | Al Viro <viro@ZenIV.linux.org.uk> | 2010-02-16 19:09:36 +0100 |
---|---|---|
committer | Al Viro <viro@zeniv.linux.org.uk> | 2010-02-19 09:56:42 +0100 |
commit | ac278a9c505092dd82077a2446af8f9fc0d9c095 (patch) | |
tree | 227d4ac77de3b909e70cbe10b2a1a6293037c8c0 /fs | |
parent | Orphan DECnet (diff) | |
download | linux-ac278a9c505092dd82077a2446af8f9fc0d9c095.tar.xz linux-ac278a9c505092dd82077a2446af8f9fc0d9c095.zip |
fix LOOKUP_FOLLOW on automount "symlinks"
Make sure that automount "symlinks" are followed regardless of LOOKUP_FOLLOW;
it should have no effect on them.
Cc: stable@kernel.org
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'fs')
-rw-r--r-- | fs/namei.c | 14 |
1 files changed, 12 insertions, 2 deletions
diff --git a/fs/namei.c b/fs/namei.c index d62fdc875f22..a4855af776a8 100644 --- a/fs/namei.c +++ b/fs/namei.c @@ -823,6 +823,17 @@ fail: } /* + * This is a temporary kludge to deal with "automount" symlinks; proper + * solution is to trigger them on follow_mount(), so that do_lookup() + * would DTRT. To be killed before 2.6.34-final. + */ +static inline int follow_on_final(struct inode *inode, unsigned lookup_flags) +{ + return inode && unlikely(inode->i_op->follow_link) && + ((lookup_flags & LOOKUP_FOLLOW) || S_ISDIR(inode->i_mode)); +} + +/* * 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. @@ -942,8 +953,7 @@ last_component: if (err) break; inode = next.dentry->d_inode; - if ((lookup_flags & LOOKUP_FOLLOW) - && inode && inode->i_op->follow_link) { + if (follow_on_final(inode, lookup_flags)) { err = do_follow_link(&next, nd); if (err) goto return_err; |