From 6da72500882d9749cb2be6eaa2568e6fe6e5ff4d Mon Sep 17 00:00:00 2001 From: Jeff Layton Date: Mon, 5 Dec 2016 14:19:23 -0500 Subject: [PATCH] mds: clear setuid/setgid bits on ownership changes If we get a ownership change, POSIX mandates that you clear the setuid and setgid bits unless you are "appropriately privileged", in which case the OS is allowed to leave them intact. Linux however always clears those bits, regardless of the process privileges, as that makes it simpler to close some potential races. Have ceph do the same. Signed-off-by: Jeff Layton --- src/mds/Server.cc | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/src/mds/Server.cc b/src/mds/Server.cc index 4f1057bf754..1293d7d0bc2 100644 --- a/src/mds/Server.cc +++ b/src/mds/Server.cc @@ -3793,13 +3793,20 @@ void Server::handle_client_setattr(MDRequestRef& mdr) pi = cur->project_inode(); - if (mask & CEPH_SETATTR_MODE) - pi->mode = (pi->mode & ~07777) | (req->head.args.setattr.mode & 07777); if (mask & CEPH_SETATTR_UID) pi->uid = req->head.args.setattr.uid; if (mask & CEPH_SETATTR_GID) pi->gid = req->head.args.setattr.gid; + if (mask & CEPH_SETATTR_MODE) + pi->mode = (pi->mode & ~07777) | (req->head.args.setattr.mode & 07777); + else if ((mask & (CEPH_SETATTR_UID|CEPH_SETATTR_GID)) && + S_ISREG(pi->mode)) { + pi->mode &= ~S_ISUID; + if ((pi->mode & (S_ISGID|S_IXGRP)) == (S_ISGID|S_IXGRP)) + pi->mode &= ~S_ISGID; + } + if (mask & CEPH_SETATTR_MTIME) pi->mtime = req->head.args.setattr.mtime; if (mask & CEPH_SETATTR_ATIME) -- 2.39.5