From fbfbe910aae6313926975156f6fdd68738b161f2 Mon Sep 17 00:00:00 2001 From: Zach Brown Date: Sun, 10 Sep 2017 15:05:23 -0700 Subject: [PATCH] scoutfs: return error from lock_name_keys xfstests generic/028 was crashing dereferencing NULL locks. It'd hit either rename trying to refresh an inode with a NULL lock or lookup trying to pass a NULL lock's end to item lookup. The addition of the lock LRU fixed a bug in lock_name_keys() where it wouldn't drop a lock when _cluster_lock() returned an error. But it always returned 0 instead of returning the error. Returning 0 without setting the lock caused the callers to deref their NULL locks. We also forcefully NULL the lock at the start of the function. It was lucky that callers had already NULLed their locks. If they hadn't they would have been following random on-stack memory and it might have been harder to debug. Signed-off-by: Zach Brown --- kmod/src/lock.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/kmod/src/lock.c b/kmod/src/lock.c index 8013c8d1..459f6c95 100644 --- a/kmod/src/lock.c +++ b/kmod/src/lock.c @@ -406,6 +406,8 @@ static int lock_name_keys(struct super_block *sb, int mode, int flags, int lkm_flags; int ret; + *ret_lock = NULL; + if (WARN_ON_ONCE(!(flags & SCOUTFS_LKF_TRYLOCK) && scoutfs_trans_held())) return -EINVAL; @@ -425,9 +427,11 @@ static int lock_name_keys(struct super_block *sb, int mode, int flags, if (ret) { dec_lock_users(lock); put_scoutfs_lock(sb, lock); - } else + } else { *ret_lock = lock; - return 0; + } + + return ret; } u64 scoutfs_lock_refresh_gen(struct scoutfs_lock *lock)