Probleam reading fdinfo symlinks after 30a08bf2d31d275c6fc71dd1811342777e95c831
Subsystems (2)
Hi Linus,
just tried 3.5-rc1 out and found that with commit 30a08bf2d31d275c6fc71dd1811342777e95c831 the reading of fdinfo files returns "Too many levels of symbolic links" error.
| [root@neptune~]# cat /proc/pidof crond/fdinfo/0 | cat: /proc/1417/fdinfo/0: Too many levels of symbolic links
so I reverted it manually and now it works as expected
| [root@neptune ~]# cat /proc/`pidof crond`/fdinfo/0 | pos: 0 | flags: 0100002
I suspect this is unintentional behaviour of the commit.
Quoted 5 lines · Cyrill Gorcunov
just tried 3.5-rc1 out and found that with commit
30a08bf2d31d275c6fc71dd1811342777e95c831the reading of fdinfo files returns "Too many levels of symbolic links" error.
Ugh. The fdinfo files aren't symlinks at all, and share the revalidate function.
My bad. The fix isn't pretty, but still better than reverting things. This should fix it.
Linus
fs/proc/base.c | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-)
fs/proc/base.c +10 -7
@@ -1803,7 +1803,7 @@ static int tid_fd_revalidate(struct dentry *dentry, struct nameidata *nd)rcu_read_lock (); file =fcheck_files (files, fd);if (file) { -unsigned i_mode, f_mode = file->f_mode; +unsigned f_mode = file->f_mode;rcu_read_unlock ();put_files_struct (files);
@@ -1819,12 +1819,14 @@ static int tid_fd_revalidate(struct dentry *dentry, struct nameidata *nd) inode->i_gid =GLOBAL_ROOT_GID ; } - i_mode =S_IFLNK ; -if (f_mode &FMODE_READ ) - i_mode |=S_IRUSR |S_IXUSR ; -if (f_mode &FMODE_WRITE ) - i_mode |=S_IWUSR |S_IXUSR ; - inode->i_mode = i_mode; +if (S_ISLNK (inode->i_mode)) { +unsigned i_mode =S_IFLNK ; +if (f_mode &FMODE_READ ) + i_mode |=S_IRUSR |S_IXUSR ; +if (f_mode &FMODE_WRITE ) + i_mode |=S_IWUSR |S_IXUSR ; + inode->i_mode = i_mode; + }security_task_to_inode (task, inode);put_task_struct (task);
@@ -1859,6 +1861,7 @@ static struct dentry *proc_fd_instantiate(struct inode *dir, ei =PROC_I (inode); ei->fd = fd; + inode->i_mode =S_IFLNK ; inode->i_op = &proc_pid_link_inode_operations; inode->i_size =64 ; ei->op.proc_get_link = proc_fd_link;
Cyrill Gorcunov
Tested-byQuoted 11 lines · Linus Torvalds
Quoted 5 lines · Cyrill Gorcunov
just tried 3.5-rc1 out and found that with commit
30a08bf2d31d275c6fc71dd1811342777e95c831the reading of fdinfo files returns "Too many levels of symbolic links" error.Ugh. The fdinfo files aren't symlinks at all, and share the revalidate function.
My bad. The fix isn't pretty, but still better than reverting things. This should fix it.
Thanks Linus! This patch fixed it.