summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKent Overstreet <kent.overstreet@gmail.com>2018-12-19 08:43:01 -0500
committerKent Overstreet <kent.overstreet@gmail.com>2018-12-27 11:38:38 -0500
commit43a612b1e1fa52b8cf413f7e604603bc4e628e71 (patch)
tree3e0ac180ed3cb8f51694010ccb62554197f3d4bc
parentd9a7c0bc0ca0fee4f12a07541f18f8e8c2e7c50b (diff)
bcachefs: more project quota fixes
-rw-r--r--fs/bcachefs/fs-ioctl.c26
-rw-r--r--fs/bcachefs/fs.h13
-rw-r--r--fs/bcachefs/quota.h2
-rw-r--r--fs/bcachefs/xattr.c7
4 files changed, 27 insertions, 21 deletions
diff --git a/fs/bcachefs/fs-ioctl.c b/fs/bcachefs/fs-ioctl.c
index 7b9acafb9491..d6cb21d69073 100644
--- a/fs/bcachefs/fs-ioctl.c
+++ b/fs/bcachefs/fs-ioctl.c
@@ -103,19 +103,6 @@ static int bch2_ioc_fsgetxattr(struct bch_inode_info *inode,
return copy_to_user(arg, &fa, sizeof(fa));
}
-static int bch2_set_projid(struct bch_fs *c,
- struct bch_inode_info *inode,
- u32 projid)
-{
- struct bch_qid qid = inode->ei_qid;
-
- qid.q[QTYP_PRJ] = projid;
-
- return bch2_fs_quota_transfer(c, inode, qid,
- 1 << QTYP_PRJ,
- KEY_TYPE_QUOTA_PREALLOC);
-}
-
static int fssetxattr_inode_update_fn(struct bch_inode_info *inode,
struct bch_inode_unpacked *bi,
void *p)
@@ -123,11 +110,7 @@ static int fssetxattr_inode_update_fn(struct bch_inode_info *inode,
struct flags_set *s = p;
if (s->projid != bi->bi_project) {
- if (s->projid)
- bi->bi_fields_set |= 1U << Inode_opt_project;
- else
- bi->bi_fields_set &= ~(1U << Inode_opt_project);
-
+ bi->bi_fields_set |= 1U << Inode_opt_project;
bi->bi_project = s->projid;
}
@@ -150,7 +133,10 @@ static int bch2_ioc_fssetxattr(struct bch_fs *c,
if (fa.fsx_xflags)
return -EOPNOTSUPP;
- s.projid = fa.fsx_projid;
+ if (fa.fsx_projid >= U32_MAX)
+ return -EINVAL;
+
+ s.projid = fa.fsx_projid + 1;
ret = mnt_want_write_file(file);
if (ret)
@@ -163,7 +149,7 @@ static int bch2_ioc_fssetxattr(struct bch_fs *c,
}
mutex_lock(&inode->ei_update_lock);
- ret = bch2_set_projid(c, inode, fa.fsx_projid);
+ ret = bch2_set_projid(c, inode, s.projid);
if (ret)
goto err_unlock;
diff --git a/fs/bcachefs/fs.h b/fs/bcachefs/fs.h
index 7dc0453af2db..9ac6fc87f69a 100644
--- a/fs/bcachefs/fs.h
+++ b/fs/bcachefs/fs.h
@@ -104,6 +104,19 @@ int bch2_fs_quota_transfer(struct bch_fs *,
unsigned,
enum quota_acct_mode);
+static inline int bch2_set_projid(struct bch_fs *c,
+ struct bch_inode_info *inode,
+ u32 projid)
+{
+ struct bch_qid qid = inode->ei_qid;
+
+ qid.q[QTYP_PRJ] = projid;
+
+ return bch2_fs_quota_transfer(c, inode, qid,
+ 1 << QTYP_PRJ,
+ KEY_TYPE_QUOTA_PREALLOC);
+}
+
struct inode *bch2_vfs_inode_get(struct bch_fs *, u64);
/* returns 0 if we want to do the update, or error is passed up */
diff --git a/fs/bcachefs/quota.h b/fs/bcachefs/quota.h
index 47e343cc0262..34b4a0f0ae77 100644
--- a/fs/bcachefs/quota.h
+++ b/fs/bcachefs/quota.h
@@ -19,7 +19,7 @@ static inline struct bch_qid bch_qid(struct bch_inode_unpacked *u)
return (struct bch_qid) {
.q[QTYP_USR] = u->bi_uid,
.q[QTYP_GRP] = u->bi_gid,
- .q[QTYP_PRJ] = u->bi_project,
+ .q[QTYP_PRJ] = u->bi_project ? u->bi_project - 1 : 0,
};
}
diff --git a/fs/bcachefs/xattr.c b/fs/bcachefs/xattr.c
index 407177b25e24..4a4dba725689 100644
--- a/fs/bcachefs/xattr.c
+++ b/fs/bcachefs/xattr.c
@@ -512,7 +512,14 @@ static int bch2_xattr_bcachefs_set(const struct xattr_handler *handler,
}
mutex_lock(&inode->ei_update_lock);
+ if (inode_opt_id == Inode_opt_project) {
+ ret = bch2_set_projid(c, inode, s.v);
+ if (ret)
+ goto err;
+ }
+
ret = bch2_write_inode(c, inode, inode_opt_set_fn, &s, 0);
+err:
mutex_unlock(&inode->ei_update_lock);
if (value &&