[XFS] Prevent deadlock when flushing inodes on unmount
authorDavid Chinner <dgc@sgi.com>
Mon, 18 Jun 2007 06:50:17 +0000 (16:50 +1000)
committerTim Shimmin <tes@chook.melbourne.sgi.com>
Sat, 14 Jul 2007 05:33:38 +0000 (15:33 +1000)
commit641c56fbfeae85d5ec87fee90a752f7b7224f236
treec626d0f48ef54031f3af502e75308c9087e4592f
parent0164af51cedf46e1d58fd53854373f544150c597
[XFS] Prevent deadlock when flushing inodes on unmount

When we are unmounting the filesystem, we flush all the inodes to disk.
Unfortunately, if we have an inode cluster that has just been freed and
marked stale sitting in an incore log buffer (i.e. hasn't been flushed to
disk), it will be holding all the flush locks on the inodes in that
cluster.

xfs_iflush_all() which is called during unmount walks all the inodes
trying to reclaim them, and it doing so calls xfs_finish_reclaim() on each
inode. If the inode is dirty, if grabs the flush lock and flushes it.
Unfortunately, find dirty inodes that already have their flush lock held
and so we sleep.

At this point in the unmount process, we are running single-threaded.
There is nothing more that can push on the log to force the transaction
holding the inode flush locks to disk and hence we deadlock.

The fix is to issue a log force before flushing the inodes on unmount so
that all the flush locks will be released before we start flushing the
inodes.

SGI-PV: 964538
SGI-Modid: xfs-linux-melb:xfs-kern:28862a

Signed-off-by: David Chinner <dgc@sgi.com>
Signed-off-by: Tim Shimmin <tes@sgi.com>
fs/xfs/xfs_mount.c