diff options
Diffstat (limited to 'fs/quota.c')
-rw-r--r-- | fs/quota.c | 60 |
1 files changed, 24 insertions, 36 deletions
diff --git a/fs/quota.c b/fs/quota.c index 3f0333a51a23..f5d1cff55196 100644 --- a/fs/quota.c +++ b/fs/quota.c | |||
@@ -149,36 +149,6 @@ static int check_quotactl_valid(struct super_block *sb, int type, int cmd, qid_t | |||
149 | return error; | 149 | return error; |
150 | } | 150 | } |
151 | 151 | ||
152 | static struct super_block *get_super_to_sync(int type) | ||
153 | { | ||
154 | struct list_head *head; | ||
155 | int cnt, dirty; | ||
156 | |||
157 | restart: | ||
158 | spin_lock(&sb_lock); | ||
159 | list_for_each(head, &super_blocks) { | ||
160 | struct super_block *sb = list_entry(head, struct super_block, s_list); | ||
161 | |||
162 | /* This test just improves performance so it needn't be reliable... */ | ||
163 | for (cnt = 0, dirty = 0; cnt < MAXQUOTAS; cnt++) | ||
164 | if ((type == cnt || type == -1) && sb_has_quota_enabled(sb, cnt) | ||
165 | && info_any_dirty(&sb_dqopt(sb)->info[cnt])) | ||
166 | dirty = 1; | ||
167 | if (!dirty) | ||
168 | continue; | ||
169 | sb->s_count++; | ||
170 | spin_unlock(&sb_lock); | ||
171 | down_read(&sb->s_umount); | ||
172 | if (!sb->s_root) { | ||
173 | drop_super(sb); | ||
174 | goto restart; | ||
175 | } | ||
176 | return sb; | ||
177 | } | ||
178 | spin_unlock(&sb_lock); | ||
179 | return NULL; | ||
180 | } | ||
181 | |||
182 | static void quota_sync_sb(struct super_block *sb, int type) | 152 | static void quota_sync_sb(struct super_block *sb, int type) |
183 | { | 153 | { |
184 | int cnt; | 154 | int cnt; |
@@ -219,17 +189,35 @@ static void quota_sync_sb(struct super_block *sb, int type) | |||
219 | 189 | ||
220 | void sync_dquots(struct super_block *sb, int type) | 190 | void sync_dquots(struct super_block *sb, int type) |
221 | { | 191 | { |
192 | int cnt, dirty; | ||
193 | |||
222 | if (sb) { | 194 | if (sb) { |
223 | if (sb->s_qcop->quota_sync) | 195 | if (sb->s_qcop->quota_sync) |
224 | quota_sync_sb(sb, type); | 196 | quota_sync_sb(sb, type); |
197 | return; | ||
225 | } | 198 | } |
226 | else { | 199 | |
227 | while ((sb = get_super_to_sync(type)) != NULL) { | 200 | spin_lock(&sb_lock); |
228 | if (sb->s_qcop->quota_sync) | 201 | restart: |
229 | quota_sync_sb(sb, type); | 202 | list_for_each_entry(sb, &super_blocks, s_list) { |
230 | drop_super(sb); | 203 | /* This test just improves performance so it needn't be reliable... */ |
231 | } | 204 | for (cnt = 0, dirty = 0; cnt < MAXQUOTAS; cnt++) |
205 | if ((type == cnt || type == -1) && sb_has_quota_enabled(sb, cnt) | ||
206 | && info_any_dirty(&sb_dqopt(sb)->info[cnt])) | ||
207 | dirty = 1; | ||
208 | if (!dirty) | ||
209 | continue; | ||
210 | sb->s_count++; | ||
211 | spin_unlock(&sb_lock); | ||
212 | down_read(&sb->s_umount); | ||
213 | if (sb->s_root && sb->s_qcop->quota_sync) | ||
214 | quota_sync_sb(sb, type); | ||
215 | up_read(&sb->s_umount); | ||
216 | spin_lock(&sb_lock); | ||
217 | if (__put_super_and_need_restart(sb)) | ||
218 | goto restart; | ||
232 | } | 219 | } |
220 | spin_unlock(&sb_lock); | ||
233 | } | 221 | } |
234 | 222 | ||
235 | /* Copy parameters and call proper function */ | 223 | /* Copy parameters and call proper function */ |