Received: by 2002:ac0:e350:0:0:0:0:0 with SMTP id g16csp2766060imn; Tue, 2 Aug 2022 15:12:46 -0700 (PDT) X-Google-Smtp-Source: AA6agR6qdouAYzbN67eIvgAJ5ZOrttHEkZxGgb09vHzdggIgHQqoQRgdTcUuLmK9/zwRWOiSrYg0 X-Received: by 2002:a17:907:75d6:b0:730:7000:6061 with SMTP id jl22-20020a17090775d600b0073070006061mr10498009ejc.234.1659478366598; Tue, 02 Aug 2022 15:12:46 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1659478366; cv=none; d=google.com; s=arc-20160816; b=N/HO0pcopw4APMIjrPU1nskIcvNfJ3nXwYGw3msYDeFCepRMozmIy0vD3hM2Eo8GR2 owswDQkEVF6+wRATVzmuApr3KTbyjqFbbJ2IVZTZBOkKgBN4b0gQMwbgj69zlFAkjknh PGi7oGFWk7ZTHkbUAT/My8sQcfzD4/JbWpdsMjwDsGKAEy11gG9/URNZEWpxmgHmhIia 9I1amYUvgj63drQ/pSpOGmB2Lt3VhaHRAykw+lqEa2cQKgi25tNaZFbLZZSqKOWKz6OD ogRQliGAjn5F9D3shwADNC5ryCQAzNdQ8VOcHIvMRzc3Ytu49q4ruZx99wv9lz//mMdv 15lg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:cc:to:subject:message-id:date:from:in-reply-to :references:mime-version:dkim-signature; bh=8uV9UFbZAJguo+D6vhULdx7KulHpkoYJxifnS7kIp60=; b=jtyfy583txVyKZuXYRL/gZ1Ea7NWZwxnMEgP2iUoY8851Ec5hTSdcAyxWAVSFcz0ze 8k7gpNY1+lfQFPIChV2TnuCzGubiti4H+SxSWq1DsQ7PMmMAkQwoOpwpdjAD7sOH2T/E rKZvGaWcpf5bcCg/ROXkfXligRpC8dTU4eWpvwoDY090Nw+cp63R9z8OLZDGXtjwtUpF wcD3uRVu6vIZbo2Hh7Pd61di+h1SisxoFeEiDCP98xArriVwMdS9g0o/t9d5CEbZUoyn Ykqi31E+mg4u48IcNPfFF5mS/2qCY40Qms/5U6j2MuxrUjk/cn9Ot1yBi+6T1q+LVdAl CmZA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@kernel.org header.s=k20201202 header.b=OvLbgmDn; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id n6-20020a5099c6000000b0043bb69a32d6si13631343edb.561.2022.08.02.15.12.22; Tue, 02 Aug 2022 15:12:46 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@kernel.org header.s=k20201202 header.b=OvLbgmDn; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232123AbiHBVrf (ORCPT + 99 others); Tue, 2 Aug 2022 17:47:35 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:55754 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229539AbiHBVrc (ORCPT ); Tue, 2 Aug 2022 17:47:32 -0400 Received: from dfw.source.kernel.org (dfw.source.kernel.org [139.178.84.217]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id D1E4425C79 for ; Tue, 2 Aug 2022 14:47:31 -0700 (PDT) Received: from smtp.kernel.org (relay.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by dfw.source.kernel.org (Postfix) with ESMTPS id 5CA2C61561 for ; Tue, 2 Aug 2022 21:47:31 +0000 (UTC) Received: by smtp.kernel.org (Postfix) with ESMTPSA id BB684C433B5 for ; Tue, 2 Aug 2022 21:47:30 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1659476850; bh=bw7ZR3OubmcRjpwNuSpXxWiUDJEe/z23F1fjfbai/Z8=; h=References:In-Reply-To:From:Date:Subject:To:Cc:From; b=OvLbgmDndBHNQP0tVJ1hHSrKjt6cZe80PHrVWs2uSh7XQzCne8KBq+oFkcH1vRxFc wrtGnfTBbf2h6c+7Utrt7AvWqZI4SugTZqG/SlJCGL80bOypt7s+rrqwSFTATxMVOi JjNHd9sLBPDLXuEr4l4hPRDyvb8JsofxJ5qSsugTXCRgBR+doo+CTi0MuRGxCVZWR5 iboQvmbAuP2Lvd5m1FX613Vo5MW2RJJStHNsoiCORC1x/O42b1IwV/mQcsgLak6ny/ dimWU3akttRARF4SyzN35Cc9TRLOhl454gBj1moYKFoFEIuOwqox6N2JMh3AMMXI5x rjvQGZiUH3XFw== Received: by mail-yb1-f181.google.com with SMTP id n8so25666896yba.2 for ; Tue, 02 Aug 2022 14:47:30 -0700 (PDT) X-Gm-Message-State: ACgBeo1vbwHHhC/TzXPc9z2UlPQwe7xZmoJs3DfxjGrXkbV2ARaSNN6S zEmdrPnhCRS5zMeTyM2MXyq9PAVhKaA/7TA6UdG8ng== X-Received: by 2002:a81:9148:0:b0:328:2c96:eaed with SMTP id i69-20020a819148000000b003282c96eaedmr1782937ywg.314.1659476838933; Tue, 02 Aug 2022 14:47:18 -0700 (PDT) MIME-Version: 1.0 References: <20220801180146.1157914-1-fred@cloudflare.com> <20220801180146.1157914-2-fred@cloudflare.com> In-Reply-To: <20220801180146.1157914-2-fred@cloudflare.com> From: KP Singh Date: Tue, 2 Aug 2022 23:47:08 +0200 X-Gmail-Original-Message-ID: Message-ID: Subject: Re: [PATCH v4 1/4] security, lsm: Introduce security_create_user_ns() To: Frederick Lawler Cc: revest@chromium.org, jackmanb@chromium.org, ast@kernel.org, daniel@iogearbox.net, andrii@kernel.org, kafai@fb.com, songliubraving@fb.com, yhs@fb.com, john.fastabend@gmail.com, jmorris@namei.org, serge@hallyn.com, paul@paul-moore.com, stephen.smalley.work@gmail.com, eparis@parisplace.org, shuah@kernel.org, brauner@kernel.org, casey@schaufler-ca.com, ebiederm@xmission.com, bpf@vger.kernel.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org, linux-kselftest@vger.kernel.org, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, kernel-team@cloudflare.com, cgzones@googlemail.com, karl@bigbadwolfsecurity.com Content-Type: text/plain; charset="UTF-8" X-Spam-Status: No, score=-7.7 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,RCVD_IN_DNSWL_HI, SPF_HELO_NONE,SPF_PASS autolearn=unavailable autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org On Mon, Aug 1, 2022 at 8:02 PM Frederick Lawler wrote: > > Preventing user namespace (privileged or otherwise) creation comes in a > few of forms in order of granularity: > > 1. /proc/sys/user/max_user_namespaces sysctl > 2. OS specific patch(es) > 3. CONFIG_USER_NS > > To block a task based on its attributes, the LSM hook cred_prepare is a > good candidate for use because it provides more granular control, and > it is called before create_user_ns(): > > cred = prepare_creds() > security_prepare_creds() > call_int_hook(cred_prepare, ... > if (cred) > create_user_ns(cred) > > Since security_prepare_creds() is meant for LSMs to copy and prepare > credentials, access control is an unintended use of the hook. Therefore > introduce a new function security_create_user_ns() with an accompanying > userns_create LSM hook. > > This hook takes the prepared creds for LSM authors to write policy > against. On success, the new namespace is applied to credentials, > otherwise an error is returned. > > Signed-off-by: Frederick Lawler > Reviewed-by: Christian Brauner (Microsoft) Reviewed-by: KP Singh This looks useful, and I would also like folks to consider the observability aspects of BPF LSM as brought up here: https://lore.kernel.org/all/CAEiveUdPhEPAk7Y0ZXjPsD=Vb5hn453CHzS9aG-tkyRa8bf_eg@mail.gmail.com/ Frederick, what about adding the observability aspects to the commit description as well. - KP > > --- > Changes since v3: > - No changes > Changes since v2: > - Rename create_user_ns hook to userns_create > Changes since v1: > - Changed commit wording > - Moved execution to be after id mapping check > - Changed signature to only accept a const struct cred * > --- > include/linux/lsm_hook_defs.h | 1 + > include/linux/lsm_hooks.h | 4 ++++ > include/linux/security.h | 6 ++++++ > kernel/user_namespace.c | 5 +++++ > security/security.c | 5 +++++ > 5 files changed, 21 insertions(+) > > diff --git a/include/linux/lsm_hook_defs.h b/include/linux/lsm_hook_defs.h > index eafa1d2489fd..7ff93cb8ca8d 100644 > --- a/include/linux/lsm_hook_defs.h > +++ b/include/linux/lsm_hook_defs.h > @@ -223,6 +223,7 @@ LSM_HOOK(int, -ENOSYS, task_prctl, int option, unsigned long arg2, > unsigned long arg3, unsigned long arg4, unsigned long arg5) > LSM_HOOK(void, LSM_RET_VOID, task_to_inode, struct task_struct *p, > struct inode *inode) > +LSM_HOOK(int, 0, userns_create, const struct cred *cred) > LSM_HOOK(int, 0, ipc_permission, struct kern_ipc_perm *ipcp, short flag) > LSM_HOOK(void, LSM_RET_VOID, ipc_getsecid, struct kern_ipc_perm *ipcp, > u32 *secid) > diff --git a/include/linux/lsm_hooks.h b/include/linux/lsm_hooks.h > index 91c8146649f5..54fe534d0e01 100644 > --- a/include/linux/lsm_hooks.h > +++ b/include/linux/lsm_hooks.h > @@ -799,6 +799,10 @@ > * security attributes, e.g. for /proc/pid inodes. > * @p contains the task_struct for the task. > * @inode contains the inode structure for the inode. > + * @userns_create: > + * Check permission prior to creating a new user namespace. > + * @cred points to prepared creds. > + * Return 0 if successful, otherwise < 0 error code. > * > * Security hooks for Netlink messaging. > * > diff --git a/include/linux/security.h b/include/linux/security.h > index 7fc4e9f49f54..a195bf33246a 100644 > --- a/include/linux/security.h > +++ b/include/linux/security.h > @@ -435,6 +435,7 @@ int security_task_kill(struct task_struct *p, struct kernel_siginfo *info, > int security_task_prctl(int option, unsigned long arg2, unsigned long arg3, > unsigned long arg4, unsigned long arg5); > void security_task_to_inode(struct task_struct *p, struct inode *inode); > +int security_create_user_ns(const struct cred *cred); > int security_ipc_permission(struct kern_ipc_perm *ipcp, short flag); > void security_ipc_getsecid(struct kern_ipc_perm *ipcp, u32 *secid); > int security_msg_msg_alloc(struct msg_msg *msg); > @@ -1185,6 +1186,11 @@ static inline int security_task_prctl(int option, unsigned long arg2, > static inline void security_task_to_inode(struct task_struct *p, struct inode *inode) > { } > > +static inline int security_create_user_ns(const struct cred *cred) > +{ > + return 0; > +} > + > static inline int security_ipc_permission(struct kern_ipc_perm *ipcp, > short flag) > { > diff --git a/kernel/user_namespace.c b/kernel/user_namespace.c > index 5481ba44a8d6..3f464bbda0e9 100644 > --- a/kernel/user_namespace.c > +++ b/kernel/user_namespace.c > @@ -9,6 +9,7 @@ > #include > #include > #include > +#include > #include > #include > #include > @@ -113,6 +114,10 @@ int create_user_ns(struct cred *new) > !kgid_has_mapping(parent_ns, group)) > goto fail_dec; > > + ret = security_create_user_ns(new); > + if (ret < 0) > + goto fail_dec; > + > ret = -ENOMEM; > ns = kmem_cache_zalloc(user_ns_cachep, GFP_KERNEL); > if (!ns) > diff --git a/security/security.c b/security/security.c > index 188b8f782220..ec9b4696e86c 100644 > --- a/security/security.c > +++ b/security/security.c > @@ -1903,6 +1903,11 @@ void security_task_to_inode(struct task_struct *p, struct inode *inode) > call_void_hook(task_to_inode, p, inode); > } > > +int security_create_user_ns(const struct cred *cred) > +{ > + return call_int_hook(userns_create, 0, cred); > +} > + > int security_ipc_permission(struct kern_ipc_perm *ipcp, short flag) > { > return call_int_hook(ipc_permission, 0, ipcp, flag); > -- > 2.30.2 >