All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jeff Layton <jlayton@kernel.org>
To: viro@zeniv.linux.org.uk
Cc: linux-fsdevel@vger.kernel.org, linux-nfs@vger.kernel.org,
	linux-kernel@vger.kernel.org,
	Christian Brauner <brauner@kernel.org>,
	Yongchen Yang <yoyang@redhat.com>
Subject: [PATCH v2] vfs: bypass may_create_in_sticky check on newly-created files if task has CAP_FOWNER
Date: Wed, 27 Jul 2022 10:00:14 -0400	[thread overview]
Message-ID: <20220727140014.69091-1-jlayton@kernel.org> (raw)

From: Christian Brauner <brauner@kernel.org>

NFS server is exporting a sticky directory (mode 01777) with root
squashing enabled. Client has protect_regular enabled and then tries to
open a file as root in that directory. File is created (with ownership
set to nobody:nobody) but the open syscall returns an error. The problem
is may_create_in_sticky which rejects the open even though the file has
already been created.

Add a new condition to may_create_in_sticky. If the file was just
created, then allow bypassing the ownership check if the task has
CAP_FOWNER. With this change, the initial open of a file by root works,
but later opens of the same file will fail.

Note that we can contrive a similar situation by exporting with
all_squash and opening the file as an unprivileged user. This patch does
not fix that case. I suspect that that configuration is likely to be
fundamentally incompatible with the protect_* sysctls enabled on the
clients.

Link: https://bugzilla.redhat.com/show_bug.cgi?id=1976829
Reported-by: Yongchen Yang <yoyang@redhat.com>
Suggested-by: Christian Brauner <brauner@kernel.org>
Signed-off-by: Jeff Layton <jlayton@kernel.org>
---
 fs/namei.c | 9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)

Hi Christian,

I left you as author here since this is basically identical to the patch
you suggested. Let me know if that's an issue.

-- Jeff

diff --git a/fs/namei.c b/fs/namei.c
index 1f28d3f463c3..26b602d1152b 100644
--- a/fs/namei.c
+++ b/fs/namei.c
@@ -1221,7 +1221,8 @@ int may_linkat(struct user_namespace *mnt_userns, struct path *link)
  * Returns 0 if the open is allowed, -ve on error.
  */
 static int may_create_in_sticky(struct user_namespace *mnt_userns,
-				struct nameidata *nd, struct inode *const inode)
+				struct nameidata *nd, struct inode *const inode,
+				bool created)
 {
 	umode_t dir_mode = nd->dir_mode;
 	kuid_t dir_uid = nd->dir_uid;
@@ -1230,7 +1231,8 @@ static int may_create_in_sticky(struct user_namespace *mnt_userns,
 	    (!sysctl_protected_regular && S_ISREG(inode->i_mode)) ||
 	    likely(!(dir_mode & S_ISVTX)) ||
 	    uid_eq(i_uid_into_mnt(mnt_userns, inode), dir_uid) ||
-	    uid_eq(current_fsuid(), i_uid_into_mnt(mnt_userns, inode)))
+	    uid_eq(current_fsuid(), i_uid_into_mnt(mnt_userns, inode)) ||
+	    (created && inode_owner_or_capable(mnt_userns, inode)))
 		return 0;
 
 	if (likely(dir_mode & 0002) ||
@@ -3496,7 +3498,8 @@ static int do_open(struct nameidata *nd,
 		if (d_is_dir(nd->path.dentry))
 			return -EISDIR;
 		error = may_create_in_sticky(mnt_userns, nd,
-					     d_backing_inode(nd->path.dentry));
+					     d_backing_inode(nd->path.dentry),
+					     (file->f_mode & FMODE_CREATED));
 		if (unlikely(error))
 			return error;
 	}
-- 
2.37.1


             reply	other threads:[~2022-07-27 14:00 UTC|newest]

Thread overview: 3+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-07-27 14:00 Jeff Layton [this message]
2022-07-27 14:33 ` [PATCH v2] vfs: bypass may_create_in_sticky check on newly-created files if task has CAP_FOWNER Christian Brauner
2022-07-27 14:53   ` Jeff Layton

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20220727140014.69091-1-jlayton@kernel.org \
    --to=jlayton@kernel.org \
    --cc=brauner@kernel.org \
    --cc=linux-fsdevel@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-nfs@vger.kernel.org \
    --cc=viro@zeniv.linux.org.uk \
    --cc=yoyang@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.