diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2014-08-13 19:45:40 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2014-08-13 19:45:40 -0400 |
| commit | cec997093bbff881c3da49084dfba4f76361e96a (patch) | |
| tree | 7c84f8c30ceef7209a18d7cd216a3c16536008c5 | |
| parent | 8d2d441ac4af223eae466c3c31ff737cc31a1411 (diff) | |
| parent | 01777836c87081e4f68c4a43c9abe6114805f91e (diff) | |
Merge branch 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs
Pull quota, reiserfs, UDF updates from Jan Kara:
"Scalability improvements for quota, a few reiserfs fixes, and couple
of misc cleanups (udf, ext2)"
* 'for_linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jack/linux-fs:
reiserfs: Fix use after free in journal teardown
reiserfs: fix corruption introduced by balance_leaf refactor
udf: avoid redundant memcpy when writing data in ICB
fs/udf: re-use hex_asc_upper_{hi,lo} macros
fs/quota: kernel-doc warning fixes
udf: use linux/uaccess.h
fs/ext2/super.c: Drop memory allocation cast
quota: remove dqptr_sem
quota: simplify remove_inode_dquot_ref()
quota: avoid unnecessary dqget()/dqput() calls
quota: protect Q_GETFMT by dqonoff_mutex
| -rw-r--r-- | fs/ext2/super.c | 2 | ||||
| -rw-r--r-- | fs/quota/dquot.c | 180 | ||||
| -rw-r--r-- | fs/quota/kqid.c | 2 | ||||
| -rw-r--r-- | fs/quota/netlink.c | 3 | ||||
| -rw-r--r-- | fs/quota/quota.c | 6 | ||||
| -rw-r--r-- | fs/reiserfs/do_balan.c | 111 | ||||
| -rw-r--r-- | fs/reiserfs/journal.c | 22 | ||||
| -rw-r--r-- | fs/reiserfs/lbalance.c | 5 | ||||
| -rw-r--r-- | fs/reiserfs/reiserfs.h | 9 | ||||
| -rw-r--r-- | fs/reiserfs/super.c | 6 | ||||
| -rw-r--r-- | fs/super.c | 1 | ||||
| -rw-r--r-- | fs/udf/file.c | 22 | ||||
| -rw-r--r-- | fs/udf/lowlevel.c | 2 | ||||
| -rw-r--r-- | fs/udf/super.c | 2 | ||||
| -rw-r--r-- | fs/udf/symlink.c | 2 | ||||
| -rw-r--r-- | fs/udf/unicode.c | 9 | ||||
| -rw-r--r-- | include/linux/quota.h | 1 |
17 files changed, 189 insertions, 196 deletions
diff --git a/fs/ext2/super.c b/fs/ext2/super.c index 3750031cfa2f..b88edc05c230 100644 --- a/fs/ext2/super.c +++ b/fs/ext2/super.c | |||
| @@ -161,7 +161,7 @@ static struct kmem_cache * ext2_inode_cachep; | |||
| 161 | static struct inode *ext2_alloc_inode(struct super_block *sb) | 161 | static struct inode *ext2_alloc_inode(struct super_block *sb) |
| 162 | { | 162 | { |
| 163 | struct ext2_inode_info *ei; | 163 | struct ext2_inode_info *ei; |
| 164 | ei = (struct ext2_inode_info *)kmem_cache_alloc(ext2_inode_cachep, GFP_KERNEL); | 164 | ei = kmem_cache_alloc(ext2_inode_cachep, GFP_KERNEL); |
| 165 | if (!ei) | 165 | if (!ei) |
| 166 | return NULL; | 166 | return NULL; |
| 167 | ei->i_block_alloc_info = NULL; | 167 | ei->i_block_alloc_info = NULL; |
diff --git a/fs/quota/dquot.c b/fs/quota/dquot.c index 7f30bdc57d13..f2d0eee9d1f1 100644 --- a/fs/quota/dquot.c +++ b/fs/quota/dquot.c | |||
| @@ -96,13 +96,16 @@ | |||
| 96 | * Note that some things (eg. sb pointer, type, id) doesn't change during | 96 | * Note that some things (eg. sb pointer, type, id) doesn't change during |
| 97 | * the life of the dquot structure and so needn't to be protected by a lock | 97 | * the life of the dquot structure and so needn't to be protected by a lock |
| 98 | * | 98 | * |
| 99 | * Any operation working on dquots via inode pointers must hold dqptr_sem. If | 99 | * Operation accessing dquots via inode pointers are protected by dquot_srcu. |
| 100 | * operation is just reading pointers from inode (or not using them at all) the | 100 | * Operation of reading pointer needs srcu_read_lock(&dquot_srcu), and |
| 101 | * read lock is enough. If pointers are altered function must hold write lock. | 101 | * synchronize_srcu(&dquot_srcu) is called after clearing pointers from |
| 102 | * inode and before dropping dquot references to avoid use of dquots after | ||
| 103 | * they are freed. dq_data_lock is used to serialize the pointer setting and | ||
| 104 | * clearing operations. | ||
| 102 | * Special care needs to be taken about S_NOQUOTA inode flag (marking that | 105 | * Special care needs to be taken about S_NOQUOTA inode flag (marking that |
| 103 | * inode is a quota file). Functions adding pointers from inode to dquots have | 106 | * inode is a quota file). Functions adding pointers from inode to dquots have |
| 104 | * to check this flag under dqptr_sem and then (if S_NOQUOTA is not set) they | 107 | * to check this flag under dq_data_lock and then (if S_NOQUOTA is not set) they |
| 105 | * have to do all pointer modifications before dropping dqptr_sem. This makes | 108 | * have to do all pointer modifications before dropping dq_data_lock. This makes |
| 106 | * sure they cannot race with quotaon which first sets S_NOQUOTA flag and | 109 | * sure they cannot race with quotaon which first sets S_NOQUOTA flag and |
| 107 | * then drops all pointers to dquots from an inode. | 110 | * then drops all pointers to dquots from an inode. |
| 108 | * | 111 | * |
| @@ -116,21 +119,15 @@ | |||
| 116 | * spinlock to internal buffers before writing. | 119 | * spinlock to internal buffers before writing. |
| 117 | * | 120 | * |
| 118 | * Lock ordering (including related VFS locks) is the following: | 121 | * Lock ordering (including related VFS locks) is the following: |
| 119 | * dqonoff_mutex > i_mutex > journal_lock > dqptr_sem > dquot->dq_lock > | 122 | * dqonoff_mutex > i_mutex > journal_lock > dquot->dq_lock > dqio_mutex |
| 120 | * dqio_mutex | ||
| 121 | * dqonoff_mutex > i_mutex comes from dquot_quota_sync, dquot_enable, etc. | 123 | * dqonoff_mutex > i_mutex comes from dquot_quota_sync, dquot_enable, etc. |
| 122 | * The lock ordering of dqptr_sem imposed by quota code is only dqonoff_sem > | ||
| 123 | * dqptr_sem. But filesystem has to count with the fact that functions such as | ||
| 124 | * dquot_alloc_space() acquire dqptr_sem and they usually have to be called | ||
| 125 | * from inside a transaction to keep filesystem consistency after a crash. Also | ||
| 126 | * filesystems usually want to do some IO on dquot from ->mark_dirty which is | ||
| 127 | * called with dqptr_sem held. | ||
| 128 | */ | 124 | */ |
| 129 | 125 | ||
| 130 | static __cacheline_aligned_in_smp DEFINE_SPINLOCK(dq_list_lock); | 126 | static __cacheline_aligned_in_smp DEFINE_SPINLOCK(dq_list_lock); |
| 131 | static __cacheline_aligned_in_smp DEFINE_SPINLOCK(dq_state_lock); | 127 | static __cacheline_aligned_in_smp DEFINE_SPINLOCK(dq_state_lock); |
| 132 | __cacheline_aligned_in_smp DEFINE_SPINLOCK(dq_data_lock); | 128 | __cacheline_aligned_in_smp DEFINE_SPINLOCK(dq_data_lock); |
| 133 | EXPORT_SYMBOL(dq_data_lock); | 129 | EXPORT_SYMBOL(dq_data_lock); |
| 130 | DEFINE_STATIC_SRCU(dquot_srcu); | ||
| 134 | 131 | ||
| 135 | void __quota_error(struct super_block *sb, const char *func, | 132 | void __quota_error(struct super_block *sb, const char *func, |
| 136 | const char *fmt, ...) | 133 | const char *fmt, ...) |
| @@ -733,7 +730,6 @@ static struct shrinker dqcache_shrinker = { | |||
| 733 | 730 | ||
| 734 | /* | 731 | /* |
| 735 | * Put reference to dquot | 732 | * Put reference to dquot |
| 736 | * NOTE: If you change this function please check whether dqput_blocks() works right... | ||
| 737 | */ | 733 | */ |
| 738 | void dqput(struct dquot *dquot) | 734 | void dqput(struct dquot *dquot) |
| 739 | { | 735 | { |
| @@ -963,46 +959,33 @@ static void add_dquot_ref(struct super_block *sb, int type) | |||
| 963 | } | 959 | } |
| 964 | 960 | ||
| 965 | /* | 961 | /* |
| 966 | * Return 0 if dqput() won't block. | ||
| 967 | * (note that 1 doesn't necessarily mean blocking) | ||
| 968 | */ | ||
| 969 | static inline int dqput_blocks(struct dquot *dquot) | ||
| 970 | { | ||
| 971 | if (atomic_read(&dquot->dq_count) <= 1) | ||
| 972 | return 1; | ||
| 973 | return 0; | ||
| 974 | } | ||
| 975 | |||
| 976 | /* | ||
| 977 | * Remove references to dquots from inode and add dquot to list for freeing | 962 | * Remove references to dquots from inode and add dquot to list for freeing |
| 978 | * if we have the last reference to dquot | 963 | * if we have the last reference to dquot |
| 979 | * We can't race with anybody because we hold dqptr_sem for writing... | ||
| 980 | */ | 964 | */ |
| 981 | static int remove_inode_dquot_ref(struct inode *inode, int type, | 965 | static void remove_inode_dquot_ref(struct inode *inode, int type, |
| 982 | struct list_head *tofree_head) | 966 | struct list_head *tofree_head) |
| 983 | { | 967 | { |
| 984 | struct dquot *dquot = inode->i_dquot[type]; | 968 | struct dquot *dquot = inode->i_dquot[type]; |
| 985 | 969 | ||
| 986 | inode->i_dquot[type] = NULL; | 970 | inode->i_dquot[type] = NULL; |
| 987 | if (dquot) { | 971 | if (!dquot) |
| 988 | if (dqput_blocks(dquot)) { | 972 | return; |
| 989 | #ifdef CONFIG_QUOTA_DEBUG | 973 | |
| 990 | if (atomic_read(&dquot->dq_count) != 1) | 974 | if (list_empty(&dquot->dq_free)) { |
| 991 | quota_error(inode->i_sb, "Adding dquot with " | 975 | /* |
| 992 | "dq_count %d to dispose list", | 976 | * The inode still has reference to dquot so it can't be in the |
| 993 | atomic_read(&dquot->dq_count)); | 977 | * free list |
| 994 | #endif | 978 | */ |
| 995 | spin_lock(&dq_list_lock); | 979 | spin_lock(&dq_list_lock); |
| 996 | /* As dquot must have currently users it can't be on | 980 | list_add(&dquot->dq_free, tofree_head); |
| 997 | * the free list... */ | 981 | spin_unlock(&dq_list_lock); |
| 998 | list_add(&dquot->dq_free, tofree_head); | 982 | } else { |
| 999 | spin_unlock(&dq_list_lock); | 983 | /* |
| 1000 | return 1; | 984 | * Dquot is already in a list to put so we won't drop the last |
| 1001 | } | 985 | * reference here. |
| 1002 | else | 986 | */ |
| 1003 | dqput(dquot); /* We have guaranteed we won't block */ | 987 | dqput(dquot); |
| 1004 | } | 988 | } |
| 1005 | return 0; | ||
| 1006 | } | 989 | } |
| 1007 | 990 | ||
| 1008 | /* | 991 | /* |
| @@ -1037,13 +1020,15 @@ static void remove_dquot_ref(struct super_block *sb, int type, | |||
| 1037 | * We have to scan also I_NEW inodes because they can already | 1020 | * We have to scan also I_NEW inodes because they can already |
| 1038 | * have quota pointer initialized. Luckily, we need to touch | 1021 | * have quota pointer initialized. Luckily, we need to touch |
| 1039 | * only quota pointers and these have separate locking | 1022 | * only quota pointers and these have separate locking |
| 1040 | * (dqptr_sem). | 1023 | * (dq_data_lock). |
| 1041 | */ | 1024 | */ |
| 1025 | spin_lock(&dq_data_lock); | ||
| 1042 | if (!IS_NOQUOTA(inode)) { | 1026 | if (!IS_NOQUOTA(inode)) { |
| 1043 | if (unlikely(inode_get_rsv_space(inode) > 0)) | 1027 | if (unlikely(inode_get_rsv_space(inode) > 0)) |
| 1044 | reserved = 1; | 1028 | reserved = 1; |
