xfs
[Top] [All Lists]

Re: [PATCH 2/2] Fix i_state of inode is changed after the inode is freed

To: Masayuki Saito <m-saito@xxxxxxxxxxxxxx>, David Chinner <dgc@xxxxxxx>
Subject: Re: [PATCH 2/2] Fix i_state of inode is changed after the inode is freed [try #2]
From: Nathan Scott <nathans@xxxxxxx>
Date: Thu, 24 Aug 2006 17:16:53 +1000
Cc: xfs@xxxxxxxxxxx, linux-kernel@xxxxxxxxxxxxxxx
In-reply-to: <20060823201445m-saito@xxxxxxxxxxxxxxxxxxxxxxx>; from m-saito@xxxxxxxxxxxxxx on Wed, Aug 23, 2006 at 08:14:45PM +0900
References: <20060823201445m-saito@xxxxxxxxxxxxxxxxxxxxxxx>
Sender: xfs-bounce@xxxxxxxxxxx
User-agent: Mutt/1.2.5i
On Wed, Aug 23, 2006 at 08:14:45PM +0900, Masayuki Saito wrote:
> Fix i_state of the inode is changed after the inode is freed.
> 
> Signed-off-by: Masayuki Saito <m-saito@xxxxxxxxxxxxxx>
> Signed-off-by: ASANO Masahiro <masano@xxxxxxxxxxxxxx>

This version is producing a gcc warning...

fs/xfs/xfs_inode.c: In function 'xfs_iunpin':
fs/xfs/xfs_inode.c:2765: warning: 'inode' may be used uninitialized in this 
function

Which doesn't look correct due to your need_iput guard, but perhaps
we should do this instead...

cheers.

-- 
Nathan


Fix i_state of the inode is changed after the inode is freed.

Signed-off-by: Masayuki Saito <m-saito@xxxxxxxxxxxxxx>
Signed-off-by: ASANO Masahiro <masano@xxxxxxxxxxxxxx>
---

Index: xfs-linux/xfs_inode.c
===================================================================
--- xfs-linux.orig/xfs_inode.c  2006-08-24 17:02:36.896740000 +1000
+++ xfs-linux/xfs_inode.c       2006-08-24 17:09:29.430521750 +1000
@@ -2761,19 +2761,29 @@ xfs_iunpin(
                 * call as the inode reclaim may be blocked waiting for
                 * the inode to become unpinned.
                 */
+               struct inode *inode = NULL;
+
+               spin_lock(&ip->i_flags_lock);
                if (!(ip->i_flags & (XFS_IRECLAIM|XFS_IRECLAIMABLE))) {
                        bhv_vnode_t     *vp = XFS_ITOV_NULL(ip);
 
                        /* make sync come back and flush this inode */
                        if (vp) {
-                               struct inode    *inode = vn_to_inode(vp);
+                               inode = vn_to_inode(vp);
 
                                if (!(inode->i_state &
-                                               (I_NEW|I_FREEING|I_CLEAR)))
-                                       mark_inode_dirty_sync(inode);
+                                               (I_NEW|I_FREEING|I_CLEAR))) {
+                                       inode = igrab(inode);
+                                       if (inode)
+                                               mark_inode_dirty_sync(inode);
+                               } else
+                                       inode = NULL;
                        }
                }
+               spin_unlock(&ip->i_flags_lock);
                wake_up(&ip->i_ipin_wait);
+               if (inode)
+                       iput(inode);
        }
 }
 


<Prev in Thread] Current Thread [Next in Thread>