From: Fan Yong Date: Sat, 10 Aug 2013 07:12:42 +0000 (+0800) Subject: LU-3706 scrub: fix mutex leak in osd_obj_map_recover() X-Git-Tag: 2.4.93~45 X-Git-Url: https://git.whamcloud.com/?p=fs%2Flustre-release.git;a=commitdiff_plain;h=0cd76523b7da56efc8695331826fc0e86bce8b0d LU-3706 scrub: fix mutex leak in osd_obj_map_recover() We forget to release inode::i_mutex on the /O// when meet OI mapping conflict in osd_obj_map_recover() to recover objects from the /lost+found to their original places. Such mutex leak will cause the OI scrub thread or other threads to be hung when access /O// next time. Test-Parameters: testlist=sanity-scrub Signed-off-by: Fan Yong Change-Id: Idc3b99aea5591f546a6d33e5d1fe015a2aac0167 Reviewed-on: http://review.whamcloud.com/7534 Reviewed-by: Bobi Jam Tested-by: Hudson Tested-by: Maloo Reviewed-by: Niu Yawei Reviewed-by: Oleg Drokin --- diff --git a/lustre/osd-ldiskfs/osd_compat.c b/lustre/osd-ldiskfs/osd_compat.c index f86da33..2dbd4e4 100644 --- a/lustre/osd-ldiskfs/osd_compat.c +++ b/lustre/osd-ldiskfs/osd_compat.c @@ -1121,11 +1121,16 @@ int osd_obj_map_recover(struct osd_thread_info *info, * So keep it there before we have suitable solution. */ brelse(bh); + mutex_unlock(&dir->i_mutex); + mutex_unlock(&src_parent->i_mutex); + + rc = -EEXIST; /* If the src object has never been modified, then remove it. */ if (inode->i_size == 0 && inode->i_mode & S_ISUID && inode->i_mode & S_ISGID) - vfs_unlink(src_parent, src_child); - GOTO(unlock_src, rc = 0); + rc = vfs_unlink(src_parent, src_child); + ldiskfs_journal_stop(jh); + RETURN(rc); } bh = osd_ldiskfs_find_entry(src_parent, src_child, &de, NULL); @@ -1143,8 +1148,6 @@ int osd_obj_map_recover(struct osd_thread_info *info, unlock: mutex_unlock(&dir->i_mutex); - -unlock_src: mutex_unlock(&src_parent->i_mutex); ldiskfs_journal_stop(jh); return rc; diff --git a/lustre/osd-ldiskfs/osd_scrub.c b/lustre/osd-ldiskfs/osd_scrub.c index 669cd95..06363da 100644 --- a/lustre/osd-ldiskfs/osd_scrub.c +++ b/lustre/osd-ldiskfs/osd_scrub.c @@ -484,7 +484,7 @@ osd_scrub_convert_ff(struct osd_thread_info *info, struct osd_device *dev, rc1 = __osd_xattr_set(info, inode, XATTR_NAME_FID, ff, size, XATTR_CREATE); - if (rc1 != 0 && rc != 0) + if (rc1 != 0 && rc == 0) rc = rc1; }