aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/notify/fanotify/fanotify_user.c36
1 files changed, 16 insertions, 20 deletions
diff --git a/fs/notify/fanotify/fanotify_user.c b/fs/notify/fanotify/fanotify_user.c
index db7467782e8c..7d7c13872852 100644
--- a/fs/notify/fanotify/fanotify_user.c
+++ b/fs/notify/fanotify/fanotify_user.c
@@ -358,8 +358,8 @@ static __u32 fanotify_mark_add_to_mask(struct fsnotify_mark *fsn_mark, __u32 mas
358 return mask & ~oldmask; 358 return mask & ~oldmask;
359} 359}
360 360
361static struct fsnotify_mark *fanotify_add_vfsmount_mark(struct fsnotify_group *group, 361static int fanotify_add_vfsmount_mark(struct fsnotify_group *group,
362 struct vfsmount *mnt, __u32 mask) 362 struct vfsmount *mnt, __u32 mask)
363{ 363{
364 struct fsnotify_mark *fsn_mark; 364 struct fsnotify_mark *fsn_mark;
365 __u32 added; 365 __u32 added;
@@ -370,27 +370,28 @@ static struct fsnotify_mark *fanotify_add_vfsmount_mark(struct fsnotify_group *g
370 370
371 fsn_mark = kmem_cache_alloc(fanotify_mark_cache, GFP_KERNEL); 371 fsn_mark = kmem_cache_alloc(fanotify_mark_cache, GFP_KERNEL);
372 if (!fsn_mark) 372 if (!fsn_mark)
373 return ERR_PTR(-ENOMEM); 373 return -ENOMEM;
374 374
375 fsnotify_init_mark(fsn_mark, fanotify_free_mark); 375 fsnotify_init_mark(fsn_mark, fanotify_free_mark);
376 ret = fsnotify_add_mark(fsn_mark, group, NULL, mnt, 0); 376 ret = fsnotify_add_mark(fsn_mark, group, NULL, mnt, 0);
377 if (ret) { 377 if (ret) {
378 fanotify_free_mark(fsn_mark); 378 fanotify_free_mark(fsn_mark);
379 return ERR_PTR(ret); 379 return ret;
380 } 380 }
381 } 381 }
382 added = fanotify_mark_add_to_mask(fsn_mark, mask); 382 added = fanotify_mark_add_to_mask(fsn_mark, mask);
383 fsnotify_put_mark(fsn_mark);
383 if (added) { 384 if (added) {
384 if (added & ~group->mask) 385 if (added & ~group->mask)
385 fsnotify_recalc_group_mask(group); 386 fsnotify_recalc_group_mask(group);
386 if (added & ~mnt->mnt_fsnotify_mask) 387 if (added & ~mnt->mnt_fsnotify_mask)
387 fsnotify_recalc_vfsmount_mask(mnt); 388 fsnotify_recalc_vfsmount_mask(mnt);
388 } 389 }
389 return fsn_mark; 390 return 0;
390} 391}
391 392
392static struct fsnotify_mark *fanotify_add_inode_mark(struct fsnotify_group *group, 393static int fanotify_add_inode_mark(struct fsnotify_group *group,
393 struct inode *inode, __u32 mask) 394 struct inode *inode, __u32 mask)
394{ 395{
395 struct fsnotify_mark *fsn_mark; 396 struct fsnotify_mark *fsn_mark;
396 __u32 added; 397 __u32 added;
@@ -403,29 +404,30 @@ static struct fsnotify_mark *fanotify_add_inode_mark(struct fsnotify_group *grou
403 404
404 fsn_mark = kmem_cache_alloc(fanotify_mark_cache, GFP_KERNEL); 405 fsn_mark = kmem_cache_alloc(fanotify_mark_cache, GFP_KERNEL);
405 if (!fsn_mark) 406 if (!fsn_mark)
406 return ERR_PTR(-ENOMEM); 407 return -ENOMEM;
407 408
408 fsnotify_init_mark(fsn_mark, fanotify_free_mark); 409 fsnotify_init_mark(fsn_mark, fanotify_free_mark);
409 ret = fsnotify_add_mark(fsn_mark, group, inode, NULL, 0); 410 ret = fsnotify_add_mark(fsn_mark, group, inode, NULL, 0);
410 if (ret) { 411 if (ret) {
411 fanotify_free_mark(fsn_mark); 412 fanotify_free_mark(fsn_mark);
412 return ERR_PTR(ret); 413 return ret;
413 } 414 }
414 } 415 }
415 added = fanotify_mark_add_to_mask(fsn_mark, mask); 416 added = fanotify_mark_add_to_mask(fsn_mark, mask);
417 fsnotify_put_mark(fsn_mark);
416 if (added) { 418 if (added) {
417 if (added & ~group->mask) 419 if (added & ~group->mask)
418 fsnotify_recalc_group_mask(group); 420 fsnotify_recalc_group_mask(group);
419 if (added & ~inode->i_fsnotify_mask) 421 if (added & ~inode->i_fsnotify_mask)
420 fsnotify_recalc_inode_mask(inode); 422 fsnotify_recalc_inode_mask(inode);
421 } 423 }
422 return fsn_mark; 424 return 0;
423} 425}
424 426
425static int fanotify_add_mark(struct fsnotify_group *group, struct inode *inode, 427static int fanotify_add_mark(struct fsnotify_group *group, struct inode *inode,
426 struct vfsmount *mnt, __u32 mask) 428 struct vfsmount *mnt, __u32 mask)
427{ 429{
428 struct fsnotify_mark *fsn_mark; 430 int ret;
429 431
430 pr_debug("%s: group=%p inode=%p mnt=%p mask=%x\n", 432 pr_debug("%s: group=%p inode=%p mnt=%p mask=%x\n",
431 __func__, group, inode, mnt, mask); 433 __func__, group, inode, mnt, mask);
@@ -434,19 +436,13 @@ static int fanotify_add_mark(struct fsnotify_group *group, struct inode *inode,
434 BUG_ON(!inode && !mnt); 436 BUG_ON(!inode && !mnt);
435 437
436 if (inode) 438 if (inode)
437 fsn_mark = fanotify_add_inode_mark(group, inode, mask); 439 ret = fanotify_add_inode_mark(group, inode, mask);
438 else if (mnt) 440 else if (mnt)
439 fsn_mark = fanotify_add_vfsmount_mark(group, mnt, mask); 441 ret = fanotify_add_vfsmount_mark(group, mnt, mask);
440 else 442 else
441 BUG(); 443 BUG();
442 444
443 if (IS_ERR(fsn_mark)) 445 return ret;
444 goto out;
445
446 /* match the init or the find.... */
447 fsnotify_put_mark(fsn_mark);
448out:
449 return PTR_ERR(fsn_mark);
450} 446}
451 447
452static bool fanotify_mark_validate_input(int flags, 448static bool fanotify_mark_validate_input(int flags,