diff options
author | Frederic Weisbecker <fweisbec@gmail.com> | 2012-01-10 18:11:09 -0500 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2012-01-10 19:30:53 -0500 |
commit | 37c69b98d0dca54d9eb72226bbf2e211aaaf126e (patch) | |
tree | 249277ba7072933b760164bfac713140c0438745 /fs/reiserfs | |
parent | f32485be8397ad811312bc055d2e2a5906bc7576 (diff) |
reiserfs: don't lock journal_init()
journal_init() doesn't need the lock since no operation on the filesystem
is involved there. journal_read() and get_list_bitmap() have yet to be
reviewed carefully though before removing the lock there. Just keep the
it around these two calls for safety.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Al Viro <viro@zeniv.linux.org.uk>
Cc: Christoph Hellwig <hch@lst.de>
Cc: Jeff Mahoney <jeffm@suse.com>
Cc: Jan Kara <jack@suse.cz>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'fs/reiserfs')
-rw-r--r-- | fs/reiserfs/journal.c | 53 | ||||
-rw-r--r-- | fs/reiserfs/super.c | 21 |
2 files changed, 31 insertions, 43 deletions
diff --git a/fs/reiserfs/journal.c b/fs/reiserfs/journal.c index cce8e8710df2..c3cf54fd4de3 100644 --- a/fs/reiserfs/journal.c +++ b/fs/reiserfs/journal.c | |||
@@ -2678,16 +2678,10 @@ int journal_init(struct super_block *sb, const char *j_dev_name, | |||
2678 | char b[BDEVNAME_SIZE]; | 2678 | char b[BDEVNAME_SIZE]; |
2679 | int ret; | 2679 | int ret; |
2680 | 2680 | ||
2681 | /* | ||
2682 | * Unlock here to avoid various RECLAIM-FS-ON <-> IN-RECLAIM-FS | ||
2683 | * dependency inversion warnings. | ||
2684 | */ | ||
2685 | reiserfs_write_unlock(sb); | ||
2686 | journal = SB_JOURNAL(sb) = vzalloc(sizeof(struct reiserfs_journal)); | 2681 | journal = SB_JOURNAL(sb) = vzalloc(sizeof(struct reiserfs_journal)); |
2687 | if (!journal) { | 2682 | if (!journal) { |
2688 | reiserfs_warning(sb, "journal-1256", | 2683 | reiserfs_warning(sb, "journal-1256", |
2689 | "unable to get memory for journal structure"); | 2684 | "unable to get memory for journal structure"); |
2690 | reiserfs_write_lock(sb); | ||
2691 | return 1; | 2685 | return 1; |
2692 | } | 2686 | } |
2693 | INIT_LIST_HEAD(&journal->j_bitmap_nodes); | 2687 | INIT_LIST_HEAD(&journal->j_bitmap_nodes); |
@@ -2695,10 +2689,8 @@ int journal_init(struct super_block *sb, const char *j_dev_name, | |||
2695 | INIT_LIST_HEAD(&journal->j_working_list); | 2689 | INIT_LIST_HEAD(&journal->j_working_list); |
2696 | INIT_LIST_HEAD(&journal->j_journal_list); | 2690 | INIT_LIST_HEAD(&journal->j_journal_list); |
2697 | journal->j_persistent_trans = 0; | 2691 | journal->j_persistent_trans = 0; |
2698 | ret = reiserfs_allocate_list_bitmaps(sb, journal->j_list_bitmap, | 2692 | if (reiserfs_allocate_list_bitmaps(sb, journal->j_list_bitmap, |
2699 | reiserfs_bmap_count(sb)); | 2693 | reiserfs_bmap_count(sb))) |
2700 | reiserfs_write_lock(sb); | ||
2701 | if (ret) | ||
2702 | goto free_and_return; | 2694 | goto free_and_return; |
2703 | 2695 | ||
2704 | allocate_bitmap_nodes(sb); | 2696 | allocate_bitmap_nodes(sb); |
@@ -2727,27 +2719,11 @@ int journal_init(struct super_block *sb, const char *j_dev_name, | |||
2727 | goto free_and_return; | 2719 | goto free_and_return; |
2728 | } | 2720 | } |
2729 | 2721 | ||
2730 | /* | ||
2731 | * We need to unlock here to avoid creating the following | ||
2732 | * dependency: | ||
2733 | * reiserfs_lock -> sysfs_mutex | ||
2734 | * Because the reiserfs mmap path creates the following dependency: | ||
2735 | * mm->mmap -> reiserfs_lock, hence we have | ||
2736 | * mm->mmap -> reiserfs_lock ->sysfs_mutex | ||
2737 | * This would ends up in a circular dependency with sysfs readdir path | ||
2738 | * which does sysfs_mutex -> mm->mmap_sem | ||
2739 | * This is fine because the reiserfs lock is useless in mount path, | ||
2740 | * at least until we call journal_begin. We keep it for paranoid | ||
2741 | * reasons. | ||
2742 | */ | ||
2743 | reiserfs_write_unlock(sb); | ||
2744 | if (journal_init_dev(sb, journal, j_dev_name) != 0) { | 2722 | if (journal_init_dev(sb, journal, j_dev_name) != 0) { |
2745 | reiserfs_write_lock(sb); | ||
2746 | reiserfs_warning(sb, "sh-462", | 2723 | reiserfs_warning(sb, "sh-462", |
2747 | "unable to initialize jornal device"); | 2724 | "unable to initialize jornal device"); |
2748 | goto free_and_return; | 2725 | goto free_and_return; |
2749 | } | 2726 | } |
2750 | reiserfs_write_lock(sb); | ||
2751 | 2727 | ||
2752 | rs = SB_DISK_SUPER_BLOCK(sb); | 2728 | rs = SB_DISK_SUPER_BLOCK(sb); |
2753 | 2729 | ||
@@ -2829,9 +2805,7 @@ int journal_init(struct super_block *sb, const char *j_dev_name, | |||
2829 | journal->j_mount_id = 10; | 2805 | journal->j_mount_id = 10; |
2830 | journal->j_state = 0; | 2806 | journal->j_state = 0; |
2831 | atomic_set(&(journal->j_jlock), 0); | 2807 | atomic_set(&(journal->j_jlock), 0); |
2832 | reiserfs_write_unlock(sb); | ||
2833 | journal->j_cnode_free_list = allocate_cnodes(num_cnodes); | 2808 | journal->j_cnode_free_list = allocate_cnodes(num_cnodes); |
2834 | reiserfs_write_lock(sb); | ||
2835 | journal->j_cnode_free_orig = journal->j_cnode_free_list; | 2809 | journal->j_cnode_free_orig = journal->j_cnode_free_list; |
2836 | journal->j_cnode_free = journal->j_cnode_free_list ? num_cnodes : 0; | 2810 | journal->j_cnode_free = journal->j_cnode_free_list ? num_cnodes : 0; |
2837 | journal->j_cnode_used = 0; | 2811 | journal->j_cnode_used = 0; |
@@ -2848,24 +2822,37 @@ int journal_init(struct super_block *sb, const char *j_dev_name, | |||
2848 | 2822 | ||
2849 | init_journal_hash(sb); | 2823 | init_journal_hash(sb); |
2850 | jl = journal->j_current_jl; | 2824 | jl = journal->j_current_jl; |
2825 | |||
2826 | /* | ||
2827 | * get_list_bitmap() may call flush_commit_list() which | ||
2828 | * requires the lock. Calling flush_commit_list() shouldn't happen | ||
2829 | * this early but I like to be paranoid. | ||
2830 | */ | ||
2831 | reiserfs_write_lock(sb); | ||
2851 | jl->j_list_bitmap = get_list_bitmap(sb, jl); | 2832 | jl->j_list_bitmap = get_list_bitmap(sb, jl); |
2833 | reiserfs_write_unlock(sb); | ||
2852 | if (!jl->j_list_bitmap) { | 2834 | if (!jl->j_list_bitmap) { |
2853 | reiserfs_warning(sb, "journal-2005", | 2835 | reiserfs_warning(sb, "journal-2005", |
2854 | "get_list_bitmap failed for journal list 0"); | 2836 | "get_list_bitmap failed for journal list 0"); |
2855 | goto free_and_return; | 2837 | goto free_and_return; |
2856 | } | 2838 | } |
2857 | if (journal_read(sb) < 0) { | 2839 | |
2840 | /* | ||
2841 | * Journal_read needs to be inspected in order to push down | ||
2842 | * the lock further inside (or even remove it). | ||
2843 | */ | ||
2844 | reiserfs_write_lock(sb); | ||
2845 | ret = journal_read(sb); | ||
2846 | reiserfs_write_unlock(sb); | ||
2847 | if (ret < 0) { | ||
2858 | reiserfs_warning(sb, "reiserfs-2006", | 2848 | reiserfs_warning(sb, "reiserfs-2006", |
2859 | "Replay Failure, unable to mount"); | 2849 | "Replay Failure, unable to mount"); |
2860 | goto free_and_return; | 2850 | goto free_and_return; |
2861 | } | 2851 | } |
2862 | 2852 | ||
2863 | reiserfs_mounted_fs_count++; | 2853 | reiserfs_mounted_fs_count++; |
2864 | if (reiserfs_mounted_fs_count <= 1) { | 2854 | if (reiserfs_mounted_fs_count <= 1) |
2865 | reiserfs_write_unlock(sb); | ||
2866 | commit_wq = alloc_workqueue("reiserfs", WQ_MEM_RECLAIM, 0); | 2855 | commit_wq = alloc_workqueue("reiserfs", WQ_MEM_RECLAIM, 0); |
2867 | reiserfs_write_lock(sb); | ||
2868 | } | ||
2869 | 2856 | ||
2870 | INIT_DELAYED_WORK(&journal->j_work, flush_async_commits); | 2857 | INIT_DELAYED_WORK(&journal->j_work, flush_async_commits); |
2871 | journal->j_work_sb = sb; | 2858 | journal->j_work_sb = sb; |
diff --git a/fs/reiserfs/super.c b/fs/reiserfs/super.c index 620dd5d9e1b1..61b60380d2ce 100644 --- a/fs/reiserfs/super.c +++ b/fs/reiserfs/super.c | |||
@@ -1826,6 +1826,17 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent) | |||
1826 | printk("reiserfs: using flush barriers\n"); | 1826 | printk("reiserfs: using flush barriers\n"); |
1827 | } | 1827 | } |
1828 | 1828 | ||
1829 | // set_device_ro(s->s_dev, 1) ; | ||
1830 | if (journal_init(s, jdev_name, old_format, commit_max_age)) { | ||
1831 | SWARN(silent, s, "sh-2022", | ||
1832 | "unable to initialize journal space"); | ||
1833 | goto error_unlocked; | ||
1834 | } else { | ||
1835 | jinit_done = 1; /* once this is set, journal_release must be called | ||
1836 | ** if we error out of the mount | ||
1837 | */ | ||
1838 | } | ||
1839 | |||
1829 | /* | 1840 | /* |
1830 | * This path assumed to be called with the BKL in the old times. | 1841 | * This path assumed to be called with the BKL in the old times. |
1831 | * Now we have inherited the big reiserfs lock from it and many | 1842 | * Now we have inherited the big reiserfs lock from it and many |
@@ -1836,16 +1847,6 @@ static int reiserfs_fill_super(struct super_block *s, void *data, int silent) | |||
1836 | */ | 1847 | */ |
1837 | reiserfs_write_lock(s); | 1848 | reiserfs_write_lock(s); |
1838 | 1849 | ||
1839 | // set_device_ro(s->s_dev, 1) ; | ||
1840 | if (journal_init(s, jdev_name, old_format, commit_max_age)) { | ||
1841 | SWARN(silent, s, "sh-2022", | ||
1842 | "unable to initialize journal space"); | ||
1843 | goto error; | ||
1844 | } else { | ||
1845 | jinit_done = 1; /* once this is set, journal_release must be called | ||
1846 | ** if we error out of the mount | ||
1847 | */ | ||
1848 | } | ||
1849 | if (reread_meta_blocks(s)) { | 1850 | if (reread_meta_blocks(s)) { |
1850 | SWARN(silent, s, "jmacd-9", | 1851 | SWARN(silent, s, "jmacd-9", |
1851 | "unable to reread meta blocks after journal init"); | 1852 | "unable to reread meta blocks after journal init"); |