summaryrefslogtreecommitdiffstats
path: root/fs/quota
diff options
context:
space:
mode:
authorJan Kara <jack@suse.cz>2017-06-09 02:59:46 -0400
committerJan Kara <jack@suse.cz>2017-08-17 13:16:24 -0400
commit42fdb8583d5a7eaf916c7323fce6cb4728f364c4 (patch)
treeab56d2a8a3735eb3e94c35cf834050ab54851e4b /fs/quota
parent9a8ae30e73cb8827dd0a8ae5fd505db457cfb7ed (diff)
quota: Push dqio_sem down to ->read_file_info()
Push down acquisition of dqio_sem into ->read_file_info() callback. This is for consistency with other operations and it also allows us to get rid of an ugliness in OCFS2. Reviewed-by: Andreas Dilger <adilger@dilger.ca> Signed-off-by: Jan Kara <jack@suse.cz>
Diffstat (limited to 'fs/quota')
-rw-r--r--fs/quota/dquot.c6
-rw-r--r--fs/quota/quota_v1.c2
-rw-r--r--fs/quota/quota_v2.c28
3 files changed, 23 insertions, 13 deletions
diff --git a/fs/quota/dquot.c b/fs/quota/dquot.c
index 1e1ff97098ec..5e77c4da69a6 100644
--- a/fs/quota/dquot.c
+++ b/fs/quota/dquot.c
@@ -2313,15 +2313,11 @@ static int vfs_load_quota_inode(struct inode *inode, int type, int format_id,
2313 dqopt->info[type].dqi_format = fmt; 2313 dqopt->info[type].dqi_format = fmt;
2314 dqopt->info[type].dqi_fmt_id = format_id; 2314 dqopt->info[type].dqi_fmt_id = format_id;
2315 INIT_LIST_HEAD(&dqopt->info[type].dqi_dirty_list); 2315 INIT_LIST_HEAD(&dqopt->info[type].dqi_dirty_list);
2316 down_read(&dqopt->dqio_sem);
2317 error = dqopt->ops[type]->read_file_info(sb, type); 2316 error = dqopt->ops[type]->read_file_info(sb, type);
2318 if (error < 0) { 2317 if (error < 0)
2319 up_read(&dqopt->dqio_sem);
2320 goto out_file_init; 2318 goto out_file_init;
2321 }
2322 if (dqopt->flags & DQUOT_QUOTA_SYS_FILE) 2319 if (dqopt->flags & DQUOT_QUOTA_SYS_FILE)
2323 dqopt->info[type].dqi_flags |= DQF_SYS_FILE; 2320 dqopt->info[type].dqi_flags |= DQF_SYS_FILE;
2324 up_read(&dqopt->dqio_sem);
2325 spin_lock(&dq_state_lock); 2321 spin_lock(&dq_state_lock);
2326 dqopt->flags |= dquot_state_flag(flags, type); 2322 dqopt->flags |= dquot_state_flag(flags, type);
2327 spin_unlock(&dq_state_lock); 2323 spin_unlock(&dq_state_lock);
diff --git a/fs/quota/quota_v1.c b/fs/quota/quota_v1.c
index fe68bf544b29..b2d8e04e567a 100644
--- a/fs/quota/quota_v1.c
+++ b/fs/quota/quota_v1.c
@@ -161,6 +161,7 @@ static int v1_read_file_info(struct super_block *sb, int type)
161 struct v1_disk_dqblk dqblk; 161 struct v1_disk_dqblk dqblk;
162 int ret; 162 int ret;
163 163
164 down_read(&dqopt->dqio_sem);
164 ret = sb->s_op->quota_read(sb, type, (char *)&dqblk, 165 ret = sb->s_op->quota_read(sb, type, (char *)&dqblk,
165 sizeof(struct v1_disk_dqblk), v1_dqoff(0)); 166 sizeof(struct v1_disk_dqblk), v1_dqoff(0));
166 if (ret != sizeof(struct v1_disk_dqblk)) { 167 if (ret != sizeof(struct v1_disk_dqblk)) {
@@ -177,6 +178,7 @@ static int v1_read_file_info(struct super_block *sb, int type)
177 dqopt->info[type].dqi_bgrace = 178 dqopt->info[type].dqi_bgrace =
178 dqblk.dqb_btime ? dqblk.dqb_btime : MAX_DQ_TIME; 179 dqblk.dqb_btime ? dqblk.dqb_btime : MAX_DQ_TIME;
179out: 180out:
181 up_read(&dqopt->dqio_sem);
180 return ret; 182 return ret;
181} 183}
182 184
diff --git a/fs/quota/quota_v2.c b/fs/quota/quota_v2.c
index 5e47012d2f57..373d7cfea5b0 100644
--- a/fs/quota/quota_v2.c
+++ b/fs/quota/quota_v2.c
@@ -90,29 +90,38 @@ static int v2_read_file_info(struct super_block *sb, int type)
90{ 90{
91 struct v2_disk_dqinfo dinfo; 91 struct v2_disk_dqinfo dinfo;
92 struct v2_disk_dqheader dqhead; 92 struct v2_disk_dqheader dqhead;
93 struct mem_dqinfo *info = sb_dqinfo(sb, type); 93 struct quota_info *dqopt = sb_dqopt(sb);
94 struct mem_dqinfo *info = &dqopt->info[type];
94 struct qtree_mem_dqinfo *qinfo; 95 struct qtree_mem_dqinfo *qinfo;
95 ssize_t size; 96 ssize_t size;
96 unsigned int version; 97 unsigned int version;
98 int ret;
97 99
98 if (!v2_read_header(sb, type, &dqhead)) 100 down_read(&dqopt->dqio_sem);
99 return -1; 101 if (!v2_read_header(sb, type, &dqhead)) {
102 ret = -1;
103 goto out;
104 }
100 version = le32_to_cpu(dqhead.dqh_version); 105 version = le32_to_cpu(dqhead.dqh_version);
101 if ((info->dqi_fmt_id == QFMT_VFS_V0 && version != 0) || 106 if ((info->dqi_fmt_id == QFMT_VFS_V0 && version != 0) ||
102 (info->dqi_fmt_id == QFMT_VFS_V1 && version != 1)) 107 (info->dqi_fmt_id == QFMT_VFS_V1 && version != 1)) {
103 return -1; 108 ret = -1;
109 goto out;
110 }
104 111
105 size = sb->s_op->quota_read(sb, type, (char *)&dinfo, 112 size = sb->s_op->quota_read(sb, type, (char *)&dinfo,
106 sizeof(struct v2_disk_dqinfo), V2_DQINFOOFF); 113 sizeof(struct v2_disk_dqinfo), V2_DQINFOOFF);
107 if (size != sizeof(struct v2_disk_dqinfo)) { 114 if (size != sizeof(struct v2_disk_dqinfo)) {
108 quota_error(sb, "Can't read info structure"); 115 quota_error(sb, "Can't read info structure");
109 return -1; 116 ret = -1;
117 goto out;
110 } 118 }
111 info->dqi_priv = kmalloc(sizeof(struct qtree_mem_dqinfo), GFP_NOFS); 119 info->dqi_priv = kmalloc(sizeof(struct qtree_mem_dqinfo), GFP_NOFS);
112 if (!info->dqi_priv) { 120 if (!info->dqi_priv) {
113 printk(KERN_WARNING 121 printk(KERN_WARNING
114 "Not enough memory for quota information structure.\n"); 122 "Not enough memory for quota information structure.\n");
115 return -ENOMEM; 123 ret = -ENOMEM;
124 goto out;
116 } 125 }
117 qinfo = info->dqi_priv; 126 qinfo = info->dqi_priv;
118 if (version == 0) { 127 if (version == 0) {
@@ -147,7 +156,10 @@ static int v2_read_file_info(struct super_block *sb, int type)
147 qinfo->dqi_entry_size = sizeof(struct v2r1_disk_dqblk); 156 qinfo->dqi_entry_size = sizeof(struct v2r1_disk_dqblk);
148 qinfo->dqi_ops = &v2r1_qtree_ops; 157 qinfo->dqi_ops = &v2r1_qtree_ops;
149 } 158 }
150 return 0; 159 ret = 0;
160out:
161 up_read(&dqopt->dqio_sem);
162 return ret;
151} 163}
152 164
153/* Write information header to quota file */ 165/* Write information header to quota file */