Merge branch 'master' into for-linus-merged
Alex Elder [Tue, 11 Jan 2011 03:35:55 +0000 (21:35 -0600)]
This merge pulls the XFS master branch into the latest Linus master.
This results in a merge conflict whose best fix is not obvious.
I manually fixed the conflict, in "fs/xfs/xfs_iget.c".

Dave Chinner had done work that resulted in RCU freeing of inodes
separate from what Nick Piggin had done, and their results differed
slightly in xfs_inode_free().  The fix updates Nick's call_rcu()
with the use of VFS_I(), while incorporating needed updates to some
XFS inode fields implemented in Dave's series.  Dave's RCU callback
function has also been removed.

Signed-off-by: Alex Elder <aelder@sgi.com>

1  2 
fs/xfs/xfs_iget.c

@@@ -145,7 -157,17 +156,18 @@@ xfs_inode_free
        ASSERT(!spin_is_locked(&ip->i_flags_lock));
        ASSERT(completion_done(&ip->i_flush));
  
-       call_rcu(&ip->i_vnode.i_rcu, xfs_inode_free_callback);
+       /*
+        * Because we use RCU freeing we need to ensure the inode always
+        * appears to be reclaimed with an invalid inode number when in the
+        * free state. The ip->i_flags_lock provides the barrier against lookup
+        * races.
+        */
+       spin_lock(&ip->i_flags_lock);
+       ip->i_flags = XFS_IRECLAIM;
+       ip->i_ino = 0;
+       spin_unlock(&ip->i_flags_lock);
 -      call_rcu((struct rcu_head *)&VFS_I(ip)->i_dentry, __xfs_inode_free);
++
++      call_rcu(&VFS_I(ip)->i_rcu, xfs_inode_free_callback);
  }
  
  /*