kill-the-BKL/reiserfs: lock only once in reiserfs_truncate_file
commit22c963addcf426bef97a43f6e601f985f8082ed5
authorFrederic Weisbecker <fweisbec@gmail.com>
Tue, 14 Apr 2009 03:34:24 +0000 (14 05:34 +0200)
committerFrederic Weisbecker <fweisbec@gmail.com>
Mon, 14 Sep 2009 05:18:03 +0000 (14 07:18 +0200)
treef71ae95fd1eee899c446ebb03a3cc02fe24daf3c
parentdaf88c898312a22b5385655bc6e0b064eaa2efba
kill-the-BKL/reiserfs: lock only once in reiserfs_truncate_file

Impact: fix a deadlock

reiserfs_truncate_file() can be called from multiple context where
the write lock can be already hold or not.

This function also acquire (possibly recursively) the write
lock. Subsequent releases before sleeping will not actually release
the lock because we may be in more than one lock depth degree.

A typical case is:

reiserfs_file_release {
acquire_the_lock()
reiserfs_truncate_file()
reacquire_the_lock()
journal_begin() {
do_journal_begin_r() {
reiserfs_wait_on_write_block() {
/*
 * Not released because still one
 * depth owned
 */
release_lock()
wait_for_event()

At this stage the event never happen because the one which provides
it needs the write lock.

We use reiserfs_write_lock_once() here to ensure that we don't acquire the
write lock recursively.

Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Alessio Igor Bogani <abogani@texware.it>
Cc: Jeff Mahoney <jeffm@suse.com>
Cc: Alexander Beregalov <a.beregalov@gmail.com>
Cc: Chris Mason <chris.mason@oracle.com>
LKML-Reference: <1239680065-25013-3-git-send-email-fweisbec@gmail.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
fs/reiserfs/inode.c