From nobody Fri May 17 10:13:26 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1632513431271349.28994340303757; Fri, 24 Sep 2021 12:57:11 -0700 (PDT) Received: from localhost ([::1]:33952 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1mTrJl-0005Yh-St for importer@patchew.org; Fri, 24 Sep 2021 15:57:09 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:47428) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCf-0004AT-HO for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:50 -0400 Received: from us-smtp-delivery-124.mimecast.com ([216.205.24.124]:53613) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCa-0004Ll-E7 for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:48 -0400 Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-409-ohi3uKu6MKK6ab47ZYEKAQ-1; Fri, 24 Sep 2021 15:49:40 -0400 Received: from smtp.corp.redhat.com (int-mx07.intmail.prod.int.phx2.redhat.com [10.5.11.22]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id 4B9221966356; Fri, 24 Sep 2021 19:49:12 +0000 (UTC) Received: from horse.redhat.com (unknown [10.22.32.185]) by smtp.corp.redhat.com (Postfix) with ESMTP id CB3671017CE7; Fri, 24 Sep 2021 19:49:06 +0000 (UTC) Received: by horse.redhat.com (Postfix, from userid 10451) id 53890228280; Fri, 24 Sep 2021 15:49:06 -0400 (EDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1632512983; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=xXZqwWIRkqd5BbVITRT/Unx2IY9mLdjehXnaepKPudg=; b=cYKbSG1Z6j4BkwlVLtW0y2IOEnB29Ks9xqmKITErwzUQLJS8ChlJP7fDWOGhgQmUOSmbPZ o9PbXj5e5R6tJsWqnm4S+GOB1krEltJ+VhwUcVEscV1GJNew1bevckzIhBcmKK19BX+u0y YSQ1N0M83YqiiSahP3enZpcu+OH6rC4= X-MC-Unique: ohi3uKu6MKK6ab47ZYEKAQ-1 From: Vivek Goyal To: qemu-devel@nongnu.org, virtio-fs@redhat.com Subject: [PATCH 1/5] fuse: Header file changes for FUSE_SECURITY_CTX Date: Fri, 24 Sep 2021 15:48:50 -0400 Message-Id: <20210924194854.919414-2-vgoyal@redhat.com> In-Reply-To: <20210924194854.919414-1-vgoyal@redhat.com> References: <20210924194854.919414-1-vgoyal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.84 on 10.5.11.22 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=vgoyal@redhat.com X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=216.205.24.124; envelope-from=vgoyal@redhat.com; helo=us-smtp-delivery-124.mimecast.com X-Spam_score_int: -23 X-Spam_score: -2.4 X-Spam_bar: -- X-Spam_report: (-2.4 / 5.0 requ) DKIMWL_WL_HIGH=-1.473, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_LOW=-0.7, RCVD_IN_MSPIKE_H2=-0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: miklos@szeredi.hu, chirantan@chromium.org, stephen.smalley.work@gmail.com, dwalsh@redhat.com, dgilbert@redhat.com, vgoyal@redhat.com Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZM-MESSAGEID: 1632513431908100001 Content-Type: text/plain; charset="utf-8" These are just header file changes which should show up in qemu if corresponding kernel changes get merged. Signed-off-by: Vivek Goyal --- include/standard-headers/linux/fuse.h | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/include/standard-headers/linux/fuse.h b/include/standard-heade= rs/linux/fuse.h index cce105bfba..9e1672fbb2 100644 --- a/include/standard-headers/linux/fuse.h +++ b/include/standard-headers/linux/fuse.h @@ -181,6 +181,10 @@ * - add FUSE_OPEN_KILL_SUIDGID * - extend fuse_setxattr_in, add FUSE_SETXATTR_EXT * - add FUSE_SETXATTR_ACL_KILL_SGID + * + * 7.35 + * - add FUSE_SECURITY_CTX flag for fuse_init_out + * - add security context to create, mkdir, symlink, and mknod requests */ =20 #ifndef _LINUX_FUSE_H @@ -212,7 +216,7 @@ #define FUSE_KERNEL_VERSION 7 =20 /** Minor version number of this interface */ -#define FUSE_KERNEL_MINOR_VERSION 33 +#define FUSE_KERNEL_MINOR_VERSION 35 =20 /** The node ID of the root inode */ #define FUSE_ROOT_ID 1 @@ -329,6 +333,8 @@ struct fuse_file_lock { * write/truncate sgid is killed only if file has group * execute permission. (Same as Linux VFS behavior). * FUSE_SETXATTR_EXT: Server supports extended struct fuse_setxattr_in + * FUSE_SECURITY_CTX: add security context to create, mkdir, symlink, and + * mknod */ #define FUSE_ASYNC_READ (1 << 0) #define FUSE_POSIX_LOCKS (1 << 1) @@ -360,6 +366,7 @@ struct fuse_file_lock { #define FUSE_SUBMOUNTS (1 << 27) #define FUSE_HANDLE_KILLPRIV_V2 (1 << 28) #define FUSE_SETXATTR_EXT (1 << 29) +#define FUSE_SECURITY_CTX (1 << 30) =20 /** * CUSE INIT request/reply flags @@ -967,4 +974,9 @@ struct fuse_removemapping_one { #define FUSE_REMOVEMAPPING_MAX_ENTRY \ (PAGE_SIZE / sizeof(struct fuse_removemapping_one)) =20 +struct fuse_secctx { + uint32_t size; + uint32_t padding; +}; + #endif /* _LINUX_FUSE_H */ --=20 2.31.1 From nobody Fri May 17 10:13:26 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1632513293708977.4662103399297; Fri, 24 Sep 2021 12:54:53 -0700 (PDT) Received: from localhost ([::1]:58570 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1mTrHY-00033J-NP for importer@patchew.org; Fri, 24 Sep 2021 15:54:52 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:47368) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCc-00049p-BR for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:47 -0400 Received: from us-smtp-delivery-124.mimecast.com ([216.205.24.124]:57445) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCR-0004FS-KY for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:45 -0400 Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-139-WpGDdcI1NF-SJwDKqbhR0A-1; Fri, 24 Sep 2021 15:49:32 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.phx2.redhat.com [10.5.11.13]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id 1D9D38C95B8; Fri, 24 Sep 2021 19:49:07 +0000 (UTC) Received: from horse.redhat.com (unknown [10.22.32.185]) by smtp.corp.redhat.com (Postfix) with ESMTP id C70E05BAF4; Fri, 24 Sep 2021 19:49:06 +0000 (UTC) Received: by horse.redhat.com (Postfix, from userid 10451) id 5808F228281; Fri, 24 Sep 2021 15:49:06 -0400 (EDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1632512974; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=rbuRCJRboLXquzEGjl2ZvdMdNNDTf7EjWG9fB8yspR0=; b=BeTzR6e8sIKBpHyzaXPgco8XT61V3zzzf4JHFDqy+vVQ/HsXfrHW47T/fRPwp3Ld9bnxE8 O5tg3+1nd2FQyfvis2U1LAhnNYGmbPFAsw1oJANK5OVl8xkYBXcof+WM650uNk5jIi2kA2 idEn6OSAcfmjXv9xqNAazpbI/NCFp2U= X-MC-Unique: WpGDdcI1NF-SJwDKqbhR0A-1 From: Vivek Goyal To: qemu-devel@nongnu.org, virtio-fs@redhat.com Subject: [PATCH 2/5] fuse_lowlevel.c: Add capability to parse security context Date: Fri, 24 Sep 2021 15:48:51 -0400 Message-Id: <20210924194854.919414-3-vgoyal@redhat.com> In-Reply-To: <20210924194854.919414-1-vgoyal@redhat.com> References: <20210924194854.919414-1-vgoyal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.13 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=vgoyal@redhat.com X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=216.205.24.124; envelope-from=vgoyal@redhat.com; helo=us-smtp-delivery-124.mimecast.com X-Spam_score_int: -23 X-Spam_score: -2.4 X-Spam_bar: -- X-Spam_report: (-2.4 / 5.0 requ) DKIMWL_WL_HIGH=-1.473, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_LOW=-0.7, RCVD_IN_MSPIKE_H2=-0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: miklos@szeredi.hu, chirantan@chromium.org, stephen.smalley.work@gmail.com, dwalsh@redhat.com, dgilbert@redhat.com, vgoyal@redhat.com Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZM-MESSAGEID: 1632513295988100001 Content-Type: text/plain; charset="utf-8" Add capability to enable and parse security context as sent by client and put into fuse_req. Filesystems now can get security context from request and set it on files during creation. Signed-off-by: Vivek Goyal --- tools/virtiofsd/fuse_common.h | 5 +++ tools/virtiofsd/fuse_i.h | 7 ++++ tools/virtiofsd/fuse_lowlevel.c | 74 +++++++++++++++++++++++++++++++++ 3 files changed, 86 insertions(+) diff --git a/tools/virtiofsd/fuse_common.h b/tools/virtiofsd/fuse_common.h index 0c2665b977..6f3485d1dc 100644 --- a/tools/virtiofsd/fuse_common.h +++ b/tools/virtiofsd/fuse_common.h @@ -377,6 +377,11 @@ struct fuse_file_info { */ #define FUSE_CAP_SETXATTR_EXT (1 << 29) =20 +/** + * Indicates that file server supports creating file security context + */ +#define FUSE_CAP_SECURITY_CTX (1 << 30) + /** * Ioctl flags * diff --git a/tools/virtiofsd/fuse_i.h b/tools/virtiofsd/fuse_i.h index 492e002181..a5572fa4ae 100644 --- a/tools/virtiofsd/fuse_i.h +++ b/tools/virtiofsd/fuse_i.h @@ -15,6 +15,12 @@ struct fv_VuDev; struct fv_QueueInfo; =20 +struct fuse_security_context { + const char *name; + uint32_t ctxlen; + const void *ctx; +}; + struct fuse_req { struct fuse_session *se; uint64_t unique; @@ -35,6 +41,7 @@ struct fuse_req { } u; struct fuse_req *next; struct fuse_req *prev; + struct fuse_security_context secctx; }; =20 struct fuse_notify_req { diff --git a/tools/virtiofsd/fuse_lowlevel.c b/tools/virtiofsd/fuse_lowleve= l.c index e4679c73ab..fae92e0f3f 100644 --- a/tools/virtiofsd/fuse_lowlevel.c +++ b/tools/virtiofsd/fuse_lowlevel.c @@ -886,11 +886,41 @@ static void do_readlink(fuse_req_t req, fuse_ino_t no= deid, } } =20 +static int parse_secctx_fill_req(fuse_req_t req, struct fuse_mbuf_iter *it= er) +{ + struct fuse_secctx *fsecctx; + const void *secctx; + + fsecctx =3D fuse_mbuf_iter_advance(iter, sizeof(*fsecctx)); + if (!fsecctx) { + return -EINVAL; + } + + if (fsecctx->size) { + const char *name =3D fuse_mbuf_iter_advance_str(iter); + if (!name) { + return -EINVAL; + } + + secctx =3D fuse_mbuf_iter_advance(iter, fsecctx->size); + if (!secctx) { + return -EINVAL; + } + + req->secctx.name =3D name; + req->secctx.ctx =3D secctx; + req->secctx.ctxlen =3D fsecctx->size; + } + return 0; +} + static void do_mknod(fuse_req_t req, fuse_ino_t nodeid, struct fuse_mbuf_iter *iter) { struct fuse_mknod_in *arg; const char *name; + bool secctx_enabled =3D req->se->conn.want & FUSE_CAP_SECURITY_CTX; + int err; =20 arg =3D fuse_mbuf_iter_advance(iter, sizeof(*arg)); name =3D fuse_mbuf_iter_advance_str(iter); @@ -901,6 +931,13 @@ static void do_mknod(fuse_req_t req, fuse_ino_t nodeid, =20 req->ctx.umask =3D arg->umask; =20 + if (secctx_enabled) { + err =3D parse_secctx_fill_req(req, iter); + if (err) { + fuse_reply_err(req, -err); + } + } + if (req->se->op.mknod) { req->se->op.mknod(req, nodeid, name, arg->mode, arg->rdev); } else { @@ -913,6 +950,8 @@ static void do_mkdir(fuse_req_t req, fuse_ino_t nodeid, { struct fuse_mkdir_in *arg; const char *name; + bool secctx_enabled =3D req->se->conn.want & FUSE_CAP_SECURITY_CTX; + int err; =20 arg =3D fuse_mbuf_iter_advance(iter, sizeof(*arg)); name =3D fuse_mbuf_iter_advance_str(iter); @@ -923,6 +962,13 @@ static void do_mkdir(fuse_req_t req, fuse_ino_t nodeid, =20 req->ctx.umask =3D arg->umask; =20 + if (secctx_enabled) { + err =3D parse_secctx_fill_req(req, iter); + if (err) { + fuse_reply_err(req, err); + } + } + if (req->se->op.mkdir) { req->se->op.mkdir(req, nodeid, name, arg->mode); } else { @@ -969,12 +1015,21 @@ static void do_symlink(fuse_req_t req, fuse_ino_t no= deid, { const char *name =3D fuse_mbuf_iter_advance_str(iter); const char *linkname =3D fuse_mbuf_iter_advance_str(iter); + bool secctx_enabled =3D req->se->conn.want & FUSE_CAP_SECURITY_CTX; + int err; =20 if (!name || !linkname) { fuse_reply_err(req, EINVAL); return; } =20 + if (secctx_enabled) { + err =3D parse_secctx_fill_req(req, iter); + if (err) { + fuse_reply_err(req, err); + } + } + if (req->se->op.symlink) { req->se->op.symlink(req, linkname, nodeid, name); } else { @@ -1048,6 +1103,8 @@ static void do_link(fuse_req_t req, fuse_ino_t nodeid, static void do_create(fuse_req_t req, fuse_ino_t nodeid, struct fuse_mbuf_iter *iter) { + bool secctx_enabled =3D req->se->conn.want & FUSE_CAP_SECURITY_CTX; + if (req->se->op.create) { struct fuse_create_in *arg; struct fuse_file_info fi; @@ -1060,6 +1117,15 @@ static void do_create(fuse_req_t req, fuse_ino_t nod= eid, return; } =20 + if (secctx_enabled) { + int err; + err =3D parse_secctx_fill_req(req, iter); + if (err) { + fuse_reply_err(req, err); + return; + } + } + memset(&fi, 0, sizeof(fi)); fi.flags =3D arg->flags; fi.kill_priv =3D arg->open_flags & FUSE_OPEN_KILL_SUIDGID; @@ -1997,6 +2063,9 @@ static void do_init(fuse_req_t req, fuse_ino_t nodeid, if (arg->flags & FUSE_SETXATTR_EXT) { se->conn.capable |=3D FUSE_CAP_SETXATTR_EXT; } + if (arg->flags & FUSE_SECURITY_CTX) { + se->conn.capable |=3D FUSE_CAP_SECURITY_CTX; + } #ifdef HAVE_SPLICE #ifdef HAVE_VMSPLICE se->conn.capable |=3D FUSE_CAP_SPLICE_WRITE | FUSE_CAP_SPLICE_MOVE; @@ -2029,6 +2098,7 @@ static void do_init(fuse_req_t req, fuse_ino_t nodeid, LL_SET_DEFAULT(se->op.readdirplus, FUSE_CAP_READDIRPLUS); LL_SET_DEFAULT(se->op.readdirplus && se->op.readdir, FUSE_CAP_READDIRPLUS_AUTO); + LL_SET_DEFAULT(1, FUSE_CAP_SECURITY_CTX); se->conn.time_gran =3D 1; =20 if (bufsize < FUSE_MIN_READ_BUFFER) { @@ -2136,6 +2206,10 @@ static void do_init(fuse_req_t req, fuse_ino_t nodei= d, outarg.flags |=3D FUSE_SETXATTR_EXT; } =20 + if (se->conn.want & FUSE_CAP_SECURITY_CTX) { + outarg.flags |=3D FUSE_SECURITY_CTX; + } + fuse_log(FUSE_LOG_DEBUG, " INIT: %u.%u\n", outarg.major, outarg.mino= r); fuse_log(FUSE_LOG_DEBUG, " flags=3D0x%08x\n", outarg.flags); fuse_log(FUSE_LOG_DEBUG, " max_readahead=3D0x%08x\n", outarg.max_rea= dahead); --=20 2.31.1 From nobody Fri May 17 10:13:26 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1632513121458892.5284504899785; Fri, 24 Sep 2021 12:52:01 -0700 (PDT) Received: from localhost ([::1]:51874 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1mTrEm-0006wH-D1 for importer@patchew.org; Fri, 24 Sep 2021 15:52:00 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:47422) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCe-0004AI-Lv for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:48 -0400 Received: from us-smtp-delivery-124.mimecast.com ([170.10.133.124]:50669) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCR-0004F7-KX for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:48 -0400 Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-400-jxeJO__vPTu26QFpNpT3tw-1; Fri, 24 Sep 2021 15:49:33 -0400 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.phx2.redhat.com [10.5.11.15]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id 37CBFABFEF; Fri, 24 Sep 2021 19:49:07 +0000 (UTC) Received: from horse.redhat.com (unknown [10.22.32.185]) by smtp.corp.redhat.com (Postfix) with ESMTP id BABB66B909; Fri, 24 Sep 2021 19:49:06 +0000 (UTC) Received: by horse.redhat.com (Postfix, from userid 10451) id 5D2CD228282; Fri, 24 Sep 2021 15:49:06 -0400 (EDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1632512974; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=AbU3zBpkTZISMheH/ABBF4b9YCeJ+lPJimNymFsSkZM=; b=Z5ECXaRTpcqROYQzmFg9dZCiILGdgBoDLYEeLUesoemMfGLUSbnepL/1/QdSFtPOFSPA4Q AwtymzSmnl0QIAcQaUQxjg+9kgUpHG4N5I0gQqDMeitQ/vzMOE8pYqBmHMzRjT60VXatzm FO1OmaoHkca1hnhu3Rh/TlJZW0Oxy+w= X-MC-Unique: jxeJO__vPTu26QFpNpT3tw-1 From: Vivek Goyal To: qemu-devel@nongnu.org, virtio-fs@redhat.com Subject: [PATCH 3/5] virtiofsd: Move core file creation code in separate function Date: Fri, 24 Sep 2021 15:48:52 -0400 Message-Id: <20210924194854.919414-4-vgoyal@redhat.com> In-Reply-To: <20210924194854.919414-1-vgoyal@redhat.com> References: <20210924194854.919414-1-vgoyal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.15 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=vgoyal@redhat.com X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=170.10.133.124; envelope-from=vgoyal@redhat.com; helo=us-smtp-delivery-124.mimecast.com X-Spam_score_int: -42 X-Spam_score: -4.3 X-Spam_bar: ---- X-Spam_report: (-4.3 / 5.0 requ) BAYES_00=-1.9, DKIMWL_WL_HIGH=-1.473, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_LOW=-0.7, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: miklos@szeredi.hu, chirantan@chromium.org, stephen.smalley.work@gmail.com, dwalsh@redhat.com, dgilbert@redhat.com, vgoyal@redhat.com Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZM-MESSAGEID: 1632513122444100005 Content-Type: text/plain; charset="utf-8" Move core file creation bits in a separate function. Soon this is going to get more complex as file creation need to set security context also. And there will be multiple modes of file creation in next patch. Signed-off-by: Vivek Goyal --- tools/virtiofsd/passthrough_ll.c | 36 ++++++++++++++++++++++---------- 1 file changed, 25 insertions(+), 11 deletions(-) diff --git a/tools/virtiofsd/passthrough_ll.c b/tools/virtiofsd/passthrough= _ll.c index 64b5b4fbb1..54978b7fae 100644 --- a/tools/virtiofsd/passthrough_ll.c +++ b/tools/virtiofsd/passthrough_ll.c @@ -1976,6 +1976,30 @@ static int lo_do_open(struct lo_data *lo, struct lo_= inode *inode, return 0; } =20 +static int do_lo_create(fuse_req_t req, struct lo_inode *parent_inode, + const char *name, mode_t mode, + struct fuse_file_info *fi, int* open_fd) +{ + int err =3D 0, fd; + struct lo_cred old =3D {}; + struct lo_data *lo =3D lo_data(req); + + err =3D lo_change_cred(req, &old, lo->change_umask); + if (err) { + return err; + } + + /* Try to create a new file but don't open existing files */ + fd =3D openat(parent_inode->fd, name, fi->flags | O_CREAT | O_EXCL, mo= de); + if (fd =3D=3D -1) { + err =3D errno; + } else { + *open_fd =3D fd; + } + lo_restore_cred(&old, lo->change_umask); + return err; +} + static void lo_create(fuse_req_t req, fuse_ino_t parent, const char *name, mode_t mode, struct fuse_file_info *fi) { @@ -1985,7 +2009,6 @@ static void lo_create(fuse_req_t req, fuse_ino_t pare= nt, const char *name, struct lo_inode *inode =3D NULL; struct fuse_entry_param e; int err; - struct lo_cred old =3D {}; =20 fuse_log(FUSE_LOG_DEBUG, "lo_create(parent=3D%" PRIu64 ", name=3D%s)" " kill_priv=3D%d\n", parent, name, fi->kill_priv); @@ -2001,18 +2024,9 @@ static void lo_create(fuse_req_t req, fuse_ino_t par= ent, const char *name, return; } =20 - err =3D lo_change_cred(req, &old, lo->change_umask); - if (err) { - goto out; - } - update_open_flags(lo->writeback, lo->allow_direct_io, fi); =20 - /* Try to create a new file but don't open existing files */ - fd =3D openat(parent_inode->fd, name, fi->flags | O_CREAT | O_EXCL, mo= de); - err =3D fd =3D=3D -1 ? errno : 0; - - lo_restore_cred(&old, lo->change_umask); + err =3D do_lo_create(req, parent_inode, name, mode, fi, &fd); =20 /* Ignore the error if file exists and O_EXCL was not given */ if (err && (err !=3D EEXIST || (fi->flags & O_EXCL))) { --=20 2.31.1 From nobody Fri May 17 10:13:26 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1632513129214131.1228239000559; Fri, 24 Sep 2021 12:52:09 -0700 (PDT) Received: from localhost ([::1]:51998 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1mTrEu-000723-1n for importer@patchew.org; Fri, 24 Sep 2021 15:52:08 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:47408) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCd-0004A5-QZ for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:47 -0400 Received: from us-smtp-delivery-124.mimecast.com ([170.10.133.124]:24182) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCU-0004IA-Ty for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:47 -0400 Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-448-kka5oMm5O_StCSJ8ihBkeQ-1; Fri, 24 Sep 2021 15:49:37 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.phx2.redhat.com [10.5.11.13]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id 2D443109A5AD; Fri, 24 Sep 2021 19:49:07 +0000 (UTC) Received: from horse.redhat.com (unknown [10.22.32.185]) by smtp.corp.redhat.com (Postfix) with ESMTP id C26155BB15; Fri, 24 Sep 2021 19:49:06 +0000 (UTC) Received: by horse.redhat.com (Postfix, from userid 10451) id 62F81228283; Fri, 24 Sep 2021 15:49:06 -0400 (EDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1632512978; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=hPZv9fa1wAYA04Oc+LTlSMKlKsKreUVAHthCd47+yh0=; b=f6SduxUjHpiDP6+Ri2Zb44Z3HfrtrOXzb3MNsic3wqVqVwvRS3tMmY9h/dH+AkcVjrg1g7 G/K/mPJdJlLknxfrfuP+84ehZjsrJjOJAKy+MafeVGr4Mqxk6LbCGKXaa525Ip0bjoDocO axkl8z1MA5uCD2O8cu0zIeDNYaGqHiU= X-MC-Unique: kka5oMm5O_StCSJ8ihBkeQ-1 From: Vivek Goyal To: qemu-devel@nongnu.org, virtio-fs@redhat.com Subject: [PATCH 4/5] virtiofsd: Create new file with fscreate set Date: Fri, 24 Sep 2021 15:48:53 -0400 Message-Id: <20210924194854.919414-5-vgoyal@redhat.com> In-Reply-To: <20210924194854.919414-1-vgoyal@redhat.com> References: <20210924194854.919414-1-vgoyal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.13 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=vgoyal@redhat.com X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=170.10.133.124; envelope-from=vgoyal@redhat.com; helo=us-smtp-delivery-124.mimecast.com X-Spam_score_int: -42 X-Spam_score: -4.3 X-Spam_bar: ---- X-Spam_report: (-4.3 / 5.0 requ) BAYES_00=-1.9, DKIMWL_WL_HIGH=-1.473, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_LOW=-0.7, RCVD_IN_MSPIKE_H2=-0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: miklos@szeredi.hu, chirantan@chromium.org, stephen.smalley.work@gmail.com, dwalsh@redhat.com, dgilbert@redhat.com, vgoyal@redhat.com Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZM-MESSAGEID: 1632513131262100001 Content-Type: text/plain; charset="utf-8" This patch adds support to set /proc/thread-self/attr/fscreate before file creation. It is set to a value as sent by client. This will allow for atomic creation of security context on files w.r.t file creation. This is primarily useful when either there is no SELinux enabled on host or host and guest policies are in sync and don't conflict. Signed-off-by: Vivek Goyal --- tools/virtiofsd/passthrough_ll.c | 284 ++++++++++++++++++++++++++++--- 1 file changed, 257 insertions(+), 27 deletions(-) diff --git a/tools/virtiofsd/passthrough_ll.c b/tools/virtiofsd/passthrough= _ll.c index 54978b7fae..d8c14d3220 100644 --- a/tools/virtiofsd/passthrough_ll.c +++ b/tools/virtiofsd/passthrough_ll.c @@ -172,6 +172,8 @@ struct lo_data { =20 /* An O_PATH file descriptor to /proc/self/fd/ */ int proc_self_fd; + /* An O_PATH file descriptor to /proc/self/task/ */ + int proc_self_task; int user_killpriv_v2, killpriv_v2; /* If set, virtiofsd is responsible for setting umask during creation = */ bool change_umask; @@ -229,6 +231,11 @@ static struct lo_inode *lo_find(struct lo_data *lo, st= ruct stat *st, static int xattr_map_client(const struct lo_data *lo, const char *client_n= ame, char **out_name); =20 +#define FCHDIR_NOFAIL(fd) do { \ + int fchdir_res =3D fchdir(fd); \ + assert(fchdir_res =3D=3D 0); \ + } while (0) + static bool is_dot_or_dotdot(const char *name) { return name[0] =3D=3D '.' && @@ -1259,16 +1266,140 @@ static void lo_restore_cred_gain_cap(struct lo_cre= d *old, bool restore_umask, } } =20 +/* Helpers to set/reset fscreate */ +static int open_set_proc_fscreate(struct lo_data *lo, const void *ctx, + size_t ctxlen, int *fd) +{ + char procname[64]; + int fscreate_fd, err =3D 0; + size_t written; + + sprintf(procname, "%d/attr/fscreate", gettid()); + fscreate_fd =3D openat(lo->proc_self_task, procname, O_WRONLY); + err =3D fscreate_fd =3D=3D -1 ? errno : 0; + if (err) { + return err; + } + + written =3D write(fscreate_fd, ctx, ctxlen); + err =3D written =3D=3D -1 ? errno : 0; + if (err) { + goto out; + } + + *fd =3D fscreate_fd; + return 0; +out: + close(fscreate_fd); + return err; +} + +static void close_reset_proc_fscreate(int fd) +{ + if ((write(fd, NULL, 0)) =3D=3D -1) { + fuse_log(FUSE_LOG_WARNING, "Failed to reset fscreate. err=3D%d\n",= errno); + } + close(fd); + return; +} + +static int do_mknod_symlink_secctx(fuse_req_t req, struct lo_inode *dir, + const char *name, const char *secctx_na= me) +{ + int path_fd, err; + char procname[64]; + struct lo_data *lo =3D lo_data(req); + + if (!req->secctx.ctxlen) { + return 0; + } + + /* Open newly created element with O_PATH */ + path_fd =3D openat(dir->fd, name, O_PATH | O_NOFOLLOW); + err =3D path_fd =3D=3D -1 ? errno : 0; + if (err) { + return err; + } + sprintf(procname, "%i", path_fd); + FCHDIR_NOFAIL(lo->proc_self_fd); + /* Set security context. This is not atomic w.r.t file creation */ + err =3D setxattr(procname, secctx_name, req->secctx.ctx, req->secctx.c= txlen, + 0); + if (err) { + err =3D errno; + } + FCHDIR_NOFAIL(lo->root.fd); + close(path_fd); + return err; +} + +static int do_mknod_symlink(fuse_req_t req, struct lo_inode *dir, + const char *name, mode_t mode, dev_t rdev, + const char *link) +{ + int err, fscreate_fd =3D -1; + const char *secctx_name =3D req->secctx.name; + struct lo_cred old =3D {}; + struct lo_data *lo =3D lo_data(req); + char *mapped_name =3D NULL; + bool secctx_enabled =3D req->secctx.ctxlen; + bool do_fscreate =3D false; + + if (secctx_enabled && lo->xattrmap) { + err =3D xattr_map_client(lo, req->secctx.name, &mapped_name); + if (err < 0) { + return -err; + } + secctx_name =3D mapped_name; + } + + /* + * If security xattr has not been remapped, set fscreate and no + * need to do a setxattr() after file creation + */ + if (secctx_enabled && !mapped_name) { + do_fscreate =3D true; + err =3D open_set_proc_fscreate(lo, req->secctx.ctx, req->secctx.ct= xlen, + &fscreate_fd); + if (err) { + goto out; + } + } + + err =3D lo_change_cred(req, &old, lo->change_umask && !S_ISLNK(mode)); + if (err) { + goto out; + } + + err =3D mknod_wrapper(dir->fd, name, link, mode, rdev); + err =3D err =3D=3D -1 ? errno : 0; + lo_restore_cred(&old, lo->change_umask && !S_ISLNK(mode)); + if (err) { + goto out; + } + + if (!do_fscreate) { + err =3D do_mknod_symlink_secctx(req, dir, name, secctx_name); + if (err) { + unlinkat(dir->fd, name, S_ISDIR(mode) ? AT_REMOVEDIR : 0); + } + } +out: + if (fscreate_fd !=3D -1) { + close_reset_proc_fscreate(fscreate_fd); + } + g_free(mapped_name); + return err; +} + static void lo_mknod_symlink(fuse_req_t req, fuse_ino_t parent, const char *name, mode_t mode, dev_t rdev, const char *link) { - int res; int saverr; struct lo_data *lo =3D lo_data(req); struct lo_inode *dir; struct fuse_entry_param e; - struct lo_cred old =3D {}; =20 if (is_empty(name)) { fuse_reply_err(req, ENOENT); @@ -1286,21 +1417,11 @@ static void lo_mknod_symlink(fuse_req_t req, fuse_i= no_t parent, return; } =20 - saverr =3D lo_change_cred(req, &old, lo->change_umask && !S_ISLNK(mode= )); + saverr =3D do_mknod_symlink(req, dir, name, mode, rdev, link); if (saverr) { goto out; } =20 - res =3D mknod_wrapper(dir->fd, name, link, mode, rdev); - - saverr =3D errno; - - lo_restore_cred(&old, lo->change_umask && !S_ISLNK(mode)); - - if (res =3D=3D -1) { - goto out; - } - saverr =3D lo_do_lookup(req, parent, name, &e, NULL); if (saverr) { goto out; @@ -1976,13 +2097,16 @@ static int lo_do_open(struct lo_data *lo, struct lo= _inode *inode, return 0; } =20 -static int do_lo_create(fuse_req_t req, struct lo_inode *parent_inode, - const char *name, mode_t mode, - struct fuse_file_info *fi, int* open_fd) +static int do_create_nosecctx(fuse_req_t req, struct lo_inode *parent_inod= e, + const char *name, mode_t mode, + struct fuse_file_info *fi, int *open_fd) { - int err =3D 0, fd; + int err, fd; struct lo_cred old =3D {}; struct lo_data *lo =3D lo_data(req); + int flags; + + flags =3D fi->flags | O_CREAT | O_EXCL; =20 err =3D lo_change_cred(req, &old, lo->change_umask); if (err) { @@ -1990,13 +2114,106 @@ static int do_lo_create(fuse_req_t req, struct lo_= inode *parent_inode, } =20 /* Try to create a new file but don't open existing files */ - fd =3D openat(parent_inode->fd, name, fi->flags | O_CREAT | O_EXCL, mo= de); - if (fd =3D=3D -1) { - err =3D errno; - } else { + fd =3D openat(parent_inode->fd, name, flags, mode); + err =3D fd =3D=3D -1 ? errno : 0; + lo_restore_cred(&old, lo->change_umask); + if (!err) { *open_fd =3D fd; } - lo_restore_cred(&old, lo->change_umask); + return err; +} + +static int do_create_secctx_fscreate(fuse_req_t req, + struct lo_inode *parent_inode, + const char *name, mode_t mode, + struct fuse_file_info *fi, int *open_= fd) +{ + int err =3D 0, fd =3D -1, fscreate_fd =3D -1; + struct lo_data *lo =3D lo_data(req); + + err =3D open_set_proc_fscreate(lo, req->secctx.ctx, req->secctx.ctxlen, + &fscreate_fd); + if (err) { + return err; + } + + err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, &fd); + + close_reset_proc_fscreate(fscreate_fd); + if (!err) { + *open_fd =3D fd; + } + return err; +} + +static int do_create_secctx_noatomic(fuse_req_t req, + struct lo_inode *parent_inode, + const char *name, mode_t mode, + struct fuse_file_info *fi, + const char *secctx_name, int *open_fd) +{ + int err =3D 0, fd =3D -1; + + err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, &fd); + if (err) { + goto out; + } + + /* Set security context. This is not atomic w.r.t file creation */ + err =3D fsetxattr(fd, secctx_name, req->secctx.ctx, req->secctx.ctxlen= , 0); + err =3D err =3D=3D -1 ? errno : 0; +out: + if (!err) { + *open_fd =3D fd; + } else { + if (fd !=3D -1) { + close(fd); + unlinkat(parent_inode->fd, name, 0); + } + } + return err; +} + +static int do_lo_create(fuse_req_t req, struct lo_inode *parent_inode, + const char *name, mode_t mode, + struct fuse_file_info *fi, int *open_fd) +{ + struct lo_data *lo =3D lo_data(req); + char *mapped_name =3D NULL; + int err; + const char *ctxname =3D req->secctx.name; + bool secctx_enabled =3D req->secctx.ctxlen; + + if (secctx_enabled && lo->xattrmap) { + err =3D xattr_map_client(lo, req->secctx.name, &mapped_name); + if (err < 0) { + return -err; + } + + ctxname =3D mapped_name; + } + + if (secctx_enabled) { + /* + * If security.selinux has not been remapped. Use fscreate to set + * context before file creation. + * Otherwise fallback to non-atomic method of file creation + * and xattr settting. + */ + if (!mapped_name) { + err =3D do_create_secctx_fscreate(req, parent_inode, name, mod= e, fi, + open_fd); + goto out; + } + + err =3D do_create_secctx_noatomic(req, parent_inode, name, mode, f= i, + ctxname, open_fd); + } else { + err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, open= _fd); + } + +out: + g_free(mapped_name); return err; } =20 @@ -2831,11 +3048,6 @@ static int xattr_map_server(const struct lo_data *lo= , const char *server_name, return -ENODATA; } =20 -#define FCHDIR_NOFAIL(fd) do { \ - int fchdir_res =3D fchdir(fd); \ - assert(fchdir_res =3D=3D 0); \ - } while (0) - static bool block_xattr(struct lo_data *lo, const char *name) { /* @@ -3497,6 +3709,13 @@ static void setup_namespaces(struct lo_data *lo, str= uct fuse_session *se) exit(1); } =20 + /* Get the /proc/self/task descriptor */ + lo->proc_self_task =3D open("/proc/self/task/", O_PATH); + if (lo->proc_self_task =3D=3D -1) { + fuse_log(FUSE_LOG_ERR, "open(/proc/self/task, O_PATH): %m\n"); + exit(1); + } + /* * We only need /proc/self/fd. Prevent ".." from accessing parent * directories of /proc/self/fd by bind-mounting it over /proc. Since = / was @@ -3713,6 +3932,12 @@ static void setup_chroot(struct lo_data *lo) exit(1); } =20 + lo->proc_self_task =3D open("/proc/self/task", O_PATH); + if (lo->proc_self_fd =3D=3D -1) { + fuse_log(FUSE_LOG_ERR, "open(\"/proc/self/task\", O_PATH): %m\n"); + exit(1); + } + /* * Make the shared directory the file system root so that FUSE_OPEN * (lo_open()) cannot escape the shared directory by opening a symlink. @@ -3898,6 +4123,10 @@ static void fuse_lo_data_cleanup(struct lo_data *lo) close(lo->proc_self_fd); } =20 + if (lo->proc_self_task >=3D 0) { + close(lo->proc_self_task); + } + if (lo->root.fd >=3D 0) { close(lo->root.fd); } @@ -3925,6 +4154,7 @@ int main(int argc, char *argv[]) .posix_lock =3D 0, .allow_direct_io =3D 0, .proc_self_fd =3D -1, + .proc_self_task =3D -1, .user_killpriv_v2 =3D -1, .user_posix_acl =3D -1, }; --=20 2.31.1 From nobody Fri May 17 10:13:26 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1632513118999698.8258620524997; Fri, 24 Sep 2021 12:51:58 -0700 (PDT) Received: from localhost ([::1]:51774 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1mTrEi-0006rc-Sm for importer@patchew.org; Fri, 24 Sep 2021 15:51:56 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:47402) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCd-00049r-Gc for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:47 -0400 Received: from us-smtp-delivery-124.mimecast.com ([216.205.24.124]:38583) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1mTrCV-0004I7-6t for qemu-devel@nongnu.org; Fri, 24 Sep 2021 15:49:47 -0400 Received: from mimecast-mx01.redhat.com (mimecast-mx01.redhat.com [209.132.183.4]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-55-RQ0JiS_5MCGtjW_NHFLETg-1; Fri, 24 Sep 2021 15:49:34 -0400 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.phx2.redhat.com [10.5.11.13]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx01.redhat.com (Postfix) with ESMTPS id AC5F21860184; Fri, 24 Sep 2021 19:49:07 +0000 (UTC) Received: from horse.redhat.com (unknown [10.22.32.185]) by smtp.corp.redhat.com (Postfix) with ESMTP id 6F4E15BAEA; Fri, 24 Sep 2021 19:49:07 +0000 (UTC) Received: by horse.redhat.com (Postfix, from userid 10451) id 67B00228284; Fri, 24 Sep 2021 15:49:06 -0400 (EDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1632512978; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=CXnOCJc0zCqSN0TB99jBNe7ZLRHAc8j+BmGoV7yK9Bs=; b=N1QZWizs//43hGhDFgDvjtnGWVYOYbw0D7JypTnQgyfpl3ChquyRpuRXeviqMvIOI8L6tZ 0t51cQOWHl8j6jIrVGx6eZ4OFOlTqk4fTrudWHALGBGpYi/KpSpjwZjWzwfZ1l990dj0rz wxw8wXhovO5csgXCInZz4FolvsOg8QY= X-MC-Unique: RQ0JiS_5MCGtjW_NHFLETg-1 From: Vivek Goyal To: qemu-devel@nongnu.org, virtio-fs@redhat.com Subject: [PATCH 5/5] virtiofsd: Create new file using O_TMPFILE and set security context Date: Fri, 24 Sep 2021 15:48:54 -0400 Message-Id: <20210924194854.919414-6-vgoyal@redhat.com> In-Reply-To: <20210924194854.919414-1-vgoyal@redhat.com> References: <20210924194854.919414-1-vgoyal@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.13 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=vgoyal@redhat.com X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=216.205.24.124; envelope-from=vgoyal@redhat.com; helo=us-smtp-delivery-124.mimecast.com X-Spam_score_int: -23 X-Spam_score: -2.4 X-Spam_bar: -- X-Spam_report: (-2.4 / 5.0 requ) DKIMWL_WL_HIGH=-1.473, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_LOW=-0.7, RCVD_IN_MSPIKE_H2=-0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: miklos@szeredi.hu, chirantan@chromium.org, stephen.smalley.work@gmail.com, dwalsh@redhat.com, dgilbert@redhat.com, vgoyal@redhat.com Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZM-MESSAGEID: 1632513120963100002 Content-Type: text/plain; charset="utf-8" If guest and host policies can't work with each other, then guest security context (selinux label) needs to be set into an xattr. Say remap guest security.selinux xattr to trusted.virtiofs.security.selinux. That means setting "fscreate" is not going to help as that's ony useful for security.selinux xattr on host. So we need another method which is atomic. Use O_TMPFILE to create new file, set xattr and then linkat() to proper place. But this works only for regular files. So dir, symlinks will continue to be non-atomic. Also if host filesystem does not support O_TMPFILE, we fallback to non-atomic behavior. Signed-off-by: Vivek Goyal --- tools/virtiofsd/passthrough_ll.c | 78 +++++++++++++++++++++++++++++--- 1 file changed, 71 insertions(+), 7 deletions(-) diff --git a/tools/virtiofsd/passthrough_ll.c b/tools/virtiofsd/passthrough= _ll.c index d8c14d3220..f5c3746510 100644 --- a/tools/virtiofsd/passthrough_ll.c +++ b/tools/virtiofsd/passthrough_ll.c @@ -2099,14 +2099,29 @@ static int lo_do_open(struct lo_data *lo, struct lo= _inode *inode, =20 static int do_create_nosecctx(fuse_req_t req, struct lo_inode *parent_inod= e, const char *name, mode_t mode, - struct fuse_file_info *fi, int *open_fd) + struct fuse_file_info *fi, int *open_fd, + bool tmpfile) { int err, fd; struct lo_cred old =3D {}; struct lo_data *lo =3D lo_data(req); int flags; =20 - flags =3D fi->flags | O_CREAT | O_EXCL; + if (tmpfile) { + flags =3D fi->flags | O_TMPFILE; + /* + * Don't use O_EXCL as we want to link file later. Also reset O_CR= EAT + * otherwise openat() returns -EINVAL. + */ + flags &=3D ~(O_CREAT | O_EXCL); + + /* O_TMPFILE needs either O_RDWR or O_WRONLY */ + if ((flags & O_ACCMODE) =3D=3D O_RDONLY) { + flags |=3D O_RDWR; + } + } else { + flags =3D fi->flags | O_CREAT | O_EXCL; + } =20 err =3D lo_change_cred(req, &old, lo->change_umask); if (err) { @@ -2137,7 +2152,7 @@ static int do_create_secctx_fscreate(fuse_req_t req, return err; } =20 - err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, &fd); + err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, &fd, fal= se); =20 close_reset_proc_fscreate(fscreate_fd); if (!err) { @@ -2146,6 +2161,44 @@ static int do_create_secctx_fscreate(fuse_req_t req, return err; } =20 +static int do_create_secctx_tmpfile(fuse_req_t req, + struct lo_inode *parent_inode, + const char *name, mode_t mode, + struct fuse_file_info *fi, + const char *secctx_name, int *open_fd) +{ + int err, fd =3D -1; + struct lo_data *lo =3D lo_data(req); + char procname[64]; + + err =3D do_create_nosecctx(req, parent_inode, ".", mode, fi, &fd, true= ); + if (err) { + return err; + } + + err =3D fsetxattr(fd, secctx_name, req->secctx.ctx, req->secctx.ctxlen= , 0); + if (err) { + err =3D errno; + goto out; + } + + /* Security context set on file. Link it in place */ + sprintf(procname, "%d", fd); + FCHDIR_NOFAIL(lo->proc_self_fd); + err =3D linkat(AT_FDCWD, procname, parent_inode->fd, name, + AT_SYMLINK_FOLLOW); + err =3D err =3D=3D -1 ? errno : 0; + FCHDIR_NOFAIL(lo->root.fd); + +out: + if (!err) { + *open_fd =3D fd; + } else if (fd !=3D -1) { + close(fd); + } + return err; +} + static int do_create_secctx_noatomic(fuse_req_t req, struct lo_inode *parent_inode, const char *name, mode_t mode, @@ -2154,7 +2207,7 @@ static int do_create_secctx_noatomic(fuse_req_t req, { int err =3D 0, fd =3D -1; =20 - err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, &fd); + err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, &fd, fal= se); if (err) { goto out; } @@ -2196,20 +2249,31 @@ static int do_lo_create(fuse_req_t req, struct lo_i= node *parent_inode, if (secctx_enabled) { /* * If security.selinux has not been remapped. Use fscreate to set - * context before file creation. - * Otherwise fallback to non-atomic method of file creation + * context before file creation. Use tempfile method for regular + * files. Otherwise fallback to non-atomic method of file creation * and xattr settting. */ if (!mapped_name) { err =3D do_create_secctx_fscreate(req, parent_inode, name, mod= e, fi, open_fd); goto out; + } else if (S_ISREG(mode)) { + err =3D do_create_secctx_tmpfile(req, parent_inode, name, mode= , fi, + ctxname, open_fd); + /* + * If filesystem does not support O_TMPFILE, fallback to non-a= tomic + * method. + */ + if (!err || err !=3D EOPNOTSUPP) { + goto out; + } } =20 err =3D do_create_secctx_noatomic(req, parent_inode, name, mode, f= i, ctxname, open_fd); } else { - err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, open= _fd); + err =3D do_create_nosecctx(req, parent_inode, name, mode, fi, open= _fd, + false); } =20 out: --=20 2.31.1