diff mbox series

[16/25] lustre: llite: avoid project quota overflow

Message ID 1627933851-7603-17-git-send-email-jsimmons@infradead.org (mailing list archive)
State New, archived
Headers show
Series Sync to OpenSFS tree as of Aug 2, 2021 | expand

Commit Message

James Simmons Aug. 2, 2021, 7:50 p.m. UTC
From: Wang Shilong <wshilong@ddn.com>

Currently, project ID is stored as u32, max possible
value for it is 4294967295.

However, VFS reserve max value for special usage, see
following function:

static inline bool
qid_has_mapping(struct user_namespace *ns, struct kqid qid)
{
        return from_kqid(ns, qid) != (qid_t) -1;
}

So qid_has_mapping() could return 0 for id 4294967295.
A further try on chown test:

$ chown 4294967295:4294967295 c.sh
  chown: invalid user: ‘4294967295:4294967295’
$ chown 4294967294:4294967294 c.sh

Fix to check max possible value for project ID in the
client kernel side, and add a test case for this.

WC-bug-id: https://jira.whamcloud.com/browse/LU-14740
Lustre-commit: 3ffa5d680f0092ae ("LU-14740 llite: avoid project quota overflow")
Signed-off-by: Wang Shilong <wshilong@ddn.com>
Reviewed-on: https://review.whamcloud.com/43939
Reviewed-by: Hongchao Zhang <hongchao@whamcloud.com>
Reviewed-by: Andreas Dilger <adilger@whamcloud.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
Signed-off-by: James Simmons <jsimmons@infradead.org>
---
 fs/lustre/llite/file.c | 11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)
diff mbox series

Patch

diff --git a/fs/lustre/llite/file.c b/fs/lustre/llite/file.c
index 1bf237b..a4e432e 100644
--- a/fs/lustre/llite/file.c
+++ b/fs/lustre/llite/file.c
@@ -3323,8 +3323,17 @@  int ll_ioctl_check_project(struct inode *inode, u32 xflags,
 	 * namespace. Enforce that restriction only if we are trying to change
 	 * the quota ID state. Everything else is allowed in user namespaces.
 	 */
-	if (current_user_ns() == &init_user_ns)
+	if (current_user_ns() == &init_user_ns) {
+		/*
+		 * Caller is allowed to change the project ID. if it is being
+		 * changed, make sure that the new value is valid.
+		 */
+		if (ll_i2info(inode)->lli_projid != projid &&
+		     !projid_valid(make_kprojid(&init_user_ns, projid)))
+			return -EINVAL;
+
 		return 0;
+	}
 
 	if (ll_i2info(inode)->lli_projid != projid)
 		return -EINVAL;