fsnotify: pin both inode and vfsmount mark
We may fail to pin one of the marks in fsnotify_prepare_user_wait() when
dropping the srcu read lock, resulting in use after free at the next
iteration.
Solution is to store both marks in iter_info instead of just the one we'll
be sending the event for.
Reviewed-by: Amir Goldstein <amir73il@gmail.com>
Signed-off-by: Miklos Szeredi <mszeredi@redhat.com>
Fixes: 9385a84d7e
("fsnotify: Pass fsnotify_iter_info into handle_event handler")
Cc: <stable@vger.kernel.org> # v4.12
Signed-off-by: Jan Kara <jack@suse.cz>
This commit is contained in:
Родитель
24c20305c7
Коммит
0d6ec079d6
|
@ -335,6 +335,13 @@ int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is,
|
|||
struct fsnotify_mark, obj_list);
|
||||
vfsmount_group = vfsmount_mark->group;
|
||||
}
|
||||
/*
|
||||
* Need to protect both marks against freeing so that we can
|
||||
* continue iteration from this place, regardless of which mark
|
||||
* we actually happen to send an event for.
|
||||
*/
|
||||
iter_info.inode_mark = inode_mark;
|
||||
iter_info.vfsmount_mark = vfsmount_mark;
|
||||
|
||||
if (inode_group && vfsmount_group) {
|
||||
int cmp = fsnotify_compare_groups(inode_group,
|
||||
|
@ -348,9 +355,6 @@ int fsnotify(struct inode *to_tell, __u32 mask, const void *data, int data_is,
|
|||
}
|
||||
}
|
||||
|
||||
iter_info.inode_mark = inode_mark;
|
||||
iter_info.vfsmount_mark = vfsmount_mark;
|
||||
|
||||
ret = send_to_group(to_tell, inode_mark, vfsmount_mark, mask,
|
||||
data, data_is, cookie, file_name,
|
||||
&iter_info);
|
||||
|
|
Загрузка…
Ссылка в новой задаче