From patchwork Thu Jun 9 23:01:21 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876085 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id A794EC43334 for ; Thu, 9 Jun 2022 23:05:32 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1345867AbiFIXF1 (ORCPT ); Thu, 9 Jun 2022 19:05:27 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:58560 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1345871AbiFIXFV (ORCPT ); Thu, 9 Jun 2022 19:05:21 -0400 Received: from sonic301-38.consmr.mail.ne1.yahoo.com (sonic301-38.consmr.mail.ne1.yahoo.com [66.163.184.207]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 24E1FA3C26 for ; Thu, 9 Jun 2022 16:05:19 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654815918; bh=9jUZwLW4KWH1kzKdw9qNpe66c2Aiuqh5NAN3p+Ltk6g=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=XGV2n8m79iduH9KxK8jHXesCmAMnpGyA9H8krj5UduGmrbvthnZNN7h2Dz33PNZqqM7jq+SkgydB4RSw/xJYRhUlG5nylRWSpKjA1pT3pGMU8A0Xu/bMbpX8pkCxFrukFeGJNMOUU3IcwErafwGWyReao/m+EWwzvLET4nXgk/HDdKeCLIF7BS2IXk2mxMIqBpgYGaJ60nVIBWYNnzSktiMWPMy5GBG82C3rc6bDHXWULozdfXmX9G7/clieK7nLNa21hrE+DTzLwHjNJklcLeHuPiJyB24r56kWj10dr0NaeWuF1fcU8cSav6FN2/Vu7Rlwl+stYXyFjMRWbkdXWQ== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654815918; bh=LrPzdmfOoNN4I8dNsqtDrrpjOa86BWePtUJg7YgaYCR=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=E2vJ0JjeWwiQhrWAUNBI7oSSIeSYI2UsAl23ooZL6BfDnOeCZ+Wu4/mt32q5RcKBOyJBFzeMNiNMHhBrJen3A7cqvneK2v6GikunHqc6zlvOzhCfm24hH7nndDN2iGRzVQaKNQX3+nzLkSo9Q/u8LwelUBvv9CmvogO1xkUnShs6ioIjg6b5R3gfsXFHMR76EXEBNQj2U68X+p+2jkXV22916gBeechQAKXZ/kcIipb5vISfF6iNbIEYkLFiSmHInLL1QqUz5mBnREW+atUg2jqqxbmAz2DzdOgo6nyXm7UFb3o9IvXSEo3qWMgylDdZpW62/FTU+1rn/8A4hfkO9w== X-YMail-OSG: GweqzFUVM1kUtL6z32ycSut04rQpfUFYG94Ur1JiWugWXy0uUYDiAIgZ7fQt_yx kYaqlT1xWdm0dkqEe85FlkA6zZlXQLTc2txRRBJp030t5pdzDyPyhi5eWHlhLH3C6HjVDBlReFhv dO0kd1hinnHU8m0E6Fa.1NbGoEr0ZHAm4UiximkJ47wsdxxEeW6gNXWY8wHqOEC5ZmsPqS7g.5SP WwLb9YkE983glSo0Ersci1VhCg6uz3o8Qs5HC7QAifkGTwqZSWf_HiOAlDOI2J8oI7xP4fft.y7C L1WSVlCRLFMayyiv.iw471jxLnCBBfrD6oQee0bum2WpF8Qk4rEBoLcUOuxIO0AzbproiYA9fGQm Smef64G.6wFspC3nOG.4F9NzncwFqgwz9C_y6zTSZof2uYZ8ocAb2jhATRxkUG6x3reMo8wgFQez LUDkPGn4yDlhRrUEkGkBxwIVFCl0ZU40YqJMlJ246pKdrOM_k.JYgOiELqeKEhmjsdBrT6DpKRPY mh5Vqt1s.UCdbgqJWG.s7LI9TDL0M2RkUvTHLf.ssBspX2S79BQySVIiimCXBLiV6AcfQ.vRcjP5 1QIEGp7jdLBOWdPWif3vLmNCc2GK_qtehIGWTA53lO.Ike5GWSikBpl7yc7iQ6gmXpBBTEFDur2P Xf1XMv4hCu2y0ZPcDDEVOcQsRwY16HIIhR4gPfffZ_6zzltt_bIgw4OIsoKQlkr9FJ.nowcSpCmh .2Fw4l89ea0UT3Nq3XrL0KGFhTII.Zj4bkX6q2VYGsAft_2pzBI8hy8JrI1QC_qSOKHk5E0PbWoF HINeqE8X4WJANZ2QBYwl4JWE9g5w9AYczGYaZEB7KUYESo7hkOTTFod7Pn2t.o2RuTEDjXVC8rV3 bUhb8oUARggD8Hmzc_..kgjLvNGoKEKg1V7THw_dXT20weA1GlbNytNXyngRf85JHE0XlL2EyALn hP.25JCEEoyt.DA2O2VXs1Iq6B_OaLo9362Eoeg1WcRUFgGnxyqdX1iQJG1Kv1fwTuDj4BfVG9X0 zRhDH_n4M9_MoAzXB.NUlCmdMs.kMNxJkB8Mc3sLeX1JEJ.geRhDBuYD7u_i7VniNXLDdfsjO4vI NBMtxFSNx7lR48Sv9GN_MZHCo9YQYKKLddHIivovQcsVBkY4wfkPGgAvlt70py8Poe1HesyXHiZK r1czegmHW.1ALUp6WxzUr.2p7ljh7BSxXI1eJB0dlslJD.ezMHd9G727y5g6uVvOqYUnRcg6.vZU mCi_daZnQ3hzGse6pcFIk7MvgNzUL2QtrutitNf3TCW99t4l7zU8HKlmfSQPZfGuseRY2Bzbnc1G dxp5sq_HTurE98VRCBTNTzWHjefgXOACjN9QVHePleHG5b4yRMwljLLAPNXvNoPVR_iyqsrCvBD9 .e0sMNOOf8BPr56fOro_UhOY2ufTPQu458ChtsZWec0vcunF8F02TVoAzXZBuyAzFJP8yznIqBOw vPuDJrsocQGvHLb0urifrEkwbJkepk5M.qk__XZK4MXbv0d5kr.8KKWPoIJBgFaaCO7D_0oPVQCJ 5K1kK.gQf06UapMH1rOKTZ8QNCz_wUQFdjRhuVsim_AzP2qCFm_r1sqL7F1PSiyV23xPu3nsEsah s0uOWGIMy2rAqnZvgUG2KXwTdSUD1yGr7XHxxnZSkS924Wt6Yl6Z_.H5aA31FVqjrDHBR3CG.oxa LWFqtKh61xWm5b8yZJnNusKDRAFwbPvVl.yks70rpTn8WUvf_l99ho9vJdrnYhT0493H5Uq.NwbA TJTdgaWaAP1RLmDJgYa.z6d73cQMgxV5Tpw_48lp8n65Z1dOgzS1Ugl1o22aYNPVic97_VjUUyvo HDvAe6ddHDgZu_bZtHDS_vHzBz1MjwUpGxask0NG33bLOg9PT2chq0B74sgc1p_7GnV68MYIblzT 6IogLd_HKv0YnYH40LVluAS.O_jCJrOd__bCEfGluW4lxVNQqa3WtI4ZPWEyh5BtRGOmj9Yle5WU W7GnTK49kAOrtAGuNV0M1XqZNMiZZTxvErK898fYchu02Zn5AfY.1aVL9VSkRckGEm9EKBnP.7lc MHkZEC6qzxFy0Bx8msx1AWvrpb4viyFgXbDyMe2Lu411YtUHz8tm2ayx6zSdu1JcKCQLKlWc7xTZ KUBiKcHw51IJRkh6T8aw10V.D39VvdsTjmH1qg3_uxdggMShluLWhZ8LsOLBHKaVNz.MykfuyAop oJWR0wll3l.hCGSI90zNMd73WPv64ZtLwEpuK0q7vIoMe4choM.jkhW5Un7RUpFdrTV98_AnrAbR OWandOO0DP89vFoMGfs59ri2CvNeQyFxrMke3TZdMNdmRJHrwmUZXe5aPnCKYqICsgkQikbtv5FV QRXuuR9oi X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic301.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:05:18 +0000 Received: by hermes--canary-production-bf1-856dbf94db-mq9q8 (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID a994d58746f340bf5c8b571efdccf4f1; Thu, 09 Jun 2022 23:05:13 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, netfilter-devel@vger.kernel.org Subject: [PATCH v36 08/33] LSM: Use lsmblob in security_secctx_to_secid Date: Thu, 9 Jun 2022 16:01:21 -0700 Message-Id: <20220609230146.319210-9-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Change the security_secctx_to_secid interface to use a lsmblob structure in place of the single u32 secid in support of module stacking. Change its callers to do the same. The security module hook is unchanged, still passing back a secid. The infrastructure passes the correct entry from the lsmblob. Acked-by: Paul Moore Reviewed-by: Kees Cook Signed-off-by: Casey Schaufler Cc: netdev@vger.kernel.org Cc: netfilter-devel@vger.kernel.org To: Pablo Neira Ayuso --- include/linux/security.h | 26 ++++++++++++++++++-- kernel/cred.c | 4 +--- net/netfilter/nft_meta.c | 10 ++++---- net/netfilter/xt_SECMARK.c | 7 +++++- net/netlabel/netlabel_unlabeled.c | 23 +++++++++++------- security/security.c | 40 ++++++++++++++++++++++++++----- 6 files changed, 85 insertions(+), 25 deletions(-) diff --git a/include/linux/security.h b/include/linux/security.h index 823880ba613e..8e09302bded7 100644 --- a/include/linux/security.h +++ b/include/linux/security.h @@ -201,6 +201,27 @@ static inline bool lsmblob_equal(const struct lsmblob *bloba, extern int lsm_name_to_slot(char *name); extern const char *lsm_slot_to_name(int slot); +/** + * lsmblob_value - find the first non-zero value in an lsmblob structure. + * @blob: Pointer to the data + * + * This needs to be used with extreme caution, as the cases where + * it is appropriate are rare. + * + * Return the first secid value set in the lsmblob. + * There should only be one. + */ +static inline u32 lsmblob_value(const struct lsmblob *blob) +{ + int i; + + for (i = 0; i < LSMBLOB_ENTRIES; i++) + if (blob->secid[i]) + return blob->secid[i]; + + return 0; +} + /* These functions are in security/commoncap.c */ extern int cap_capable(const struct cred *cred, struct user_namespace *ns, int cap, unsigned int opts); @@ -531,7 +552,8 @@ int security_setprocattr(const char *lsm, const char *name, void *value, int security_netlink_send(struct sock *sk, struct sk_buff *skb); int security_ismaclabel(const char *name); int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen); -int security_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid); +int security_secctx_to_secid(const char *secdata, u32 seclen, + struct lsmblob *blob); void security_release_secctx(char *secdata, u32 seclen); void security_inode_invalidate_secctx(struct inode *inode); int security_inode_notifysecctx(struct inode *inode, void *ctx, u32 ctxlen); @@ -1386,7 +1408,7 @@ static inline int security_secid_to_secctx(u32 secid, char **secdata, u32 *secle static inline int security_secctx_to_secid(const char *secdata, u32 seclen, - u32 *secid) + struct lsmblob *blob) { return -EOPNOTSUPP; } diff --git a/kernel/cred.c b/kernel/cred.c index 3925d38f49f4..adea727744f4 100644 --- a/kernel/cred.c +++ b/kernel/cred.c @@ -791,14 +791,12 @@ EXPORT_SYMBOL(set_security_override); int set_security_override_from_ctx(struct cred *new, const char *secctx) { struct lsmblob blob; - u32 secid; int ret; - ret = security_secctx_to_secid(secctx, strlen(secctx), &secid); + ret = security_secctx_to_secid(secctx, strlen(secctx), &blob); if (ret < 0) return ret; - lsmblob_init(&blob, secid); return set_security_override(new, &blob); } EXPORT_SYMBOL(set_security_override_from_ctx); diff --git a/net/netfilter/nft_meta.c b/net/netfilter/nft_meta.c index ac4859241e17..fc0028c9e33d 100644 --- a/net/netfilter/nft_meta.c +++ b/net/netfilter/nft_meta.c @@ -860,21 +860,21 @@ static const struct nla_policy nft_secmark_policy[NFTA_SECMARK_MAX + 1] = { static int nft_secmark_compute_secid(struct nft_secmark *priv) { - u32 tmp_secid = 0; + struct lsmblob blob; int err; - err = security_secctx_to_secid(priv->ctx, strlen(priv->ctx), &tmp_secid); + err = security_secctx_to_secid(priv->ctx, strlen(priv->ctx), &blob); if (err) return err; - if (!tmp_secid) + if (!lsmblob_is_set(&blob)) return -ENOENT; - err = security_secmark_relabel_packet(tmp_secid); + err = security_secmark_relabel_packet(lsmblob_value(&blob)); if (err) return err; - priv->secid = tmp_secid; + priv->secid = lsmblob_value(&blob); return 0; } diff --git a/net/netfilter/xt_SECMARK.c b/net/netfilter/xt_SECMARK.c index 498a0bf6f044..87ca3a537d1c 100644 --- a/net/netfilter/xt_SECMARK.c +++ b/net/netfilter/xt_SECMARK.c @@ -42,13 +42,14 @@ secmark_tg(struct sk_buff *skb, const struct xt_secmark_target_info_v1 *info) static int checkentry_lsm(struct xt_secmark_target_info_v1 *info) { + struct lsmblob blob; int err; info->secctx[SECMARK_SECCTX_MAX - 1] = '\0'; info->secid = 0; err = security_secctx_to_secid(info->secctx, strlen(info->secctx), - &info->secid); + &blob); if (err) { if (err == -EINVAL) pr_info_ratelimited("invalid security context \'%s\'\n", @@ -56,6 +57,10 @@ static int checkentry_lsm(struct xt_secmark_target_info_v1 *info) return err; } + /* xt_secmark_target_info can't be changed to use lsmblobs because + * it is exposed as an API. Use lsmblob_value() to get the one + * value that got set by security_secctx_to_secid(). */ + info->secid = lsmblob_value(&blob); if (!info->secid) { pr_info_ratelimited("unable to map security context \'%s\'\n", info->secctx); diff --git a/net/netlabel/netlabel_unlabeled.c b/net/netlabel/netlabel_unlabeled.c index 8490e46359ae..f3e2cde76919 100644 --- a/net/netlabel/netlabel_unlabeled.c +++ b/net/netlabel/netlabel_unlabeled.c @@ -880,7 +880,7 @@ static int netlbl_unlabel_staticadd(struct sk_buff *skb, void *addr; void *mask; u32 addr_len; - u32 secid; + struct lsmblob blob; struct netlbl_audit audit_info; /* Don't allow users to add both IPv4 and IPv6 addresses for a @@ -904,13 +904,18 @@ static int netlbl_unlabel_staticadd(struct sk_buff *skb, ret_val = security_secctx_to_secid( nla_data(info->attrs[NLBL_UNLABEL_A_SECCTX]), nla_len(info->attrs[NLBL_UNLABEL_A_SECCTX]), - &secid); + &blob); if (ret_val != 0) return ret_val; + /* netlbl_unlhsh_add will be changed to pass a struct lsmblob * + * instead of a u32 later in this patch set. security_secctx_to_secid() + * will only be setting one entry in the lsmblob struct, so it is + * safe to use lsmblob_value() to get that one value. */ + return netlbl_unlhsh_add(&init_net, - dev_name, addr, mask, addr_len, secid, - &audit_info); + dev_name, addr, mask, addr_len, + lsmblob_value(&blob), &audit_info); } /** @@ -931,7 +936,7 @@ static int netlbl_unlabel_staticadddef(struct sk_buff *skb, void *addr; void *mask; u32 addr_len; - u32 secid; + struct lsmblob blob; struct netlbl_audit audit_info; /* Don't allow users to add both IPv4 and IPv6 addresses for a @@ -953,13 +958,15 @@ static int netlbl_unlabel_staticadddef(struct sk_buff *skb, ret_val = security_secctx_to_secid( nla_data(info->attrs[NLBL_UNLABEL_A_SECCTX]), nla_len(info->attrs[NLBL_UNLABEL_A_SECCTX]), - &secid); + &blob); if (ret_val != 0) return ret_val; + /* security_secctx_to_secid() will only put one secid into the lsmblob + * so it's safe to use lsmblob_value() to get the secid. */ return netlbl_unlhsh_add(&init_net, - NULL, addr, mask, addr_len, secid, - &audit_info); + NULL, addr, mask, addr_len, + lsmblob_value(&blob), &audit_info); } /** diff --git a/security/security.c b/security/security.c index d3b28a6b9248..08ed7acf4205 100644 --- a/security/security.c +++ b/security/security.c @@ -2205,10 +2205,22 @@ int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen) } EXPORT_SYMBOL(security_secid_to_secctx); -int security_secctx_to_secid(const char *secdata, u32 seclen, u32 *secid) +int security_secctx_to_secid(const char *secdata, u32 seclen, + struct lsmblob *blob) { - *secid = 0; - return call_int_hook(secctx_to_secid, 0, secdata, seclen, secid); + struct security_hook_list *hp; + int rc; + + lsmblob_init(blob, 0); + hlist_for_each_entry(hp, &security_hook_heads.secctx_to_secid, list) { + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) + continue; + rc = hp->hook.secctx_to_secid(secdata, seclen, + &blob->secid[hp->lsmid->slot]); + if (rc != 0) + return rc; + } + return 0; } EXPORT_SYMBOL(security_secctx_to_secid); @@ -2359,10 +2371,26 @@ int security_socket_getpeersec_stream(struct socket *sock, char __user *optval, optval, optlen, len); } -int security_socket_getpeersec_dgram(struct socket *sock, struct sk_buff *skb, u32 *secid) +int security_socket_getpeersec_dgram(struct socket *sock, struct sk_buff *skb, + u32 *secid) { - return call_int_hook(socket_getpeersec_dgram, -ENOPROTOOPT, sock, - skb, secid); + struct security_hook_list *hp; + int rc = -ENOPROTOOPT; + + /* + * Only one security module should provide a real hook for + * this. A stub or bypass like is used in BPF should either + * (somehow) leave rc unaltered or return -ENOPROTOOPT. + */ + hlist_for_each_entry(hp, &security_hook_heads.socket_getpeersec_dgram, + list) { + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) + continue; + rc = hp->hook.socket_getpeersec_dgram(sock, skb, secid); + if (rc != -ENOPROTOOPT) + break; + } + return rc; } EXPORT_SYMBOL(security_socket_getpeersec_dgram); From patchwork Thu Jun 9 23:01:22 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876086 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id B7D9ACCA473 for ; Thu, 9 Jun 2022 23:06:57 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S239457AbiFIXGz (ORCPT ); Thu, 9 Jun 2022 19:06:55 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:37058 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231710AbiFIXGw (ORCPT ); Thu, 9 Jun 2022 19:06:52 -0400 Received: from sonic304-28.consmr.mail.ne1.yahoo.com (sonic304-28.consmr.mail.ne1.yahoo.com [66.163.191.154]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 06D8826C0D5 for ; Thu, 9 Jun 2022 16:06:49 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816009; bh=nefeTtnhXzPjjsSwoDn1M1Z5DUt1kxzzojqO9qby85s=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=GWPGq+0Z4TqOwRoaCxAGSwLDWt8MSQl3VdtkHb5L2jB2Djm7XVU9B3oJ6F2v/f/In3uMBAwWRK+1tQz9R9X4sn79k/agnpxAy/08mYtiSxlvi8xDyP/LENNu7ebIUpN6gMTO6TtVKvk7XAeJ93faXsb51cAQiabFo9/fptWzpuYM4NeuDlG2xX9kPpMDL+EGprC9K4KX+CkM22Y30ve69hYBy6A3e0dIgLQ9yV0d3uUNUUF3DuBVAxtEYFsln8tcS7Jy42qFwvI2LrZ/wMAPtNC9YYbzUiG2ujiMJSLoweg+kWCkfaeEOzkHrHo7Y8AjAQxeSXfXSRui/MyukWsRTw== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816009; bh=QMS6zo77mQAAdq7Abuil2+qo6QCmsBzMnj94lDY9xYn=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=TpTqhtQofO2IrIYptFKrdQT4iGQs6sMwUII31IBE+b1vVQi9SEXNSUvS8PLV7bLQTIOwQ325Vkcyfg9UGSbcURIyRu882dGAi8VE/gFIIIBdWVqZ7X7aD+EhVmEylRrUSl3AubKzSjiCtXaKQYZNH5VLSum0Adc7CE1n9G4UAo1fpGRJeqxX3tM32pVN2LwS4L2tBUO1glYtKjT46ujlL4OV9mbJhq8DTPuU7VNXk0Tg99Jgr0oerU+PYdYgg4JGL3U/ULLc4Kw2v0Nf0Z0ZtprSBK3iXtJMFdU0Pp280br903C0jMuzLeWdieElu7Y84WrwqyIdDAmZdJjUCb1gRQ== X-YMail-OSG: _OIvWnMVM1nwdvuBJFTT7loZ2_RYrKH68rB_yPqv.EUKBF92Eh8lug8vkqdGE9p 5_O1rKKic8iCmsEDmrIUU9UQNhL.S9dZsZgF9WlRfJAS4ll4hIm0Mku7NgLzObszGKOHwGjTKxmG rzNW.LvHSA8wiWjgwHBzy2jdHCMGGKEvPORGRJ_.gKwOYq3Q2fyYhqs5leauPcURVY5PzLBe5tV1 JzEancb2DJMGkH.sDw9.wUrv1vVEVEG_K8Q4xyKCZZkoX_gVx.af_FqOD7qtc.tdMRFFlNS4HOik D0iTsH0jZ.6Wq.rvMvd5DIwN6XiTO9ax645P3CJsi.9.UYMO.tG8dJ0pIGpZUZ6Bb6_n1jJkQk9. pV1oAWEDdK7zVhOrWoawtLDAWSA25XSTvlHGhyHoB.Ob4Htf88stUjmAjYvxU.Gsyt7KKOPbCGcF vMXh8c3vIMMOQxivmF7A84_B9QM3AtXIh0._vIMum69FxqK55uDa5zoQc_sovcdtknHY4KeHGU5c j7iY.VI725rYg_kl2zedMD6idsSLO4QEFHfsvj355b8WJtqH7gAKbKl8b1.GEvQbix75J4J_IlAi jAAqIQ_Km_w2NMqfFeF73IvvHKq3gYSniSz.Or4FdVMrYVZ0GxMzBvh7L83fgRQOf9lIOeHj14wC ocIe9AGdkEVekM.CcDpRXcjH9eLVs._Vu0jv34ftyUl7rbaE4Fxon9iYXplmjDfCOKYgUj1.o.yT wBsdBMN6a1OrmN2UTrTbxyv_qzgrjHY.VF.CSU0I8CL8heWClkVNlO0FUVPjWHHSdebBGfuMWM9P avcisbEeazkX6Jv628vMXMDRGSxJz8Wp8sZG4PVqkbpDTfS0gL78OQnd8UW_vWlg0g3mAu3VM6bu s4XgGpTohl_g1d5I9nh_l2Vo_1UOvsX0Huwc3EBkTz9Gn2xPtig06bZZesffpF.ik9ftKeTKS5vQ U1IiExM3TtgqdeZqa.w5iuBpmwmmh0arL6zFJaa2Q4kQ7vWoaa1vePZP1B4kPZxPB2JW1hnjI8bB lcfjzToiB_LukVeyISHEzH0YFVOkDkKfhk9X0pXHO3wbNgadwl7kj2GuXDUPEdaAwOZAiosMvEHM 3.UO_xqf7zfVSQCXYzVVPHd8PEv1K3ZuzZqD5fvPHyNmx5bb2PZKoL8_4pI4Xq.LNy9FynuQpWvC nk5gVqVAxfdOIJgN7rhpa9VJLpd0Ndz..Lh0KDzFY_2nV9OZzy2spKymJNV4EL33u7ua9NfAKCJN HA_2ztxVarHePJv4QT0_48yva.bdenOAvQnQK3GjnkDkjm_JV6Jv1NJLi6wsVIE4ujE784F6Zi5Z vUCJJRD0f2o9XdArnDFyzyq2.ziVvknXidlB2YGY45UaeTts6cRD42S3mouXmwFRXDq4udjAT6C8 PQ9MfJ.MAkj1GSLSiaFQ3pdF1NesH7z2sMIMup_iqc3t3cDggDxt2gpsFMRZ5xc3lvm1Dmu7zQVc 1s0zWFs_1PAM1_kWk3RRuZwjxmZrEmSAnGSL5OQGqoZ3NQo5.y9GrVe7UsuV5ain4Y3PqV1o_G9c x9P2CsrTdVYIsfTgO8gRa4VopfG2itQ6.c914MEDqg4kru2ArBWZobhK_jB4plNYCLJtIGJ_c4z0 VpDyb7YfQzCUJXEoQzw4V.wyeLkL3e9QID2SvLLsEwoL4NNwtK_VPIOofgRWzXVaMOvI3yoWIv5U 7qfgaotVpTthjyaK2pWtfIhVAkz37CMlUSXNsfyF1aT6qcN8GHlaaVWBNG8NVLcgYttG.4E._Akx 03sD.0.7CM64_5jjxAvc6MXe9GM7emukbut1i7.3vDOF7h1ZZVXbDyA8mPfqqbE6sqKREOX37nQu yJoSXME7LTGDDh5DNjqFFm7qbzY0w8S0Vk2zu7MQpnBdC7.UiICihuE.R2GOcs89UA6eTsCN0oMz ZOrIiXUpK2gsIJgurIpZR96BfVTxXKvTvXIb4QBTXXYqVvUgUxfhh5rjO4761_CT.z9Tw8sUMegd CRXFN4aeqvfHP0yFE524BhAmhejMo2znjFusvwtWuZjA5csxEAJ.brnwHZW1V9SgTK4Z5tzPelF6 AI0XFbcrQxBKiBpEkoO7VscE1P.UpMsJDQHaQIbpg2JJZg9xOj_4b4k1bFSHqqeRSjx6QWYmNieO AxZnfXM4I4GkOD7m0ZD_tTudXyKdMO5BT4kSHtMwGgHeXXC19DZ3cOLaAoS7DLy44rPPqqzxPiw2 BMrv4CrN4HrWK6.v.CK19oHyp757ge_Ssf7KzOCrcugTxLOlHGR.lh54gIp24KUn3vehERz.EazE Z6CDXms_fLuy9NHN955fPPBQSwFnJgP8- X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic304.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:06:49 +0000 Received: by hermes--canary-production-ne1-799d7bd497-2pzdr (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID b20ca8b25547b2b344a65fa8c4e3e611; Thu, 09 Jun 2022 23:06:46 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, netfilter-devel@vger.kernel.org Subject: [PATCH v36 09/33] LSM: Use lsmblob in security_secid_to_secctx Date: Thu, 9 Jun 2022 16:01:22 -0700 Message-Id: <20220609230146.319210-10-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Change security_secid_to_secctx() to take a lsmblob as input instead of a u32 secid. It will then call the LSM hooks using the lsmblob element allocated for that module. The callers have been updated as well. This allows for the possibility that more than one module may be called upon to translate a secid to a string, as can occur in the audit code. Acked-by: Paul Moore Reviewed-by: Kees Cook Signed-off-by: Casey Schaufler Cc: netdev@vger.kernel.org Cc: linux-audit@redhat.com Cc: netfilter-devel@vger.kernel.org To: Pablo Neira Ayuso --- drivers/android/binder.c | 12 +++++++++- include/linux/security.h | 5 +++-- include/net/scm.h | 7 +++++- kernel/audit.c | 21 +++++++++++++++-- kernel/auditsc.c | 27 ++++++++++++++++++---- net/ipv4/ip_sockglue.c | 4 +++- net/netfilter/nf_conntrack_netlink.c | 14 ++++++++++-- net/netfilter/nf_conntrack_standalone.c | 4 +++- net/netfilter/nfnetlink_queue.c | 11 +++++++-- net/netlabel/netlabel_unlabeled.c | 30 +++++++++++++++++++++---- net/netlabel/netlabel_user.c | 6 ++--- security/security.c | 11 +++++---- 12 files changed, 123 insertions(+), 29 deletions(-) diff --git a/drivers/android/binder.c b/drivers/android/binder.c index 362c0deb65f1..4ead3360a1c0 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c @@ -3055,10 +3055,20 @@ static void binder_transaction(struct binder_proc *proc, if (target_node && target_node->txn_security_ctx) { u32 secid; + struct lsmblob blob; size_t added_size; security_cred_getsecid(proc->cred, &secid); - ret = security_secid_to_secctx(secid, &secctx, &secctx_sz); + /* + * Later in this patch set security_task_getsecid() will + * provide a lsmblob instead of a secid. lsmblob_init + * is used to ensure that all the secids in the lsmblob + * get the value returned from security_task_getsecid(), + * which means that the one expected by + * security_secid_to_secctx() will be set. + */ + lsmblob_init(&blob, secid); + ret = security_secid_to_secctx(&blob, &secctx, &secctx_sz); if (ret) { binder_txn_error("%d:%d failed to get security context\n", thread->pid, proc->pid); diff --git a/include/linux/security.h b/include/linux/security.h index 8e09302bded7..e8e4a7a1029b 100644 --- a/include/linux/security.h +++ b/include/linux/security.h @@ -551,7 +551,7 @@ int security_setprocattr(const char *lsm, const char *name, void *value, size_t size); int security_netlink_send(struct sock *sk, struct sk_buff *skb); int security_ismaclabel(const char *name); -int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen); +int security_secid_to_secctx(struct lsmblob *blob, char **secdata, u32 *seclen); int security_secctx_to_secid(const char *secdata, u32 seclen, struct lsmblob *blob); void security_release_secctx(char *secdata, u32 seclen); @@ -1401,7 +1401,8 @@ static inline int security_ismaclabel(const char *name) return 0; } -static inline int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen) +static inline int security_secid_to_secctx(struct lsmblob *blob, + char **secdata, u32 *seclen) { return -EOPNOTSUPP; } diff --git a/include/net/scm.h b/include/net/scm.h index 1ce365f4c256..23a35ff1b3f2 100644 --- a/include/net/scm.h +++ b/include/net/scm.h @@ -92,12 +92,17 @@ static __inline__ int scm_send(struct socket *sock, struct msghdr *msg, #ifdef CONFIG_SECURITY_NETWORK static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct scm_cookie *scm) { + struct lsmblob lb; char *secdata; u32 seclen; int err; if (test_bit(SOCK_PASSSEC, &sock->flags)) { - err = security_secid_to_secctx(scm->secid, &secdata, &seclen); + /* There can only be one security module using the secid, + * and the infrastructure will know which it is. + */ + lsmblob_init(&lb, scm->secid); + err = security_secid_to_secctx(&lb, &secdata, &seclen); if (!err) { put_cmsg(msg, SOL_SOCKET, SCM_SECURITY, seclen, secdata); diff --git a/kernel/audit.c b/kernel/audit.c index 7690c29d4ee4..2acf95cf9895 100644 --- a/kernel/audit.c +++ b/kernel/audit.c @@ -1464,7 +1464,16 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) case AUDIT_SIGNAL_INFO: len = 0; if (audit_sig_sid) { - err = security_secid_to_secctx(audit_sig_sid, &ctx, &len); + struct lsmblob blob; + + /* + * lsmblob_init sets all values in the lsmblob + * to audit_sig_sid. This is temporary until + * audit_sig_sid is converted to a lsmblob, which + * happens later in this patch set. + */ + lsmblob_init(&blob, audit_sig_sid); + err = security_secid_to_secctx(&blob, &ctx, &len); if (err) return err; } @@ -2170,12 +2179,20 @@ int audit_log_task_context(struct audit_buffer *ab) unsigned len; int error; u32 sid; + struct lsmblob blob; security_current_getsecid_subj(&sid); if (!sid) return 0; - error = security_secid_to_secctx(sid, &ctx, &len); + /* + * lsmblob_init sets all values in the lsmblob to sid. + * This is temporary until security_task_getsecid is converted + * to use a lsmblob, which happens later in this patch set. + */ + lsmblob_init(&blob, sid); + error = security_secid_to_secctx(&blob, &ctx, &len); + if (error) { if (error != -EINVAL) goto error_path; diff --git a/kernel/auditsc.c b/kernel/auditsc.c index 7701dba499f5..58e3f39f47ab 100644 --- a/kernel/auditsc.c +++ b/kernel/auditsc.c @@ -679,6 +679,13 @@ static int audit_filter_rules(struct task_struct *tsk, security_current_getsecid_subj(&sid); need_sid = 0; } + /* + * lsmblob_init sets all values in the lsmblob + * to sid. This is temporary until + * security_task_getsecid() is converted to + * provide a lsmblob, which happens later in + * this patch set. + */ lsmblob_init(&blob, sid); result = security_audit_rule_match(&blob, f->type, f->op, @@ -695,6 +702,13 @@ static int audit_filter_rules(struct task_struct *tsk, if (f->lsm_str) { /* Find files that match */ if (name) { + /* + * lsmblob_init sets all values in the + * lsmblob to sid. This is temporary + * until name->osid is converted to a + * lsmblob, which happens later in + * this patch set. + */ lsmblob_init(&blob, name->osid); result = security_audit_rule_match( &blob, @@ -1118,6 +1132,7 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid, char *ctx = NULL; u32 len; int rc = 0; + struct lsmblob blob; ab = audit_log_start(context, GFP_KERNEL, AUDIT_OBJ_PID); if (!ab) @@ -1127,7 +1142,8 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid, from_kuid(&init_user_ns, auid), from_kuid(&init_user_ns, uid), sessionid); if (sid) { - if (security_secid_to_secctx(sid, &ctx, &len)) { + lsmblob_init(&blob, sid); + if (security_secid_to_secctx(&blob, &ctx, &len)) { audit_log_format(ab, " obj=(none)"); rc = 1; } else { @@ -1418,8 +1434,10 @@ static void show_special(struct audit_context *context, int *call_panic) if (osid) { char *ctx = NULL; u32 len; + struct lsmblob blob; - if (security_secid_to_secctx(osid, &ctx, &len)) { + lsmblob_init(&blob, osid); + if (security_secid_to_secctx(&blob, &ctx, &len)) { audit_log_format(ab, " osid=%u", osid); *call_panic = 1; } else { @@ -1585,9 +1603,10 @@ static void audit_log_name(struct audit_context *context, struct audit_names *n, if (n->osid != 0) { char *ctx = NULL; u32 len; + struct lsmblob blob; - if (security_secid_to_secctx( - n->osid, &ctx, &len)) { + lsmblob_init(&blob, n->osid); + if (security_secid_to_secctx(&blob, &ctx, &len)) { audit_log_format(ab, " osid=%u", n->osid); if (call_panic) *call_panic = 2; diff --git a/net/ipv4/ip_sockglue.c b/net/ipv4/ip_sockglue.c index 445a9ecaefa1..933a8f94f93a 100644 --- a/net/ipv4/ip_sockglue.c +++ b/net/ipv4/ip_sockglue.c @@ -130,6 +130,7 @@ static void ip_cmsg_recv_checksum(struct msghdr *msg, struct sk_buff *skb, static void ip_cmsg_recv_security(struct msghdr *msg, struct sk_buff *skb) { + struct lsmblob lb; char *secdata; u32 seclen, secid; int err; @@ -138,7 +139,8 @@ static void ip_cmsg_recv_security(struct msghdr *msg, struct sk_buff *skb) if (err) return; - err = security_secid_to_secctx(secid, &secdata, &seclen); + lsmblob_init(&lb, secid); + err = security_secid_to_secctx(&lb, &secdata, &seclen); if (err) return; diff --git a/net/netfilter/nf_conntrack_netlink.c b/net/netfilter/nf_conntrack_netlink.c index 722af5e309ba..ddc8cd65ed12 100644 --- a/net/netfilter/nf_conntrack_netlink.c +++ b/net/netfilter/nf_conntrack_netlink.c @@ -347,8 +347,13 @@ static int ctnetlink_dump_secctx(struct sk_buff *skb, const struct nf_conn *ct) struct nlattr *nest_secctx; int len, ret; char *secctx; + struct lsmblob blob; - ret = security_secid_to_secctx(ct->secmark, &secctx, &len); + /* lsmblob_init() puts ct->secmark into all of the secids in blob. + * security_secid_to_secctx() will know which security module + * to use to create the secctx. */ + lsmblob_init(&blob, ct->secmark); + ret = security_secid_to_secctx(&blob, &secctx, &len); if (ret) return 0; @@ -656,8 +661,13 @@ static inline int ctnetlink_secctx_size(const struct nf_conn *ct) { #ifdef CONFIG_NF_CONNTRACK_SECMARK int len, ret; + struct lsmblob blob; - ret = security_secid_to_secctx(ct->secmark, NULL, &len); + /* lsmblob_init() puts ct->secmark into all of the secids in blob. + * security_secid_to_secctx() will know which security module + * to use to create the secctx. */ + lsmblob_init(&blob, ct->secmark); + ret = security_secid_to_secctx(&blob, NULL, &len); if (ret) return 0; diff --git a/net/netfilter/nf_conntrack_standalone.c b/net/netfilter/nf_conntrack_standalone.c index 6ad7bbc90d38..2c1f3280d56e 100644 --- a/net/netfilter/nf_conntrack_standalone.c +++ b/net/netfilter/nf_conntrack_standalone.c @@ -178,8 +178,10 @@ static void ct_show_secctx(struct seq_file *s, const struct nf_conn *ct) int ret; u32 len; char *secctx; + struct lsmblob blob; - ret = security_secid_to_secctx(ct->secmark, &secctx, &len); + lsmblob_init(&blob, ct->secmark); + ret = security_secid_to_secctx(&blob, &secctx, &len); if (ret) return; diff --git a/net/netfilter/nfnetlink_queue.c b/net/netfilter/nfnetlink_queue.c index a364f8e5e698..6269fe122345 100644 --- a/net/netfilter/nfnetlink_queue.c +++ b/net/netfilter/nfnetlink_queue.c @@ -305,13 +305,20 @@ static u32 nfqnl_get_sk_secctx(struct sk_buff *skb, char **secdata) { u32 seclen = 0; #if IS_ENABLED(CONFIG_NETWORK_SECMARK) + struct lsmblob blob; + if (!skb || !sk_fullsock(skb->sk)) return 0; read_lock_bh(&skb->sk->sk_callback_lock); - if (skb->secmark) - security_secid_to_secctx(skb->secmark, secdata, &seclen); + if (skb->secmark) { + /* lsmblob_init() puts ct->secmark into all of the secids in + * blob. security_secid_to_secctx() will know which security + * module to use to create the secctx. */ + lsmblob_init(&blob, skb->secmark); + security_secid_to_secctx(&blob, secdata, &seclen); + } read_unlock_bh(&skb->sk->sk_callback_lock); #endif diff --git a/net/netlabel/netlabel_unlabeled.c b/net/netlabel/netlabel_unlabeled.c index f3e2cde76919..0a99663e6edb 100644 --- a/net/netlabel/netlabel_unlabeled.c +++ b/net/netlabel/netlabel_unlabeled.c @@ -376,6 +376,7 @@ int netlbl_unlhsh_add(struct net *net, struct audit_buffer *audit_buf = NULL; char *secctx = NULL; u32 secctx_len; + struct lsmblob blob; if (addr_len != sizeof(struct in_addr) && addr_len != sizeof(struct in6_addr)) @@ -438,7 +439,11 @@ int netlbl_unlhsh_add(struct net *net, unlhsh_add_return: rcu_read_unlock(); if (audit_buf != NULL) { - if (security_secid_to_secctx(secid, + /* lsmblob_init() puts secid into all of the secids in blob. + * security_secid_to_secctx() will know which security module + * to use to create the secctx. */ + lsmblob_init(&blob, secid); + if (security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " sec_obj=%s", secctx); @@ -475,6 +480,7 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, struct net_device *dev; char *secctx; u32 secctx_len; + struct lsmblob blob; spin_lock(&netlbl_unlhsh_lock); list_entry = netlbl_af4list_remove(addr->s_addr, mask->s_addr, @@ -493,8 +499,13 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, (dev != NULL ? dev->name : NULL), addr->s_addr, mask->s_addr); dev_put(dev); + /* lsmblob_init() puts entry->secid into all of the secids + * in blob. security_secid_to_secctx() will know which + * security module to use to create the secctx. */ + if (entry != NULL) + lsmblob_init(&blob, entry->secid); if (entry != NULL && - security_secid_to_secctx(entry->secid, + security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " sec_obj=%s", secctx); security_release_secctx(secctx, secctx_len); @@ -536,6 +547,7 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, struct net_device *dev; char *secctx; u32 secctx_len; + struct lsmblob blob; spin_lock(&netlbl_unlhsh_lock); list_entry = netlbl_af6list_remove(addr, mask, &iface->addr6_list); @@ -553,8 +565,13 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, (dev != NULL ? dev->name : NULL), addr, mask); dev_put(dev); + /* lsmblob_init() puts entry->secid into all of the secids + * in blob. security_secid_to_secctx() will know which + * security module to use to create the secctx. */ + if (entry != NULL) + lsmblob_init(&blob, entry->secid); if (entry != NULL && - security_secid_to_secctx(entry->secid, + security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " sec_obj=%s", secctx); security_release_secctx(secctx, secctx_len); @@ -1080,6 +1097,7 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, u32 secid; char *secctx; u32 secctx_len; + struct lsmblob blob; data = genlmsg_put(cb_arg->skb, NETLINK_CB(cb_arg->nl_cb->skb).portid, cb_arg->seq, &netlbl_unlabel_gnl_family, @@ -1134,7 +1152,11 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, secid = addr6->secid; } - ret_val = security_secid_to_secctx(secid, &secctx, &secctx_len); + /* lsmblob_init() secid into all of the secids in blob. + * security_secid_to_secctx() will know which security module + * to use to create the secctx. */ + lsmblob_init(&blob, secid); + ret_val = security_secid_to_secctx(&blob, &secctx, &secctx_len); if (ret_val != 0) goto list_cb_failure; ret_val = nla_put(cb_arg->skb, diff --git a/net/netlabel/netlabel_user.c b/net/netlabel/netlabel_user.c index 3ed4fea2a2de..893301ae0131 100644 --- a/net/netlabel/netlabel_user.c +++ b/net/netlabel/netlabel_user.c @@ -86,6 +86,7 @@ struct audit_buffer *netlbl_audit_start_common(int type, struct audit_buffer *audit_buf; char *secctx; u32 secctx_len; + struct lsmblob blob; if (audit_enabled == AUDIT_OFF) return NULL; @@ -98,10 +99,9 @@ struct audit_buffer *netlbl_audit_start_common(int type, from_kuid(&init_user_ns, audit_info->loginuid), audit_info->sessionid); + lsmblob_init(&blob, audit_info->secid); if (audit_info->secid != 0 && - security_secid_to_secctx(audit_info->secid, - &secctx, - &secctx_len) == 0) { + security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " subj=%s", secctx); security_release_secctx(secctx, secctx_len); } diff --git a/security/security.c b/security/security.c index 08ed7acf4205..552a08750843 100644 --- a/security/security.c +++ b/security/security.c @@ -2186,17 +2186,16 @@ int security_ismaclabel(const char *name) } EXPORT_SYMBOL(security_ismaclabel); -int security_secid_to_secctx(u32 secid, char **secdata, u32 *seclen) +int security_secid_to_secctx(struct lsmblob *blob, char **secdata, u32 *seclen) { struct security_hook_list *hp; int rc; - /* - * Currently, only one LSM can implement secid_to_secctx (i.e this - * LSM hook is not "stackable"). - */ hlist_for_each_entry(hp, &security_hook_heads.secid_to_secctx, list) { - rc = hp->hook.secid_to_secctx(secid, secdata, seclen); + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) + continue; + rc = hp->hook.secid_to_secctx(blob->secid[hp->lsmid->slot], + secdata, seclen); if (rc != LSM_RET_DEFAULT(secid_to_secctx)) return rc; } From patchwork Thu Jun 9 23:01:24 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876087 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 52590CCA473 for ; Thu, 9 Jun 2022 23:07:01 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1345866AbiFIXG5 (ORCPT ); Thu, 9 Jun 2022 19:06:57 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:37156 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S241049AbiFIXGz (ORCPT ); Thu, 9 Jun 2022 19:06:55 -0400 Received: from sonic308-16.consmr.mail.ne1.yahoo.com (sonic308-16.consmr.mail.ne1.yahoo.com [66.163.187.39]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 6BFA73AE819 for ; Thu, 9 Jun 2022 16:06:51 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816010; bh=qiW1yV5f9ANJJqC5KoOG/KftqckkY8ixFX0Qx5G3hEY=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=OltRWRwPyeEAJAVHx6JshOHFECancEVfDuBjWl+5ERxnmMpSHvDIhvsECRALbw88DZKB0cKQED/v2Cvw/f0UvbzF7txO71hUbqPsC9/PDZ20nUryT/BosP9xZnXXVZzksex/BTy/Y/cdtE4cnyOiDT4z0EGY2+WpSk0YI3MA2HeHufW0c/pVFMH1SsWWVZcNsK/Rb1hc9zSbR1OPKfYvLVIE36uMBZKUctf+oQi5q2714XrB8zTzcNy58JCBFmahUm0cQgiE4Nm201NUmldsWqbqxsGwlZibUnY3pUpoxsPj0lW/WlBnMo79R7bABf1bfxVHsOL+eHJsxNCoTJzcbQ== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816010; bh=7Ofc497974l5RuZBFERq7xVI0b4WVtaIGA2et/OERb7=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=XnRIBSg0AWh2b1yw8f+Ulvgw7+RY8vxIvqCQ1GIMBjJ9FpzpYWzvlSU/HQ4COYLoZTMfUVlUWOQVa8EhISJvWH66idyJji//SJFwBlfKGZAHwl8B03xU76q8ZVak3wFFjiZJ4SH1wePZhsa22NZNQ09ScZ9G4G+h977Jyckk19LQyeHWI0KgqfGuyjfciWBTK4SYf1OQ2tOmj7W8FXknl7vo3bxzb+YOFdbYg7j0bB3AJT/2x+e140P/atWjul9PKq5DVb5euVEFdz3dk9GY6xkEwmIncSRhtCpn7h/HSowOZC3si37uLzhI1SBLgV5Ke7C6BYNyCWLLNCxpe8z7Eg== X-YMail-OSG: L.dzM1cVM1lXyC6oMeacXhsClYVMEfXAsFbL.AlfjQa5DapRi2gO7XILeS9Y_On Wcu5PAfAHeIR25.Ko7QWrMnZ2EmarrPGT1jB8UKuKi1Uv3Z80MWzoW70Q2SGsyF2vz6h1OpAZRcH AhfIHN5yHfh4UxAr5ZFoGr5O.ijsHacToO0IHjcAeWLLoPuntbYEwOYs5dh2KUw1MnRlhhK_sUKP yWY_wibUyaMqZI2_ru.szkEPHe6qhhEnecddnG6gqN78xMCYYRbzBK9B304r0lkvEMf7MAV_1Gm2 PRQBxu6Thoe2bhQB0hwJpVO2TPBLbznY8kz6unqRGZPi_SmcchRT_XnwPBS8OVc8n7sQALr0x4Ee v_dTnTAk4DRbF_O0Xzp3yh5hLJtXdvkWGT.YE5Qb1orMs_jGD.JRiYw1.w7lTihSy2zk51QUn1wN GgK9piWrSwvlQAE.VY0ZwcRV.1n5p0yYNjYIADLPVT0Ws4kHsdnjxb_wubvtvX_9G7faz_oGjW2l oF6aQHmnGe1FWfB8vpM5LPhA6KTnrs.xoz5QxTk.lbImh5w9Gw6QU4R_wvjnyB1Oy6bByH_FuQz4 oecoVmgZaGPnOag5hTxlsCisFv.iRZimu_R7Enujt5ITDoFE.2nmBiwRHVYQCzpFaEZC7DPE0AmC eNpcTbsR5HyGJkisMt8e081X_P1anWVCcdLRYfOivNN45Vica7qDGogUcU1znSpMnzsSXl7VAglc RrYgtnJ6ju.7G9fZQB4n_OWEC_Ldz60BOUb1L0T2jJ9IsiN49fnMltPNm_YeXrXUSP7WJYyktbpp bxd2RXpVr1ipM_oVpikLSJXjpnZRmqIZngPAMXC9bhbKW6IaqLDPHrkqRqPydQHMJ7M0I_aaUrK7 _V.H1m8xHWIlx5h__Yt6PTJeVQD59Ha7H6fu9FsTSG8yUSZqR78ScbEbQ0egfvVXl9BRABtUeGrL zoW9cv5fda_2kZcnmkYpkAHdwbAZiMhy5tWvH9gPRWhbRkezNEZDQHdBNVMv6SXy1_4qCcrNnBM8 O9Xk2HQYAYL_p3n1z1crT6zowuweOVY.QtJ8ZqPCHcfe9agU4elgdMJ9iSZhSe8oEjcaNmWxNCYH gCKzIgrMx7sdJ0ZQLYKgDaUCVfozw0Bz1XTZr2xiUSvWVgbZMTlbUb.QUMcsP6SNlswN3XCexnb1 cLfNntSu12X20tYwGiviL7lwu7Hz5AgNIVVxzPA2V6Cppzy7e2CW4g7r_WwooHnfznr3keFoh8Zm .JxuLUEj6xIvdfrFIVNhOD.5nkijQZuyc_oPE49EFn2U3YHNeCH6qAKEJ_Gi4lIjOTPatNyJeo3g 0RPJhJV8Xvo3PQn0Gk7YpgPoGa7bzTXlOLTNrl1TX3EzG7OpguxqlGGKL.WX4X_H7jwCk37VRBJK Q62_7w8Vqc8tQ7mpQcEFikZkGW1Ja31dUlojRwVGMspuvwwKfjpN5cIee23qvz9RsmNRslcu8kUG gs1HUCChoN5_toVXjUTfeT0AkFTotOuIoEydSOXAkhaRek3XAnMGDhj8PCsXEj7i1wtbIuxwHHQ6 3nRC0tXnc7U2nE6yxpoqJ.hmN4k4nidq8MoIN30IRDb.F7z7wvgkfHazghjZt0Vdd0UV3whfTjzA kkUDmJ6MJI_.5_JYWnHuHrdqfUnhn2E87LsSFEWwfrtxp1.Fs5feZjkpAILordMpQ0mOMNfKI_F5 u5_7u5E2xTV_DXXBAB.alVgUrM_ZAz6Zi59bwuiihwj4PylG.1axwCvwd6FoP..SXjYZn0qOcVf6 E7DXuLeBN8nOqoolqtPPi.DatDeLVSIPT5mD3rnA44GJxvGKdolPB7xZek5AgqbBRIGWJYPyqKMI r8bmXerEsXlg8C9G6UZY6WfjZb4qmUNSVFFCNd1gVOAeVuZj3OovHCSvZKBtXaXFWMjwauiAQ.CS js9NnGi_7co0GKfKR9dBYukwea4d9NDoqik6WVF0BaCiNeNm4dCTrrffLPHm1w0JboNuVAEz2cNc Pz.Ms_a9Y9gBFN1G2SABMDfoeOPyWAuoQJAVN9zPhLwt0ta3zMyma9nLltZJxHAVnVqzCUzcFd7W fg6eRr_4uHCMOcm81eoC6NqMB_4PaQSbkUnQo.yOKN80VNRIsr9gnyFuRRdiINlp4tig7WwFhT.B bmcHX_fl546luR37zX6q_lcIOSpSwdcb0k.Lj_nnt1AqNKJuyuO2iP5jWyuZ9C4Rzfiz_rlD_C02 ccSKR6KqDF4VjYsCHxFVwppPN8eclJDEzylo1mmDApJBlc3qKpWWRvbTRqarohx2UiLK2WMK3Sml 1fItyKeSNiJ7HKv_5DD8GhN.MqnPQE.A- X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic308.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:06:50 +0000 Received: by hermes--canary-production-ne1-799d7bd497-2pzdr (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID b20ca8b25547b2b344a65fa8c4e3e611; Thu, 09 Jun 2022 23:06:49 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, linux-integrity@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v36 11/33] LSM: Use lsmblob in security_current_getsecid Date: Thu, 9 Jun 2022 16:01:24 -0700 Message-Id: <20220609230146.319210-12-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Change the security_current_getsecid_subj() and security_task_getsecid_obj() interfaces to fill in a lsmblob structure instead of a u32 secid in support of LSM stacking. Audit interfaces will need to collect all possible secids for possible reporting. Reviewed-by: Kees Cook Reviewed-by: John Johansen Acked-by: Stephen Smalley Acked-by: Paul Moore Signed-off-by: Casey Schaufler Cc: linux-integrity@vger.kernel.org Cc: linux-audit@redhat.com Cc: netdev@vger.kernel.org --- drivers/android/binder.c | 6 +-- include/linux/security.h | 31 ++++++++++++--- kernel/audit.c | 16 +++----- kernel/auditfilter.c | 4 +- kernel/auditsc.c | 25 ++++++------ net/netlabel/netlabel_unlabeled.c | 4 +- net/netlabel/netlabel_user.h | 6 ++- security/integrity/ima/ima.h | 6 +-- security/integrity/ima/ima_api.c | 6 +-- security/integrity/ima/ima_appraise.c | 11 +++--- security/integrity/ima/ima_main.c | 57 ++++++++++++++------------- security/integrity/ima/ima_policy.c | 15 +++---- security/security.c | 25 +++++++++--- 13 files changed, 124 insertions(+), 88 deletions(-) diff --git a/drivers/android/binder.c b/drivers/android/binder.c index 4ead3360a1c0..f25a867063e5 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c @@ -3054,16 +3054,16 @@ static void binder_transaction(struct binder_proc *proc, t->priority = task_nice(current); if (target_node && target_node->txn_security_ctx) { - u32 secid; struct lsmblob blob; size_t added_size; + u32 secid; security_cred_getsecid(proc->cred, &secid); /* - * Later in this patch set security_task_getsecid() will + * Later in this patch set security_cred_getsecid() will * provide a lsmblob instead of a secid. lsmblob_init * is used to ensure that all the secids in the lsmblob - * get the value returned from security_task_getsecid(), + * get the value returned from security_cred_getsecid(), * which means that the one expected by * security_secid_to_secctx() will be set. */ diff --git a/include/linux/security.h b/include/linux/security.h index 029c23719a5c..ce4a4af362f3 100644 --- a/include/linux/security.h +++ b/include/linux/security.h @@ -222,6 +222,24 @@ static inline u32 lsmblob_value(const struct lsmblob *blob) return 0; } +/** + * lsmblob_first - secid value for the first LSM slot + * @blob: Pointer to the data + * + * Return the secid value from the first LSM slot. + * There may not be any LSM slots. + * + * Return the value in secid[0] if there are any slots, 0 otherwise. + */ +static inline u32 lsmblob_first(const struct lsmblob *blob) +{ +#if LSMBLOB_ENTRIES > 0 + return blob->secid[0]; +#else + return 0; +#endif +} + /* These functions are in security/commoncap.c */ extern int cap_capable(const struct cred *cred, struct user_namespace *ns, int cap, unsigned int opts); @@ -504,8 +522,8 @@ int security_task_fix_setgid(struct cred *new, const struct cred *old, int security_task_setpgid(struct task_struct *p, pid_t pgid); int security_task_getpgid(struct task_struct *p); int security_task_getsid(struct task_struct *p); -void security_current_getsecid_subj(u32 *secid); -void security_task_getsecid_obj(struct task_struct *p, u32 *secid); +void security_current_getsecid_subj(struct lsmblob *blob); +void security_task_getsecid_obj(struct task_struct *p, struct lsmblob *blob); int security_task_setnice(struct task_struct *p, int nice); int security_task_setioprio(struct task_struct *p, int ioprio); int security_task_getioprio(struct task_struct *p); @@ -1201,14 +1219,15 @@ static inline int security_task_getsid(struct task_struct *p) return 0; } -static inline void security_current_getsecid_subj(u32 *secid) +static inline void security_current_getsecid_subj(struct lsmblob *blob) { - *secid = 0; + lsmblob_init(blob, 0); } -static inline void security_task_getsecid_obj(struct task_struct *p, u32 *secid) +static inline void security_task_getsecid_obj(struct task_struct *p, + struct lsmblob *blob) { - *secid = 0; + lsmblob_init(blob, 0); } static inline int security_task_setnice(struct task_struct *p, int nice) diff --git a/kernel/audit.c b/kernel/audit.c index 2acf95cf9895..2834e55844db 100644 --- a/kernel/audit.c +++ b/kernel/audit.c @@ -2178,19 +2178,12 @@ int audit_log_task_context(struct audit_buffer *ab) char *ctx = NULL; unsigned len; int error; - u32 sid; struct lsmblob blob; - security_current_getsecid_subj(&sid); - if (!sid) + security_current_getsecid_subj(&blob); + if (!lsmblob_is_set(&blob)) return 0; - /* - * lsmblob_init sets all values in the lsmblob to sid. - * This is temporary until security_task_getsecid is converted - * to use a lsmblob, which happens later in this patch set. - */ - lsmblob_init(&blob, sid); error = security_secid_to_secctx(&blob, &ctx, &len); if (error) { @@ -2399,6 +2392,7 @@ int audit_set_loginuid(kuid_t loginuid) int audit_signal_info(int sig, struct task_struct *t) { kuid_t uid = current_uid(), auid; + struct lsmblob blob; if (auditd_test_task(t) && (sig == SIGTERM || sig == SIGHUP || @@ -2409,7 +2403,9 @@ int audit_signal_info(int sig, struct task_struct *t) audit_sig_uid = auid; else audit_sig_uid = uid; - security_current_getsecid_subj(&audit_sig_sid); + security_current_getsecid_subj(&blob); + /* scaffolding until audit_sig_sid is converted */ + audit_sig_sid = lsmblob_first(&blob); } return audit_signal_info_syscall(t); diff --git a/kernel/auditfilter.c b/kernel/auditfilter.c index 15cd4fe35e9c..39ded5cb2429 100644 --- a/kernel/auditfilter.c +++ b/kernel/auditfilter.c @@ -1339,7 +1339,6 @@ int audit_filter(int msgtype, unsigned int listtype) struct audit_field *f = &e->rule.fields[i]; struct lsmblob blob; pid_t pid; - u32 sid; switch (f->type) { case AUDIT_PID: @@ -1369,8 +1368,7 @@ int audit_filter(int msgtype, unsigned int listtype) case AUDIT_SUBJ_SEN: case AUDIT_SUBJ_CLR: if (f->lsm_str) { - security_current_getsecid_subj(&sid); - lsmblob_init(&blob, sid); + security_current_getsecid_subj(&blob); result = security_audit_rule_match( &blob, f->type, f->op, &f->lsm_rules); diff --git a/kernel/auditsc.c b/kernel/auditsc.c index 0986ded8e798..e56637b5d518 100644 --- a/kernel/auditsc.c +++ b/kernel/auditsc.c @@ -467,7 +467,6 @@ static int audit_filter_rules(struct task_struct *tsk, { const struct cred *cred; int i, need_sid = 1; - u32 sid; struct lsmblob blob; unsigned int sessionid; @@ -676,17 +675,9 @@ static int audit_filter_rules(struct task_struct *tsk, * here even though it always refs * @current's creds */ - security_current_getsecid_subj(&sid); + security_current_getsecid_subj(&blob); need_sid = 0; } - /* - * lsmblob_init sets all values in the lsmblob - * to sid. This is temporary until - * security_task_getsecid() is converted to - * provide a lsmblob, which happens later in - * this patch set. - */ - lsmblob_init(&blob, sid); result = security_audit_rule_match(&blob, f->type, f->op, &f->lsm_rules); @@ -2770,12 +2761,15 @@ int __audit_sockaddr(int len, void *a) void __audit_ptrace(struct task_struct *t) { struct audit_context *context = audit_context(); + struct lsmblob blob; context->target_pid = task_tgid_nr(t); context->target_auid = audit_get_loginuid(t); context->target_uid = task_uid(t); context->target_sessionid = audit_get_sessionid(t); - security_task_getsecid_obj(t, &context->target_sid); + security_task_getsecid_obj(t, &blob); + /* scaffolding - until target_sid is converted */ + context->target_sid = lsmblob_first(&blob); memcpy(context->target_comm, t->comm, TASK_COMM_LEN); } @@ -2791,6 +2785,7 @@ int audit_signal_info_syscall(struct task_struct *t) struct audit_aux_data_pids *axp; struct audit_context *ctx = audit_context(); kuid_t t_uid = task_uid(t); + struct lsmblob blob; if (!audit_signals || audit_dummy_context()) return 0; @@ -2802,7 +2797,9 @@ int audit_signal_info_syscall(struct task_struct *t) ctx->target_auid = audit_get_loginuid(t); ctx->target_uid = t_uid; ctx->target_sessionid = audit_get_sessionid(t); - security_task_getsecid_obj(t, &ctx->target_sid); + security_task_getsecid_obj(t, &blob); + /* scaffolding until target_sid is converted */ + ctx->target_sid = lsmblob_first(&blob); memcpy(ctx->target_comm, t->comm, TASK_COMM_LEN); return 0; } @@ -2823,7 +2820,9 @@ int audit_signal_info_syscall(struct task_struct *t) axp->target_auid[axp->pid_count] = audit_get_loginuid(t); axp->target_uid[axp->pid_count] = t_uid; axp->target_sessionid[axp->pid_count] = audit_get_sessionid(t); - security_task_getsecid_obj(t, &axp->target_sid[axp->pid_count]); + security_task_getsecid_obj(t, &blob); + /* scaffolding until target_sid is converted */ + axp->target_sid[axp->pid_count] = lsmblob_first(&blob); memcpy(axp->target_comm[axp->pid_count], t->comm, TASK_COMM_LEN); axp->pid_count++; diff --git a/net/netlabel/netlabel_unlabeled.c b/net/netlabel/netlabel_unlabeled.c index 0a99663e6edb..bbb3b6a4f0d7 100644 --- a/net/netlabel/netlabel_unlabeled.c +++ b/net/netlabel/netlabel_unlabeled.c @@ -1562,11 +1562,13 @@ int __init netlbl_unlabel_defconf(void) int ret_val; struct netlbl_dom_map *entry; struct netlbl_audit audit_info; + struct lsmblob blob; /* Only the kernel is allowed to call this function and the only time * it is called is at bootup before the audit subsystem is reporting * messages so don't worry to much about these values. */ - security_current_getsecid_subj(&audit_info.secid); + security_current_getsecid_subj(&blob); + audit_info.secid = lsmblob_first(&blob); audit_info.loginuid = GLOBAL_ROOT_UID; audit_info.sessionid = 0; diff --git a/net/netlabel/netlabel_user.h b/net/netlabel/netlabel_user.h index d6c5b31eb4eb..34bb6572f33b 100644 --- a/net/netlabel/netlabel_user.h +++ b/net/netlabel/netlabel_user.h @@ -32,7 +32,11 @@ */ static inline void netlbl_netlink_auditinfo(struct netlbl_audit *audit_info) { - security_current_getsecid_subj(&audit_info->secid); + struct lsmblob blob; + + security_current_getsecid_subj(&blob); + /* scaffolding until secid is converted */ + audit_info->secid = lsmblob_first(&blob); audit_info->loginuid = audit_get_loginuid(current); audit_info->sessionid = audit_get_sessionid(current); } diff --git a/security/integrity/ima/ima.h b/security/integrity/ima/ima.h index 1b5d70ac2dc9..f347d63b61e7 100644 --- a/security/integrity/ima/ima.h +++ b/security/integrity/ima/ima.h @@ -255,7 +255,7 @@ static inline void ima_process_queued_keys(void) {} /* LIM API function definitions */ int ima_get_action(struct user_namespace *mnt_userns, struct inode *inode, - const struct cred *cred, u32 secid, int mask, + const struct cred *cred, struct lsmblob *blob, int mask, enum ima_hooks func, int *pcr, struct ima_template_desc **template_desc, const char *func_data, unsigned int *allowed_algos); @@ -286,8 +286,8 @@ const char *ima_d_path(const struct path *path, char **pathbuf, char *filename); /* IMA policy related functions */ int ima_match_policy(struct user_namespace *mnt_userns, struct inode *inode, - const struct cred *cred, u32 secid, enum ima_hooks func, - int mask, int flags, int *pcr, + const struct cred *cred, struct lsmblob *blob, + enum ima_hooks func, int mask, int flags, int *pcr, struct ima_template_desc **template_desc, const char *func_data, unsigned int *allowed_algos); void ima_init_policy(void); diff --git a/security/integrity/ima/ima_api.c b/security/integrity/ima/ima_api.c index c1e76282b5ee..8c48da6a6583 100644 --- a/security/integrity/ima/ima_api.c +++ b/security/integrity/ima/ima_api.c @@ -166,7 +166,7 @@ void ima_add_violation(struct file *file, const unsigned char *filename, * @mnt_userns: user namespace of the mount the inode was found from * @inode: pointer to the inode associated with the object being validated * @cred: pointer to credentials structure to validate - * @secid: secid of the task being validated + * @blob: secid(s) of the task being validated * @mask: contains the permission mask (MAY_READ, MAY_WRITE, MAY_EXEC, * MAY_APPEND) * @func: caller identifier @@ -187,7 +187,7 @@ void ima_add_violation(struct file *file, const unsigned char *filename, * */ int ima_get_action(struct user_namespace *mnt_userns, struct inode *inode, - const struct cred *cred, u32 secid, int mask, + const struct cred *cred, struct lsmblob *blob, int mask, enum ima_hooks func, int *pcr, struct ima_template_desc **template_desc, const char *func_data, unsigned int *allowed_algos) @@ -196,7 +196,7 @@ int ima_get_action(struct user_namespace *mnt_userns, struct inode *inode, flags &= ima_policy_flag; - return ima_match_policy(mnt_userns, inode, cred, secid, func, mask, + return ima_match_policy(mnt_userns, inode, cred, blob, func, mask, flags, pcr, template_desc, func_data, allowed_algos); } diff --git a/security/integrity/ima/ima_appraise.c b/security/integrity/ima/ima_appraise.c index cdb84dccd24e..9ef8210e901f 100644 --- a/security/integrity/ima/ima_appraise.c +++ b/security/integrity/ima/ima_appraise.c @@ -73,15 +73,16 @@ bool is_ima_appraise_enabled(void) int ima_must_appraise(struct user_namespace *mnt_userns, struct inode *inode, int mask, enum ima_hooks func) { - u32 secid; + struct lsmblob blob; if (!ima_appraise) return 0; - security_current_getsecid_subj(&secid); - return ima_match_policy(mnt_userns, inode, current_cred(), secid, - func, mask, IMA_APPRAISE | IMA_HASH, NULL, - NULL, NULL, NULL); + security_current_getsecid_subj(&blob); + return ima_match_policy(mnt_userns, inode, current_cred(), + &blob, func, mask, + IMA_APPRAISE | IMA_HASH, NULL, NULL, NULL, + NULL); } static int ima_fix_xattr(struct dentry *dentry, diff --git a/security/integrity/ima/ima_main.c b/security/integrity/ima/ima_main.c index 040b03ddc1c7..5d6029ac52f0 100644 --- a/security/integrity/ima/ima_main.c +++ b/security/integrity/ima/ima_main.c @@ -199,8 +199,8 @@ void ima_file_free(struct file *file) } static int process_measurement(struct file *file, const struct cred *cred, - u32 secid, char *buf, loff_t size, int mask, - enum ima_hooks func) + struct lsmblob *blob, char *buf, loff_t size, + int mask, enum ima_hooks func) { struct inode *inode = file_inode(file); struct integrity_iint_cache *iint = NULL; @@ -224,7 +224,7 @@ static int process_measurement(struct file *file, const struct cred *cred, * bitmask based on the appraise/audit/measurement policy. * Included is the appraise submask. */ - action = ima_get_action(file_mnt_user_ns(file), inode, cred, secid, + action = ima_get_action(file_mnt_user_ns(file), inode, cred, blob, mask, func, &pcr, &template_desc, NULL, &allowed_algos); violation_check = ((func == FILE_CHECK || func == MMAP_CHECK) && @@ -405,12 +405,13 @@ static int process_measurement(struct file *file, const struct cred *cred, */ int ima_file_mmap(struct file *file, unsigned long prot) { - u32 secid; + struct lsmblob blob; if (file && (prot & PROT_EXEC)) { - security_current_getsecid_subj(&secid); - return process_measurement(file, current_cred(), secid, NULL, - 0, MAY_EXEC, MMAP_CHECK); + security_current_getsecid_subj(&blob); + return process_measurement(file, current_cred(), + &blob, NULL, 0, + MAY_EXEC, MMAP_CHECK); } return 0; @@ -437,9 +438,9 @@ int ima_file_mprotect(struct vm_area_struct *vma, unsigned long prot) char *pathbuf = NULL; const char *pathname = NULL; struct inode *inode; + struct lsmblob blob; int result = 0; int action; - u32 secid; int pcr; /* Is mprotect making an mmap'ed file executable? */ @@ -447,11 +448,12 @@ int ima_file_mprotect(struct vm_area_struct *vma, unsigned long prot) !(prot & PROT_EXEC) || (vma->vm_flags & VM_EXEC)) return 0; - security_current_getsecid_subj(&secid); + security_current_getsecid_subj(&blob); inode = file_inode(vma->vm_file); action = ima_get_action(file_mnt_user_ns(vma->vm_file), inode, - current_cred(), secid, MAY_EXEC, MMAP_CHECK, - &pcr, &template, NULL, NULL); + current_cred(), &blob, + MAY_EXEC, MMAP_CHECK, &pcr, &template, NULL, + NULL); /* Is the mmap'ed file in policy? */ if (!(action & (IMA_MEASURE | IMA_APPRAISE_SUBMASK))) @@ -487,10 +489,11 @@ int ima_bprm_check(struct linux_binprm *bprm) { int ret; u32 secid; + struct lsmblob blob; - security_current_getsecid_subj(&secid); - ret = process_measurement(bprm->file, current_cred(), secid, NULL, 0, - MAY_EXEC, BPRM_CHECK); + security_current_getsecid_subj(&blob); + ret = process_measurement(bprm->file, current_cred(), + &blob, NULL, 0, MAY_EXEC, BPRM_CHECK); if (ret) return ret; @@ -511,10 +514,10 @@ int ima_bprm_check(struct linux_binprm *bprm) */ int ima_file_check(struct file *file, int mask) { - u32 secid; + struct lsmblob blob; - security_current_getsecid_subj(&secid); - return process_measurement(file, current_cred(), secid, NULL, 0, + security_current_getsecid_subj(&blob); + return process_measurement(file, current_cred(), &blob, NULL, 0, mask & (MAY_READ | MAY_WRITE | MAY_EXEC | MAY_APPEND), FILE_CHECK); } @@ -710,7 +713,7 @@ int ima_read_file(struct file *file, enum kernel_read_file_id read_id, bool contents) { enum ima_hooks func; - u32 secid; + struct lsmblob blob; /* * Do devices using pre-allocated memory run the risk of the @@ -730,9 +733,9 @@ int ima_read_file(struct file *file, enum kernel_read_file_id read_id, /* Read entire file for all partial reads. */ func = read_idmap[read_id] ?: FILE_CHECK; - security_current_getsecid_subj(&secid); - return process_measurement(file, current_cred(), secid, NULL, - 0, MAY_READ, func); + security_current_getsecid_subj(&blob); + return process_measurement(file, current_cred(), &blob, NULL, 0, + MAY_READ, func); } const int read_idmap[READING_MAX_ID] = { @@ -760,7 +763,7 @@ int ima_post_read_file(struct file *file, void *buf, loff_t size, enum kernel_read_file_id read_id) { enum ima_hooks func; - u32 secid; + struct lsmblob blob; /* permit signed certs */ if (!file && read_id == READING_X509_CERTIFICATE) @@ -773,8 +776,8 @@ int ima_post_read_file(struct file *file, void *buf, loff_t size, } func = read_idmap[read_id] ?: FILE_CHECK; - security_current_getsecid_subj(&secid); - return process_measurement(file, current_cred(), secid, buf, size, + security_current_getsecid_subj(&blob); + return process_measurement(file, current_cred(), &blob, buf, size, MAY_READ, func); } @@ -900,7 +903,7 @@ int process_buffer_measurement(struct user_namespace *mnt_userns, int digest_hash_len = hash_digest_size[ima_hash_algo]; int violation = 0; int action = 0; - u32 secid; + struct lsmblob blob; if (digest && digest_len < digest_hash_len) return -EINVAL; @@ -923,9 +926,9 @@ int process_buffer_measurement(struct user_namespace *mnt_userns, * buffer measurements. */ if (func) { - security_current_getsecid_subj(&secid); + security_current_getsecid_subj(&blob); action = ima_get_action(mnt_userns, inode, current_cred(), - secid, 0, func, &pcr, &template, + &blob, 0, func, &pcr, &template, func_data, NULL); if (!(action & IMA_MEASURE) && !digest) return -ENOENT; diff --git a/security/integrity/ima/ima_policy.c b/security/integrity/ima/ima_policy.c index b04733a5d066..5c2bc6782e17 100644 --- a/security/integrity/ima/ima_policy.c +++ b/security/integrity/ima/ima_policy.c @@ -563,7 +563,7 @@ static bool ima_match_rule_data(struct ima_rule_entry *rule, * @mnt_userns: user namespace of the mount the inode was found from * @inode: a pointer to an inode * @cred: a pointer to a credentials structure for user validation - * @secid: the secid of the task to be validated + * @blob: the secid(s) of the task to be validated * @func: LIM hook identifier * @mask: requested action (MAY_READ | MAY_WRITE | MAY_APPEND | MAY_EXEC) * @func_data: func specific data, may be NULL @@ -573,7 +573,7 @@ static bool ima_match_rule_data(struct ima_rule_entry *rule, static bool ima_match_rules(struct ima_rule_entry *rule, struct user_namespace *mnt_userns, struct inode *inode, const struct cred *cred, - u32 secid, enum ima_hooks func, int mask, + struct lsmblob *blob, enum ima_hooks func, int mask, const char *func_data) { int i; @@ -657,7 +657,8 @@ static bool ima_match_rules(struct ima_rule_entry *rule, case LSM_SUBJ_USER: case LSM_SUBJ_ROLE: case LSM_SUBJ_TYPE: - rc = ima_filter_rule_match(secid, rule->lsm[i].type, + rc = ima_filter_rule_match(lsmblob_first(blob), + rule->lsm[i].type, Audit_equal, rule->lsm[i].rule, rule->lsm[i].rules_lsm); @@ -702,7 +703,7 @@ static int get_subaction(struct ima_rule_entry *rule, enum ima_hooks func) * @inode: pointer to an inode for which the policy decision is being made * @cred: pointer to a credentials structure for which the policy decision is * being made - * @secid: LSM secid of the task to be validated + * @blob: LSM secid(s) of the task to be validated * @func: IMA hook identifier * @mask: requested action (MAY_READ | MAY_WRITE | MAY_APPEND | MAY_EXEC) * @pcr: set the pcr to extend @@ -718,8 +719,8 @@ static int get_subaction(struct ima_rule_entry *rule, enum ima_hooks func) * than writes so ima_match_policy() is classical RCU candidate. */ int ima_match_policy(struct user_namespace *mnt_userns, struct inode *inode, - const struct cred *cred, u32 secid, enum ima_hooks func, - int mask, int flags, int *pcr, + const struct cred *cred, struct lsmblob *blob, + enum ima_hooks func, int mask, int flags, int *pcr, struct ima_template_desc **template_desc, const char *func_data, unsigned int *allowed_algos) { @@ -737,7 +738,7 @@ int ima_match_policy(struct user_namespace *mnt_userns, struct inode *inode, if (!(entry->action & actmask)) continue; - if (!ima_match_rules(entry, mnt_userns, inode, cred, secid, + if (!ima_match_rules(entry, mnt_userns, inode, cred, blob, func, mask, func_data)) continue; diff --git a/security/security.c b/security/security.c index 1e9c06607c39..1a4741178944 100644 --- a/security/security.c +++ b/security/security.c @@ -1916,17 +1916,30 @@ int security_task_getsid(struct task_struct *p) return call_int_hook(task_getsid, 0, p); } -void security_current_getsecid_subj(u32 *secid) +void security_current_getsecid_subj(struct lsmblob *blob) { - *secid = 0; - call_void_hook(current_getsecid_subj, secid); + struct security_hook_list *hp; + + lsmblob_init(blob, 0); + hlist_for_each_entry(hp, &security_hook_heads.current_getsecid_subj, + list) { + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) + continue; + hp->hook.current_getsecid_subj(&blob->secid[hp->lsmid->slot]); + } } EXPORT_SYMBOL(security_current_getsecid_subj); -void security_task_getsecid_obj(struct task_struct *p, u32 *secid) +void security_task_getsecid_obj(struct task_struct *p, struct lsmblob *blob) { - *secid = 0; - call_void_hook(task_getsecid_obj, p, secid); + struct security_hook_list *hp; + + lsmblob_init(blob, 0); + hlist_for_each_entry(hp, &security_hook_heads.task_getsecid_obj, list) { + if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) + continue; + hp->hook.task_getsecid_obj(p, &blob->secid[hp->lsmid->slot]); + } } EXPORT_SYMBOL(security_task_getsecid_obj); From patchwork Thu Jun 9 23:01:28 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876121 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 68077CCA483 for ; Thu, 9 Jun 2022 23:10:19 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1345904AbiFIXKR (ORCPT ); Thu, 9 Jun 2022 19:10:17 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:50592 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231657AbiFIXKL (ORCPT ); Thu, 9 Jun 2022 19:10:11 -0400 Received: from sonic308-16.consmr.mail.ne1.yahoo.com (sonic308-16.consmr.mail.ne1.yahoo.com [66.163.187.39]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 8802414A928 for ; Thu, 9 Jun 2022 16:10:06 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816206; bh=oje8zQ4VCRBDmqjoigGlMIX5a/E3pyPEAc2tsL9W+gA=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=B55to1FCRZX1YdwrNJNchU/0/o3Md6+GOfjGsUMArl6WPbh2E693NgjblLgbqmJ+BsgWrLF4x25ps6nlM9CnqcvC//VRlvsmVOREEID4CSrkw++dYr3wc5WM+dE0tyn3QJOIbSzRh6BEW582xcFiwcr5TvvSjyeLGhM5DOLi5NhcYtFepsgbLwKJNJGxr7/qRfeEEbtwzjhXNkPJ2Kx4IORAkaSTmsQoM8RGssH4/d85OotvapQPRQpc9qrV7pTtzEsJg6QyqEOCSqvpEodekXetoSrLX9jGTWImYIig4KYoceuoW7OD34GS5FIwkk50JoetLmhjk3Xn7vAfh+4gGw== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816206; bh=CqzXq3iQmMd4vQS9ZElBjIDiU4NZnare2qoWshabyvX=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=VAGUNkNiCk7dzaubmlZkzdBQzkTZkbiqFsmhIzgNw8QJfz5SgJXhYLgVIoMy1wBfX63Oxmc/N3/Trg4D3xVFYr3OhS5DxaijAQ8SzS5+cgEHDzI+h0jJEpuIcpBZvrKu1BUTp3Up1d8OX9Op8vTVX04cn44iVmh6cw9PyydThwgCJ7oF/QXuCzBgzRC0AvRqlJnjePZy+t88jX1cJ0zuO+QHeBl6w0pmWSM+p+pHCoBgRTFNHL9P4lgMRoUHi+ovMLU9fPAFSjsbVOMb4g8Gg5WyG0n8ZgbRNwXcOw6lJ5HLC0oft/7KKI+BcomhbhCejSSv8jeB1MA+SmnNv/QJsQ== X-YMail-OSG: PHVLovEVM1lj4RfjXzil.wvsOm1FDdshO3vQ5WSuWtkoXysGSWpjFloxbF7Gahe KDmb3VqgxgoRFI2cCG_YlzJ8jdVTokkWTs8iqA3Etr8Tl9N.kkoIEkehSAcYFCQEBuV05MczdQM5 wGSo1puPbL6jOlxzhsD.PfkP2KE99rNpwGQ4vOEvO9E6.vH_XsNTnDbLds2DT_PE6_ngqRw66vnv mQ69MRAT5.kjR4mxkB8eZBPbXqgooUMS0rS.IHo7Xc8TAIosx7Im646hrHHVNjuMyVFPzTqW24KL XMsadvD7tsPjC19PY.hVI1fNTiVywRssqefTQaWN90qvd7D7Obzc9wN_G0USzFlylUfBtBkTFWRK 9DYnPMzZYHFBgt_gXFXgm6e.4iMFZjFrHuck9fXSqpr57Ff5qvPtkSxpcd5jWD5ti6Fkcg9_lEDC 9oWITLtveN5Pv66vDY_411iOIfc4pQNGAD3ElG.fE5YMyR9CC5CowuTzFKqJP170aCA22BTboa7G cpMuZ56ZH69H33kHjea0mGwMThhi8X6NFcZ4RLAYymjmBeH_xGMtOSJHxrvpNsgYsrjvAA2Rv3VV S.U4RjLTuUiu1MaFiWTcya_cOXdmQpM_q1noyyMdx4ZmTygidmlzwlwBOD7ByDHFbjdFUG0JSXIB TDXVqTCdljkJ31NXoNWM8TmHG0783wFWvS0gyQosUvo4lcxRln1ex.1fzfr_fo2KSmK9uTm4Laki 2jtwoNE102liq9_KIiHu4tcypgQQ.wI4LjQdMrHgDHvgfl3IChQLwT1F47kf2gmbV48UOwzTs6pF _u55rnwuHD7iYtTsMk85pogObTWMwRE6wd_B0mvplyivBPIxSP6X_8IgaoluB.6MhZ0xpklRkQ5t FKs6Weuckx5zHovJ4ZDnffFunKET0N_9Q36toSZE79isAPiTkcfoFQKb7aduHhwZVTOxNiRKIt_R GwDGfucGWt.wgM8KsnzbGFl4e7Vklx67EuHU7R_Khx88F.BcdW.8up.pBxphSIDA7l5AHw00GhrI 7ECwOV10Zj04Z5ZonyRTkf032pPkv4urKY.h2fvWA2g3Jegqq23BVI13Yx.eU4t08qSQZzV7kDog dhrg1mY9_HEIcmp0qWhZhC.liveT0rV0ekkUsPBgZsNuBFbFPK.T0M8yKVfvP9IRcm7TDnVs3hFe i4YBCAOb3yw3piw3NpmOnIvZTjmOAk6_87V3fty7pm1O09vxJP5w625SBHuLs09n4eChDvKNmB21 ICTg3sw06n9zX9Az2xnzLb0JEI080rgnibsFY6iTyEyoVauqIIjRI7eDHUyHvIP5b1dV7DXNd2e_ dsCs6rl2FymT3Ji.6l.Ja_xPAjSyaZAVAjHPjb_RX1ebLvudfSvypbU8ZLASW2U8KEqVZ9jJ0as4 9ljpCd2DXaYdUfpLzEs3dsxaX0EyHSWpVV1fOA0sZUUUkznmdvUwG2QVYLhOgSsgrsGDWyw_ZRNe YWRjp61ju172pPuzURpxbYmy6u1390G9lXGRw1arQb_LvaD7RJCsLXRhGtSoyculV7iXcV4F2i0p XOkQ26jVN1VFAr3BF8aL0uBCCmoeUTY6lPNLXKOhGpEk9kPxs3xbDuySbDNsseqBIyElmTHXKxc9 m_AskE1JMCgXlZp8dCWaxdX33DBU9iKm18HMS2QwVwOxH98sYyKw12QeAEzZp3Y9aDKlXhp33SOi KlYfU8RNiu6ukmmYy644lE9Tdu5KOeB46V4dpuLaBau7JJlRVlyD6evd1MfBQ1Uc_lWcWYTcAgke dFv8YNMYtA5F614MQd1zWRiku5ZDThv2l6NlRnqNk6oH.i6ByjBxa1vF0iprC0FTtzkn9ZNbSSxZ bkJOvtXHf6mpdmhuwCxk.3Gqoe3P0MoBtgfPEyreS_2HKm6kIMuYFKD5vdlgsxLYWQH.Sl2DlnLq g.75IXCd_F5OItVRahwPdfyDQB1xBSbJEuvuzsybaEHnV.b_mvysZQCRpz.Wp0oE5dFLWjjXixNi cbkRcQonPnldDY62Cs14h0l.RF6CtVKL.s4HeS5kGoytbltZF4R21TpvXWHZNVU3OIAyXWh.caGJ Hj81KysODfemCYlWs3ClzQaFLF13Qy3jn2FNSHNDuaEmQvm1q5AkMwxuwTIz_Q_zPKtUxGXYoHF_ kl05nfcfmYmkgzq2fqkJ9WILS_CXbg4ojdbGYdvgFsj9lUU5mK3tmVdf6P6EWt7sIyLFhYWS60p0 rQy8WM80.dzH.R823j7uvquylR5WB52gn62L_PW2d4gZqObwh1qAGzPM8Q2N7gZ.1lApLcaNHLWH kFzXhqrimnJziTO9XBiVmKHD5u4f5QF6NmiuEtAZGHQAKfcAc4IeRTbXQqJJIaiQxuvWVLowFYaG nzboo4As4 X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic308.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:10:06 +0000 Received: by hermes--canary-production-ne1-799d7bd497-7z8w4 (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID 62296d5a5fc11a6b88291aff65d8e04f; Thu, 09 Jun 2022 23:10:01 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, Chuck Lever , linux-integrity@vger.kernel.org, netdev@vger.kernel.org, netfilter-devel@vger.kernel.org, linux-nfs@vger.kernel.org Subject: [PATCH v36 15/33] LSM: Ensure the correct LSM context releaser Date: Thu, 9 Jun 2022 16:01:28 -0700 Message-Id: <20220609230146.319210-16-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Add a new lsmcontext data structure to hold all the information about a "security context", including the string, its size and which LSM allocated the string. The allocation information is necessary because LSMs have different policies regarding the lifecycle of these strings. SELinux allocates and destroys them on each use, whereas Smack provides a pointer to an entry in a list that never goes away. Reviewed-by: Kees Cook Reviewed-by: John Johansen Acked-by: Paul Moore Acked-by: Stephen Smalley Acked-by: Chuck Lever Signed-off-by: Casey Schaufler Cc: linux-integrity@vger.kernel.org Cc: netdev@vger.kernel.org Cc: linux-audit@redhat.com Cc: netfilter-devel@vger.kernel.org To: Pablo Neira Ayuso Cc: linux-nfs@vger.kernel.org --- drivers/android/binder.c | 10 ++++--- fs/ceph/xattr.c | 6 ++++- fs/nfs/nfs4proc.c | 8 ++++-- fs/nfsd/nfs4xdr.c | 7 +++-- include/linux/security.h | 35 +++++++++++++++++++++++-- include/net/scm.h | 5 +++- kernel/audit.c | 14 +++++++--- kernel/auditsc.c | 12 ++++++--- net/ipv4/ip_sockglue.c | 4 ++- net/netfilter/nf_conntrack_netlink.c | 4 ++- net/netfilter/nf_conntrack_standalone.c | 4 ++- net/netfilter/nfnetlink_queue.c | 13 ++++++--- net/netlabel/netlabel_unlabeled.c | 19 +++++++++++--- net/netlabel/netlabel_user.c | 4 ++- security/security.c | 11 ++++---- 15 files changed, 121 insertions(+), 35 deletions(-) diff --git a/drivers/android/binder.c b/drivers/android/binder.c index c2f71c22a90e..9c1ed7fbda87 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c @@ -2783,6 +2783,7 @@ static void binder_transaction(struct binder_proc *proc, int t_debug_id = atomic_inc_return(&binder_last_id); char *secctx = NULL; u32 secctx_sz = 0; + struct lsmcontext scaff; /* scaffolding */ struct list_head sgc_head; struct list_head pf_head; const void __user *user_buffer = (const void __user *) @@ -3116,7 +3117,8 @@ static void binder_transaction(struct binder_proc *proc, t->security_ctx = 0; WARN_ON(1); } - security_release_secctx(secctx, secctx_sz); + lsmcontext_init(&scaff, secctx, secctx_sz, 0); + security_release_secctx(&scaff); secctx = NULL; } t->buffer->debug_id = t->debug_id; @@ -3532,8 +3534,10 @@ static void binder_transaction(struct binder_proc *proc, binder_alloc_free_buf(&target_proc->alloc, t->buffer); err_binder_alloc_buf_failed: err_bad_extra_size: - if (secctx) - security_release_secctx(secctx, secctx_sz); + if (secctx) { + lsmcontext_init(&scaff, secctx, secctx_sz, 0); + security_release_secctx(&scaff); + } err_get_secctx_failed: kfree(tcomplete); binder_stats_deleted(BINDER_STAT_TRANSACTION_COMPLETE); diff --git a/fs/ceph/xattr.c b/fs/ceph/xattr.c index 8c2dc2c762a4..b1c81e75f37f 100644 --- a/fs/ceph/xattr.c +++ b/fs/ceph/xattr.c @@ -1391,12 +1391,16 @@ int ceph_security_init_secctx(struct dentry *dentry, umode_t mode, void ceph_release_acl_sec_ctx(struct ceph_acl_sec_ctx *as_ctx) { +#ifdef CONFIG_CEPH_FS_SECURITY_LABEL + struct lsmcontext scaff; /* scaffolding */ +#endif #ifdef CONFIG_CEPH_FS_POSIX_ACL posix_acl_release(as_ctx->acl); posix_acl_release(as_ctx->default_acl); #endif #ifdef CONFIG_CEPH_FS_SECURITY_LABEL - security_release_secctx(as_ctx->sec_ctx, as_ctx->sec_ctxlen); + lsmcontext_init(&scaff, as_ctx->sec_ctx, as_ctx->sec_ctxlen, 0); + security_release_secctx(&scaff); #endif if (as_ctx->pagelist) ceph_pagelist_release(as_ctx->pagelist); diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index c0fdcf8c0032..d6bdb0868729 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c @@ -133,8 +133,12 @@ nfs4_label_init_security(struct inode *dir, struct dentry *dentry, static inline void nfs4_label_release_security(struct nfs4_label *label) { - if (label) - security_release_secctx(label->label, label->len); + struct lsmcontext scaff; /* scaffolding */ + + if (label) { + lsmcontext_init(&scaff, label->label, label->len, 0); + security_release_secctx(&scaff); + } } static inline u32 *nfs4_bitmask(struct nfs_server *server, struct nfs4_label *label) { diff --git a/fs/nfsd/nfs4xdr.c b/fs/nfsd/nfs4xdr.c index 61b2aae81abb..512ad208d62a 100644 --- a/fs/nfsd/nfs4xdr.c +++ b/fs/nfsd/nfs4xdr.c @@ -2830,6 +2830,7 @@ nfsd4_encode_fattr(struct xdr_stream *xdr, struct svc_fh *fhp, int err; struct nfs4_acl *acl = NULL; #ifdef CONFIG_NFSD_V4_SECURITY_LABEL + struct lsmcontext scaff; /* scaffolding */ void *context = NULL; int contextlen; #endif @@ -3341,8 +3342,10 @@ nfsd4_encode_fattr(struct xdr_stream *xdr, struct svc_fh *fhp, out: #ifdef CONFIG_NFSD_V4_SECURITY_LABEL - if (context) - security_release_secctx(context, contextlen); + if (context) { + lsmcontext_init(&scaff, context, contextlen, 0); /*scaffolding*/ + security_release_secctx(&scaff); + } #endif /* CONFIG_NFSD_V4_SECURITY_LABEL */ kfree(acl); if (tempfh) { diff --git a/include/linux/security.h b/include/linux/security.h index a7a445bac8ce..a20fc156c697 100644 --- a/include/linux/security.h +++ b/include/linux/security.h @@ -137,6 +137,37 @@ enum lockdown_reason { extern const char *const lockdown_reasons[LOCKDOWN_CONFIDENTIALITY_MAX+1]; +/* + * A "security context" is the text representation of + * the information used by LSMs. + * This structure contains the string, its length, and which LSM + * it is useful for. + */ +struct lsmcontext { + char *context; /* Provided by the module */ + u32 len; + int slot; /* Identifies the module */ +}; + +/** + * lsmcontext_init - initialize an lsmcontext structure. + * @cp: Pointer to the context to initialize + * @context: Initial context, or NULL + * @size: Size of context, or 0 + * @slot: Which LSM provided the context + * + * Fill in the lsmcontext from the provided information. + * This is a scaffolding function that will be removed when + * lsmcontext integration is complete. + */ +static inline void lsmcontext_init(struct lsmcontext *cp, char *context, + u32 size, int slot) +{ + cp->slot = slot; + cp->context = context; + cp->len = size; +} + /* * Data exported by the security modules * @@ -589,7 +620,7 @@ int security_ismaclabel(const char *name); int security_secid_to_secctx(struct lsmblob *blob, char **secdata, u32 *seclen); int security_secctx_to_secid(const char *secdata, u32 seclen, struct lsmblob *blob); -void security_release_secctx(char *secdata, u32 seclen); +void security_release_secctx(struct lsmcontext *cp); void security_inode_invalidate_secctx(struct inode *inode); int security_inode_notifysecctx(struct inode *inode, void *ctx, u32 ctxlen); int security_inode_setsecctx(struct dentry *dentry, void *ctx, u32 ctxlen); @@ -1453,7 +1484,7 @@ static inline int security_secctx_to_secid(const char *secdata, return -EOPNOTSUPP; } -static inline void security_release_secctx(char *secdata, u32 seclen) +static inline void security_release_secctx(struct lsmcontext *cp) { } diff --git a/include/net/scm.h b/include/net/scm.h index 23a35ff1b3f2..f273c4d777ec 100644 --- a/include/net/scm.h +++ b/include/net/scm.h @@ -92,6 +92,7 @@ static __inline__ int scm_send(struct socket *sock, struct msghdr *msg, #ifdef CONFIG_SECURITY_NETWORK static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct scm_cookie *scm) { + struct lsmcontext context; struct lsmblob lb; char *secdata; u32 seclen; @@ -106,7 +107,9 @@ static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct sc if (!err) { put_cmsg(msg, SOL_SOCKET, SCM_SECURITY, seclen, secdata); - security_release_secctx(secdata, seclen); + /*scaffolding*/ + lsmcontext_init(&context, secdata, seclen, 0); + security_release_secctx(&context); } } } diff --git a/kernel/audit.c b/kernel/audit.c index 2b670ac129be..0eff57959b4e 100644 --- a/kernel/audit.c +++ b/kernel/audit.c @@ -1214,6 +1214,7 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) struct audit_sig_info *sig_data; char *ctx = NULL; u32 len; + struct lsmcontext scaff; /* scaffolding */ err = audit_netlink_ok(skb, msg_type); if (err) @@ -1471,15 +1472,18 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) } sig_data = kmalloc(struct_size(sig_data, ctx, len), GFP_KERNEL); if (!sig_data) { - if (lsmblob_is_set(&audit_sig_lsm)) - security_release_secctx(ctx, len); + if (lsmblob_is_set(&audit_sig_lsm)) { + lsmcontext_init(&scaff, ctx, len, 0); + security_release_secctx(&scaff); + } return -ENOMEM; } sig_data->uid = from_kuid(&init_user_ns, audit_sig_uid); sig_data->pid = audit_sig_pid; if (lsmblob_is_set(&audit_sig_lsm)) { memcpy(sig_data->ctx, ctx, len); - security_release_secctx(ctx, len); + lsmcontext_init(&scaff, ctx, len, 0); + security_release_secctx(&scaff); } audit_send_reply(skb, seq, AUDIT_SIGNAL_INFO, 0, 0, sig_data, struct_size(sig_data, ctx, len)); @@ -2171,6 +2175,7 @@ int audit_log_task_context(struct audit_buffer *ab) unsigned len; int error; struct lsmblob blob; + struct lsmcontext scaff; /* scaffolding */ security_current_getsecid_subj(&blob); if (!lsmblob_is_set(&blob)) @@ -2185,7 +2190,8 @@ int audit_log_task_context(struct audit_buffer *ab) } audit_log_format(ab, " subj=%s", ctx); - security_release_secctx(ctx, len); + lsmcontext_init(&scaff, ctx, len, 0); + security_release_secctx(&scaff); return 0; error_path: diff --git a/kernel/auditsc.c b/kernel/auditsc.c index 030f6e84026e..cc902c9df77f 100644 --- a/kernel/auditsc.c +++ b/kernel/auditsc.c @@ -1121,6 +1121,7 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid, struct lsmblob *blob, char *comm) { struct audit_buffer *ab; + struct lsmcontext lsmcxt; char *ctx = NULL; u32 len; int rc = 0; @@ -1138,7 +1139,8 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid, rc = 1; } else { audit_log_format(ab, " obj=%s", ctx); - security_release_secctx(ctx, len); + lsmcontext_init(&lsmcxt, ctx, len, 0); /*scaffolding*/ + security_release_secctx(&lsmcxt); } } audit_log_format(ab, " ocomm="); @@ -1398,6 +1400,7 @@ static void audit_log_time(struct audit_context *context, struct audit_buffer ** static void show_special(struct audit_context *context, int *call_panic) { + struct lsmcontext lsmcxt; struct audit_buffer *ab; int i; @@ -1432,7 +1435,8 @@ static void show_special(struct audit_context *context, int *call_panic) *call_panic = 1; } else { audit_log_format(ab, " obj=%s", ctx); - security_release_secctx(ctx, len); + lsmcontext_init(&lsmcxt, ctx, len, 0); + security_release_secctx(&lsmcxt); } } if (context->ipc.has_perm) { @@ -1594,6 +1598,7 @@ static void audit_log_name(struct audit_context *context, struct audit_names *n, char *ctx = NULL; u32 len; struct lsmblob blob; + struct lsmcontext lsmcxt; lsmblob_init(&blob, n->osid); if (security_secid_to_secctx(&blob, &ctx, &len)) { @@ -1602,7 +1607,8 @@ static void audit_log_name(struct audit_context *context, struct audit_names *n, *call_panic = 2; } else { audit_log_format(ab, " obj=%s", ctx); - security_release_secctx(ctx, len); + lsmcontext_init(&lsmcxt, ctx, len, 0); /* scaffolding */ + security_release_secctx(&lsmcxt); } } diff --git a/net/ipv4/ip_sockglue.c b/net/ipv4/ip_sockglue.c index 933a8f94f93a..70ca4510ea35 100644 --- a/net/ipv4/ip_sockglue.c +++ b/net/ipv4/ip_sockglue.c @@ -130,6 +130,7 @@ static void ip_cmsg_recv_checksum(struct msghdr *msg, struct sk_buff *skb, static void ip_cmsg_recv_security(struct msghdr *msg, struct sk_buff *skb) { + struct lsmcontext context; struct lsmblob lb; char *secdata; u32 seclen, secid; @@ -145,7 +146,8 @@ static void ip_cmsg_recv_security(struct msghdr *msg, struct sk_buff *skb) return; put_cmsg(msg, SOL_IP, SCM_SECURITY, seclen, secdata); - security_release_secctx(secdata, seclen); + lsmcontext_init(&context, secdata, seclen, 0); /* scaffolding */ + security_release_secctx(&context); } static void ip_cmsg_recv_dstaddr(struct msghdr *msg, struct sk_buff *skb) diff --git a/net/netfilter/nf_conntrack_netlink.c b/net/netfilter/nf_conntrack_netlink.c index ddc8cd65ed12..da36301e2185 100644 --- a/net/netfilter/nf_conntrack_netlink.c +++ b/net/netfilter/nf_conntrack_netlink.c @@ -348,6 +348,7 @@ static int ctnetlink_dump_secctx(struct sk_buff *skb, const struct nf_conn *ct) int len, ret; char *secctx; struct lsmblob blob; + struct lsmcontext context; /* lsmblob_init() puts ct->secmark into all of the secids in blob. * security_secid_to_secctx() will know which security module @@ -368,7 +369,8 @@ static int ctnetlink_dump_secctx(struct sk_buff *skb, const struct nf_conn *ct) ret = 0; nla_put_failure: - security_release_secctx(secctx, len); + lsmcontext_init(&context, secctx, len, 0); /* scaffolding */ + security_release_secctx(&context); return ret; } #else diff --git a/net/netfilter/nf_conntrack_standalone.c b/net/netfilter/nf_conntrack_standalone.c index 2c1f3280d56e..644dec6a8ef5 100644 --- a/net/netfilter/nf_conntrack_standalone.c +++ b/net/netfilter/nf_conntrack_standalone.c @@ -179,6 +179,7 @@ static void ct_show_secctx(struct seq_file *s, const struct nf_conn *ct) u32 len; char *secctx; struct lsmblob blob; + struct lsmcontext context; lsmblob_init(&blob, ct->secmark); ret = security_secid_to_secctx(&blob, &secctx, &len); @@ -187,7 +188,8 @@ static void ct_show_secctx(struct seq_file *s, const struct nf_conn *ct) seq_printf(s, "secctx=%s ", secctx); - security_release_secctx(secctx, len); + lsmcontext_init(&context, secctx, len, 0); /* scaffolding */ + security_release_secctx(&context); } #else static inline void ct_show_secctx(struct seq_file *s, const struct nf_conn *ct) diff --git a/net/netfilter/nfnetlink_queue.c b/net/netfilter/nfnetlink_queue.c index 6269fe122345..f69d5e997da2 100644 --- a/net/netfilter/nfnetlink_queue.c +++ b/net/netfilter/nfnetlink_queue.c @@ -397,6 +397,7 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, enum ip_conntrack_info ctinfo = 0; const struct nfnl_ct_hook *nfnl_ct; bool csum_verify; + struct lsmcontext scaff; /* scaffolding */ char *secdata = NULL; u32 seclen = 0; ktime_t tstamp; @@ -634,8 +635,10 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, } nlh->nlmsg_len = skb->len; - if (seclen) - security_release_secctx(secdata, seclen); + if (seclen) { + lsmcontext_init(&scaff, secdata, seclen, 0); + security_release_secctx(&scaff); + } return skb; nla_put_failure: @@ -643,8 +646,10 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, kfree_skb(skb); net_err_ratelimited("nf_queue: error creating packet message\n"); nlmsg_failure: - if (seclen) - security_release_secctx(secdata, seclen); + if (seclen) { + lsmcontext_init(&scaff, secdata, seclen, 0); + security_release_secctx(&scaff); + } return NULL; } diff --git a/net/netlabel/netlabel_unlabeled.c b/net/netlabel/netlabel_unlabeled.c index bbb3b6a4f0d7..b3e3d920034d 100644 --- a/net/netlabel/netlabel_unlabeled.c +++ b/net/netlabel/netlabel_unlabeled.c @@ -374,6 +374,7 @@ int netlbl_unlhsh_add(struct net *net, struct net_device *dev; struct netlbl_unlhsh_iface *iface; struct audit_buffer *audit_buf = NULL; + struct lsmcontext context; char *secctx = NULL; u32 secctx_len; struct lsmblob blob; @@ -447,7 +448,9 @@ int netlbl_unlhsh_add(struct net *net, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " sec_obj=%s", secctx); - security_release_secctx(secctx, secctx_len); + /* scaffolding */ + lsmcontext_init(&context, secctx, secctx_len, 0); + security_release_secctx(&context); } audit_log_format(audit_buf, " res=%u", ret_val == 0 ? 1 : 0); audit_log_end(audit_buf); @@ -478,6 +481,7 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, struct netlbl_unlhsh_addr4 *entry; struct audit_buffer *audit_buf; struct net_device *dev; + struct lsmcontext context; char *secctx; u32 secctx_len; struct lsmblob blob; @@ -508,7 +512,9 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " sec_obj=%s", secctx); - security_release_secctx(secctx, secctx_len); + /* scaffolding */ + lsmcontext_init(&context, secctx, secctx_len, 0); + security_release_secctx(&context); } audit_log_format(audit_buf, " res=%u", entry != NULL ? 1 : 0); audit_log_end(audit_buf); @@ -545,6 +551,7 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, struct netlbl_unlhsh_addr6 *entry; struct audit_buffer *audit_buf; struct net_device *dev; + struct lsmcontext context; char *secctx; u32 secctx_len; struct lsmblob blob; @@ -574,7 +581,8 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " sec_obj=%s", secctx); - security_release_secctx(secctx, secctx_len); + lsmcontext_init(&context, secctx, secctx_len, 0); + security_release_secctx(&context); } audit_log_format(audit_buf, " res=%u", entry != NULL ? 1 : 0); audit_log_end(audit_buf); @@ -1093,6 +1101,7 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, int ret_val = -ENOMEM; struct netlbl_unlhsh_walk_arg *cb_arg = arg; struct net_device *dev; + struct lsmcontext context; void *data; u32 secid; char *secctx; @@ -1163,7 +1172,9 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, NLBL_UNLABEL_A_SECCTX, secctx_len, secctx); - security_release_secctx(secctx, secctx_len); + /* scaffolding */ + lsmcontext_init(&context, secctx, secctx_len, 0); + security_release_secctx(&context); if (ret_val != 0) goto list_cb_failure; diff --git a/net/netlabel/netlabel_user.c b/net/netlabel/netlabel_user.c index 893301ae0131..ef139d8ae7cd 100644 --- a/net/netlabel/netlabel_user.c +++ b/net/netlabel/netlabel_user.c @@ -84,6 +84,7 @@ struct audit_buffer *netlbl_audit_start_common(int type, struct netlbl_audit *audit_info) { struct audit_buffer *audit_buf; + struct lsmcontext context; char *secctx; u32 secctx_len; struct lsmblob blob; @@ -103,7 +104,8 @@ struct audit_buffer *netlbl_audit_start_common(int type, if (audit_info->secid != 0 && security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { audit_log_format(audit_buf, " subj=%s", secctx); - security_release_secctx(secctx, secctx_len); + lsmcontext_init(&context, secctx, secctx_len, 0);/*scaffolding*/ + security_release_secctx(&context); } return audit_buf; diff --git a/security/security.c b/security/security.c index d60bc6abaa40..e434f085afab 100644 --- a/security/security.c +++ b/security/security.c @@ -2373,16 +2373,17 @@ int security_secctx_to_secid(const char *secdata, u32 seclen, } EXPORT_SYMBOL(security_secctx_to_secid); -void security_release_secctx(char *secdata, u32 seclen) +void security_release_secctx(struct lsmcontext *cp) { struct security_hook_list *hp; - int ilsm = lsm_task_ilsm(current); hlist_for_each_entry(hp, &security_hook_heads.release_secctx, list) - if (ilsm == LSMBLOB_INVALID || ilsm == hp->lsmid->slot) { - hp->hook.release_secctx(secdata, seclen); - return; + if (cp->slot == hp->lsmid->slot) { + hp->hook.release_secctx(cp->context, cp->len); + break; } + + memset(cp, 0, sizeof(*cp)); } EXPORT_SYMBOL(security_release_secctx); From patchwork Thu Jun 9 23:01:29 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876120 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id BA520CCA480 for ; Thu, 9 Jun 2022 23:10:17 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1345925AbiFIXKN (ORCPT ); Thu, 9 Jun 2022 19:10:13 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:50626 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1345907AbiFIXKL (ORCPT ); Thu, 9 Jun 2022 19:10:11 -0400 Received: from sonic316-27.consmr.mail.ne1.yahoo.com (sonic316-27.consmr.mail.ne1.yahoo.com [66.163.187.153]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 4D8E412F0EC for ; Thu, 9 Jun 2022 16:10:07 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816207; bh=11Yl0L6BEXDtiUicAPpo8DaV+47sQMhyvYBeOsS8N3U=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=q485xN6wCCfj8tFJoD3/+kpNQlVt6bvb4+gHxP4okDSnpNLrAM6woDZJyPYEbA+86WP5+u4G/5SahMykk0JTy1GlhZgfY4RRqrOwk9Cb0MAAkFN//BG7B8aIms1L80Qi5zTOKhSeOfmCdkU1VXlgiF/ShlNsUE/vnp1UYg9KiGr/BxKxD4b2XvRFIiOtxluPmgVJlBQWIhOsCrwPtbxho1Wj+Uw1A6FKXt3gwIK8ZHAR6Yd9kz8bTiHnpAZE6nLalwInCmvc0Lw5CLh6C+Q5wApf+l1vT8xKAtD0nV7mQvoy/CPmr4utdhhDhuqZF5eXtHUAIxC3ThGYExkTvaTZLg== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816207; bh=g/GDnGQLQhw/3Hwg4EqIRpY2DMXDEREWOOiXABwKWUx=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=d8RlmK8s68Zax15U7bKFyKg8K1vvT4Z6lB5We8SwBMTnSkaKpJayCeEN5uSICRxMlaDBiSRAE+jRdzfQBBC7lvFj6wEk1ebgWLBacHXj/RMYP7aVtNifDhiZpz1yDyGpw8kNfGDmI1uvCWZ9RSipx23dEsx+kFd5X9WxI7NTjsPA8wV/fqfpa3WDazdynDXrqmANzrOXieVXRy4gflfrecI4X4BhHrdYSZOk3eKRkiZDeG5CgPybQ+9ev46c8VnNhKyUJj70tBP0I8OZWdFNTEfZZoE5Bpw9KYa4qEIjxQ2gTCuGKv569PvSU8w3YNVprEPgcUIE9iKjhmDYpn3Hwg== X-YMail-OSG: dNeGoMMVM1mnWUs7SV5csfY6F3BEXFvmofWKqDdDsjLfSjja_IVXhw2nd4mRpuU w7wkDcQAPzMrGxLOqI94IqCDqypR14rpQBhckn9rVuF.JZvx_e2S4SGnpnEMo8geEKQML4.SWV9w 9CWzSOEJMylhjwtf8XztW0NHD9AWZOKtHwrGjYKNJALCbc5U8aoQQYX72SfBvYt4mo7KWYMaSMD. g_vcZWy..mJlVAZzu.rPvdjTM0Zk7LTfub6roan33jXiDUyipMlQODNHRfd5Pc2_hCbSJKu_cqz. ozih2nrY_GYg6AUDlKWOkuv1kPHolzkPie1EoQTbr0PcbLjA9F8JXz.nICl4n4Mf_qwZnxVbkNmk OlBn3x.6QB7.tJGDmiBuQEI7uWrUKaeTbJ.UXEVZ9nP54_A0uM.QmAH6po7MBaqmiGpCImvfqRJM hS2SFp0_muGjzFy_34PlblukAkb2rolXnJ3gaT90T71wlPSGEZgf6bz1LY5oLyIEqegtPAMj15CN QtH8c_BnWp6wI0Ekt6g9DhklQDXmUmFREsuFyCunXvtdU3Ohg0Kny32x4gzQp5jcbALZbvrXVASZ xjXx6IzT0yTdL_y4WXalA76EgPJi1K0zdlYnAF_a3keQnUWSCMVuQr7TKBM268Y8FL_7ud6xgTZT vZMi8iR1sGP5jxbIsxZeyUF6u8hTHfLCe75GwPRdLm6kJ5IGtQ3Rh16PyIAPh397uqMVGr0SGHz1 pfzXGN0Pt7_KRPLKkEU.8Riua_ZGM1MdyDpBQK9gyydRUY9uVewtBnyR7flgMyK.RKlZ.Gb2o57U 7JSjnTyJoMFRVzJoIdUqJP1M0mKiSQCWj0fuWzk7vO0tKm9j8_hOQBk2vF2ZF3lURo4ETgpaHpbp ajs9VAj9SEHtVwqiA41w_eaXED1xl5ubWgEMxq5e16yat7ztjLAyGQ3sU8L0tXa6LoyW2aFSRAcE 4Iu7dsAvUOBvP2e7TJgfCkx38WJ.VA0_GXEsF8.wjS8rT07.S4b_m5kPF17dOk2SkFrYpITgEMHz HXUz0DhhBZ_CUOltX5p_gjfVFLU1mBwaxIepXltgYaWXuK_HuZ63DlKgPKTRNug2IZEIeOmteCjf ZyAYn4Fkkuljf0rlJUbkAxnup3PUs4MCxwzdlo5A5AhPahg7DQsDT0T0sGASOtEtcBqUGKU34rIL E_0gPhOt43CJIjXx5TnwoiCDGtHKw._rc55tMfhpDyDDHhheWHM0uNc_ve7ysQBzKRosON01Cf7P JerJUQtBhf4713pKlRlpzp5gttVekzZ5eE9qiDswef93uYEcNE7n84F9C5lxGzxmrnmVSjpc3Cnj _RDyfbdSd0vb8.XvS8VyAvfd2T4mUe.GFBFq1l2y244oEOFi9cyPXa6.QKPlm5rSf1kZUUiTobsn nIKt_70Hz1635Vd3Wg0dD8xIB8ycVFCMNEwfb.jyLHIzDXbDnoN.GfU9IhbxfFYiQJ1o7VV9IA3R YUInHwMzL.CvUUA5wU1PJPzuncbnvrD1LY2uo76XJVvusFh3l9Nl61lWZSSlH5A8Hf_7GdKIvS32 m3msq35uujGR3zRwcUJIPUXdchc3CU00nabdsuFUBcDNbeUXalcIekdjbYVHqdC2TtYQzGT8qbyJ tQmwIRmsPaZjO_FJNyRII2BD2nKewGRjtjvjmTZg2pmFuQLDe8X9KkCqLaV_pR4ibiY78WYMEMHm UxK8MzhgStQKUdy120VwSfnHXR15n6scEcE9c_b8uZTMs6CHUhfpMe1b4aS0oSgglV9IY3Z8t37g M6WkjmPO6GL.MRMQTGg3EhBVnEEq6Qeh8Txv05ngz7YINa2t0qOCqBgX5qRz_39TVwiXa2pITUEK hgp5Q_s_ktXHtkx5RHn75wyHXwXeoaDChgEr8lTuwB7.SLEy.ql6nv6yMWnT6KxfABkPHASZDk4U TgDpaul0zTzuTMPL2TQI9a7EEBrptP0g.yTgCVMX3HPepWiz2kvSSb9IPPweFJL.4pb2nkUnnuiq cNYW9xIk7YECecMt63Dhm3AOOnrSPaj0bL8Y9WI1Q7isEozrGamuZULDoCfWKOUc79SlsRe.e3sf OLBggcrnd1oTVxeCeaFhTehilgxFKdFcPneUQZtHdaTpVcDEHKttbN14zdTSMdvIS1NeMurdDCWb 03tLvpw5VCFch7WE3iTzU7NhvLQRQHJ5KcNXMRcb9m0dfrm1W35AcB9dT8huOH6avolgqVBV.5eQ w9svRzHAWYcde6mxT3_jOvUp6Bc5xaODXnn_6WuRHjhKvtAe_IQOUwtjEsO1v95f3KBuQcc7imWO csvdRsNU6thvR7xZmnKuzn9xyo6i_yg-- X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic316.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:10:07 +0000 Received: by hermes--canary-production-ne1-799d7bd497-7z8w4 (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID 62296d5a5fc11a6b88291aff65d8e04f; Thu, 09 Jun 2022 23:10:02 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, netfilter-devel@vger.kernel.org Subject: [PATCH v36 16/33] LSM: Use lsmcontext in security_secid_to_secctx Date: Thu, 9 Jun 2022 16:01:29 -0700 Message-Id: <20220609230146.319210-17-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Replace the (secctx,seclen) pointer pair with a single lsmcontext pointer to allow return of the LSM identifier along with the context and context length. This allows security_release_secctx() to know how to release the context. Callers have been modified to use or save the returned data from the new structure. security_secid_to_secctx() will now return the length value if the passed lsmcontext pointer is NULL. Signed-off-by: Casey Schaufler Cc: netdev@vger.kernel.org Cc: linux-audit@redhat.com Cc: netfilter-devel@vger.kernel.org --- drivers/android/binder.c | 26 ++++++--------- include/linux/security.h | 4 +-- include/net/scm.h | 9 ++---- kernel/audit.c | 42 +++++++++++-------------- kernel/auditsc.c | 31 +++++++----------- net/ipv4/ip_sockglue.c | 8 ++--- net/netfilter/nf_conntrack_netlink.c | 18 ++++------- net/netfilter/nf_conntrack_standalone.c | 7 ++--- net/netfilter/nfnetlink_queue.c | 5 ++- net/netlabel/netlabel_unlabeled.c | 40 +++++++---------------- net/netlabel/netlabel_user.c | 7 ++--- security/security.c | 29 +++++++++++++++-- 12 files changed, 99 insertions(+), 127 deletions(-) diff --git a/drivers/android/binder.c b/drivers/android/binder.c index 9c1ed7fbda87..8ae1a624cd37 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c @@ -2781,9 +2781,7 @@ static void binder_transaction(struct binder_proc *proc, binder_size_t last_fixup_min_off = 0; struct binder_context *context = proc->context; int t_debug_id = atomic_inc_return(&binder_last_id); - char *secctx = NULL; - u32 secctx_sz = 0; - struct lsmcontext scaff; /* scaffolding */ + struct lsmcontext lsmctx = { }; struct list_head sgc_head; struct list_head pf_head; const void __user *user_buffer = (const void __user *) @@ -3059,7 +3057,7 @@ static void binder_transaction(struct binder_proc *proc, size_t added_size; security_cred_getsecid(proc->cred, &blob); - ret = security_secid_to_secctx(&blob, &secctx, &secctx_sz); + ret = security_secid_to_secctx(&blob, &lsmctx); if (ret) { binder_txn_error("%d:%d failed to get security context\n", thread->pid, proc->pid); @@ -3068,7 +3066,7 @@ static void binder_transaction(struct binder_proc *proc, return_error_line = __LINE__; goto err_get_secctx_failed; } - added_size = ALIGN(secctx_sz, sizeof(u64)); + added_size = ALIGN(lsmctx.len, sizeof(u64)); extra_buffers_size += added_size; if (extra_buffers_size < added_size) { binder_txn_error("%d:%d integer overflow of extra_buffers_size\n", @@ -3102,24 +3100,22 @@ static void binder_transaction(struct binder_proc *proc, t->buffer = NULL; goto err_binder_alloc_buf_failed; } - if (secctx) { + if (lsmctx.context) { int err; size_t buf_offset = ALIGN(tr->data_size, sizeof(void *)) + ALIGN(tr->offsets_size, sizeof(void *)) + ALIGN(extra_buffers_size, sizeof(void *)) - - ALIGN(secctx_sz, sizeof(u64)); + ALIGN(lsmctx.len, sizeof(u64)); t->security_ctx = (uintptr_t)t->buffer->user_data + buf_offset; err = binder_alloc_copy_to_buffer(&target_proc->alloc, t->buffer, buf_offset, - secctx, secctx_sz); + lsmctx.context, lsmctx.len); if (err) { t->security_ctx = 0; WARN_ON(1); } - lsmcontext_init(&scaff, secctx, secctx_sz, 0); - security_release_secctx(&scaff); - secctx = NULL; + security_release_secctx(&lsmctx); } t->buffer->debug_id = t->debug_id; t->buffer->transaction = t; @@ -3163,7 +3159,7 @@ static void binder_transaction(struct binder_proc *proc, off_end_offset = off_start_offset + tr->offsets_size; sg_buf_offset = ALIGN(off_end_offset, sizeof(void *)); sg_buf_end_offset = sg_buf_offset + extra_buffers_size - - ALIGN(secctx_sz, sizeof(u64)); + ALIGN(lsmctx.len, sizeof(u64)); off_min = 0; for (buffer_offset = off_start_offset; buffer_offset < off_end_offset; buffer_offset += sizeof(binder_size_t)) { @@ -3534,10 +3530,8 @@ static void binder_transaction(struct binder_proc *proc, binder_alloc_free_buf(&target_proc->alloc, t->buffer); err_binder_alloc_buf_failed: err_bad_extra_size: - if (secctx) { - lsmcontext_init(&scaff, secctx, secctx_sz, 0); - security_release_secctx(&scaff); - } + if (lsmctx.context) + security_release_secctx(&lsmctx); err_get_secctx_failed: kfree(tcomplete); binder_stats_deleted(BINDER_STAT_TRANSACTION_COMPLETE); diff --git a/include/linux/security.h b/include/linux/security.h index a20fc156c697..5afd0148a1a5 100644 --- a/include/linux/security.h +++ b/include/linux/security.h @@ -617,7 +617,7 @@ int security_setprocattr(const char *lsm, const char *name, void *value, size_t size); int security_netlink_send(struct sock *sk, struct sk_buff *skb); int security_ismaclabel(const char *name); -int security_secid_to_secctx(struct lsmblob *blob, char **secdata, u32 *seclen); +int security_secid_to_secctx(struct lsmblob *blob, struct lsmcontext *cp); int security_secctx_to_secid(const char *secdata, u32 seclen, struct lsmblob *blob); void security_release_secctx(struct lsmcontext *cp); @@ -1472,7 +1472,7 @@ static inline int security_ismaclabel(const char *name) } static inline int security_secid_to_secctx(struct lsmblob *blob, - char **secdata, u32 *seclen) + struct lsmcontext *cp) { return -EOPNOTSUPP; } diff --git a/include/net/scm.h b/include/net/scm.h index f273c4d777ec..b77a52f93389 100644 --- a/include/net/scm.h +++ b/include/net/scm.h @@ -94,8 +94,6 @@ static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct sc { struct lsmcontext context; struct lsmblob lb; - char *secdata; - u32 seclen; int err; if (test_bit(SOCK_PASSSEC, &sock->flags)) { @@ -103,12 +101,11 @@ static inline void scm_passec(struct socket *sock, struct msghdr *msg, struct sc * and the infrastructure will know which it is. */ lsmblob_init(&lb, scm->secid); - err = security_secid_to_secctx(&lb, &secdata, &seclen); + err = security_secid_to_secctx(&lb, &context); if (!err) { - put_cmsg(msg, SOL_SOCKET, SCM_SECURITY, seclen, secdata); - /*scaffolding*/ - lsmcontext_init(&context, secdata, seclen, 0); + put_cmsg(msg, SOL_SOCKET, SCM_SECURITY, context.len, + context.context); security_release_secctx(&context); } } diff --git a/kernel/audit.c b/kernel/audit.c index 0eff57959b4e..a885ebdbb91e 100644 --- a/kernel/audit.c +++ b/kernel/audit.c @@ -1212,9 +1212,6 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) struct audit_buffer *ab; u16 msg_type = nlh->nlmsg_type; struct audit_sig_info *sig_data; - char *ctx = NULL; - u32 len; - struct lsmcontext scaff; /* scaffolding */ err = audit_netlink_ok(skb, msg_type); if (err) @@ -1462,33 +1459,33 @@ static int audit_receive_msg(struct sk_buff *skb, struct nlmsghdr *nlh) kfree(new); break; } - case AUDIT_SIGNAL_INFO: - len = 0; + case AUDIT_SIGNAL_INFO: { + struct lsmcontext context = { }; + if (lsmblob_is_set(&audit_sig_lsm)) { - err = security_secid_to_secctx(&audit_sig_lsm, &ctx, - &len); + err = security_secid_to_secctx(&audit_sig_lsm, + &context); if (err) return err; } - sig_data = kmalloc(struct_size(sig_data, ctx, len), GFP_KERNEL); + sig_data = kmalloc(struct_size(sig_data, ctx, context.len), + GFP_KERNEL); if (!sig_data) { - if (lsmblob_is_set(&audit_sig_lsm)) { - lsmcontext_init(&scaff, ctx, len, 0); - security_release_secctx(&scaff); - } + if (lsmblob_is_set(&audit_sig_lsm)) + security_release_secctx(&context); return -ENOMEM; } sig_data->uid = from_kuid(&init_user_ns, audit_sig_uid); sig_data->pid = audit_sig_pid; if (lsmblob_is_set(&audit_sig_lsm)) { - memcpy(sig_data->ctx, ctx, len); - lsmcontext_init(&scaff, ctx, len, 0); - security_release_secctx(&scaff); + memcpy(sig_data->ctx, context.context, context.len); + security_release_secctx(&context); } - audit_send_reply(skb, seq, AUDIT_SIGNAL_INFO, 0, 0, - sig_data, struct_size(sig_data, ctx, len)); + audit_send_reply(skb, seq, AUDIT_SIGNAL_INFO, 0, 0, sig_data, + struct_size(sig_data, ctx, context.len)); kfree(sig_data); break; + } case AUDIT_TTY_GET: { struct audit_tty_status s; unsigned int t; @@ -2171,17 +2168,15 @@ void audit_log_key(struct audit_buffer *ab, char *key) int audit_log_task_context(struct audit_buffer *ab) { - char *ctx = NULL; - unsigned len; int error; struct lsmblob blob; - struct lsmcontext scaff; /* scaffolding */ + struct lsmcontext context; security_current_getsecid_subj(&blob); if (!lsmblob_is_set(&blob)) return 0; - error = security_secid_to_secctx(&blob, &ctx, &len); + error = security_secid_to_secctx(&blob, &context); if (error) { if (error != -EINVAL) @@ -2189,9 +2184,8 @@ int audit_log_task_context(struct audit_buffer *ab) return 0; } - audit_log_format(ab, " subj=%s", ctx); - lsmcontext_init(&scaff, ctx, len, 0); - security_release_secctx(&scaff); + audit_log_format(ab, " subj=%s", context.context); + security_release_secctx(&context); return 0; error_path: diff --git a/kernel/auditsc.c b/kernel/auditsc.c index cc902c9df77f..8551ce71e6c9 100644 --- a/kernel/auditsc.c +++ b/kernel/auditsc.c @@ -1121,9 +1121,7 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid, struct lsmblob *blob, char *comm) { struct audit_buffer *ab; - struct lsmcontext lsmcxt; - char *ctx = NULL; - u32 len; + struct lsmcontext lsmctx; int rc = 0; ab = audit_log_start(context, GFP_KERNEL, AUDIT_OBJ_PID); @@ -1134,13 +1132,12 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid, from_kuid(&init_user_ns, auid), from_kuid(&init_user_ns, uid), sessionid); if (lsmblob_is_set(blob)) { - if (security_secid_to_secctx(blob, &ctx, &len)) { + if (security_secid_to_secctx(blob, &lsmctx)) { audit_log_format(ab, " obj=(none)"); rc = 1; } else { - audit_log_format(ab, " obj=%s", ctx); - lsmcontext_init(&lsmcxt, ctx, len, 0); /*scaffolding*/ - security_release_secctx(&lsmcxt); + audit_log_format(ab, " obj=%s", lsmctx.context); + security_release_secctx(&lsmctx); } } audit_log_format(ab, " ocomm="); @@ -1400,7 +1397,6 @@ static void audit_log_time(struct audit_context *context, struct audit_buffer ** static void show_special(struct audit_context *context, int *call_panic) { - struct lsmcontext lsmcxt; struct audit_buffer *ab; int i; @@ -1425,17 +1421,15 @@ static void show_special(struct audit_context *context, int *call_panic) from_kgid(&init_user_ns, context->ipc.gid), context->ipc.mode); if (osid) { - char *ctx = NULL; - u32 len; + struct lsmcontext lsmcxt; struct lsmblob blob; lsmblob_init(&blob, osid); - if (security_secid_to_secctx(&blob, &ctx, &len)) { + if (security_secid_to_secctx(&blob, &lsmcxt)) { audit_log_format(ab, " osid=%u", osid); *call_panic = 1; } else { - audit_log_format(ab, " obj=%s", ctx); - lsmcontext_init(&lsmcxt, ctx, len, 0); + audit_log_format(ab, " obj=%s", lsmcxt.context); security_release_secctx(&lsmcxt); } } @@ -1595,20 +1589,17 @@ static void audit_log_name(struct audit_context *context, struct audit_names *n, MAJOR(n->rdev), MINOR(n->rdev)); if (n->osid != 0) { - char *ctx = NULL; - u32 len; struct lsmblob blob; - struct lsmcontext lsmcxt; + struct lsmcontext lsmctx; lsmblob_init(&blob, n->osid); - if (security_secid_to_secctx(&blob, &ctx, &len)) { + if (security_secid_to_secctx(&blob, &lsmctx)) { audit_log_format(ab, " osid=%u", n->osid); if (call_panic) *call_panic = 2; } else { - audit_log_format(ab, " obj=%s", ctx); - lsmcontext_init(&lsmcxt, ctx, len, 0); /* scaffolding */ - security_release_secctx(&lsmcxt); + audit_log_format(ab, " obj=%s", lsmctx.context); + security_release_secctx(&lsmctx); } } diff --git a/net/ipv4/ip_sockglue.c b/net/ipv4/ip_sockglue.c index 70ca4510ea35..ad5be7707bca 100644 --- a/net/ipv4/ip_sockglue.c +++ b/net/ipv4/ip_sockglue.c @@ -132,8 +132,7 @@ static void ip_cmsg_recv_security(struct msghdr *msg, struct sk_buff *skb) { struct lsmcontext context; struct lsmblob lb; - char *secdata; - u32 seclen, secid; + u32 secid; int err; err = security_socket_getpeersec_dgram(NULL, skb, &secid); @@ -141,12 +140,11 @@ static void ip_cmsg_recv_security(struct msghdr *msg, struct sk_buff *skb) return; lsmblob_init(&lb, secid); - err = security_secid_to_secctx(&lb, &secdata, &seclen); + err = security_secid_to_secctx(&lb, &context); if (err) return; - put_cmsg(msg, SOL_IP, SCM_SECURITY, seclen, secdata); - lsmcontext_init(&context, secdata, seclen, 0); /* scaffolding */ + put_cmsg(msg, SOL_IP, SCM_SECURITY, context.len, context.context); security_release_secctx(&context); } diff --git a/net/netfilter/nf_conntrack_netlink.c b/net/netfilter/nf_conntrack_netlink.c index da36301e2185..8bd6ce5f9e93 100644 --- a/net/netfilter/nf_conntrack_netlink.c +++ b/net/netfilter/nf_conntrack_netlink.c @@ -345,8 +345,7 @@ static int ctnetlink_dump_mark(struct sk_buff *skb, const struct nf_conn *ct) static int ctnetlink_dump_secctx(struct sk_buff *skb, const struct nf_conn *ct) { struct nlattr *nest_secctx; - int len, ret; - char *secctx; + int ret; struct lsmblob blob; struct lsmcontext context; @@ -354,7 +353,7 @@ static int ctnetlink_dump_secctx(struct sk_buff *skb, const struct nf_conn *ct) * security_secid_to_secctx() will know which security module * to use to create the secctx. */ lsmblob_init(&blob, ct->secmark); - ret = security_secid_to_secctx(&blob, &secctx, &len); + ret = security_secid_to_secctx(&blob, &context); if (ret) return 0; @@ -363,13 +362,12 @@ static int ctnetlink_dump_secctx(struct sk_buff *skb, const struct nf_conn *ct) if (!nest_secctx) goto nla_put_failure; - if (nla_put_string(skb, CTA_SECCTX_NAME, secctx)) + if (nla_put_string(skb, CTA_SECCTX_NAME, context.context)) goto nla_put_failure; nla_nest_end(skb, nest_secctx); ret = 0; nla_put_failure: - lsmcontext_init(&context, secctx, len, 0); /* scaffolding */ security_release_secctx(&context); return ret; } @@ -662,15 +660,11 @@ static inline size_t ctnetlink_acct_size(const struct nf_conn *ct) static inline int ctnetlink_secctx_size(const struct nf_conn *ct) { #ifdef CONFIG_NF_CONNTRACK_SECMARK - int len, ret; + int len; struct lsmblob blob; - /* lsmblob_init() puts ct->secmark into all of the secids in blob. - * security_secid_to_secctx() will know which security module - * to use to create the secctx. */ - lsmblob_init(&blob, ct->secmark); - ret = security_secid_to_secctx(&blob, NULL, &len); - if (ret) + len = security_secid_to_secctx(&blob, NULL); + if (len <= 0) return 0; return nla_total_size(0) /* CTA_SECCTX */ diff --git a/net/netfilter/nf_conntrack_standalone.c b/net/netfilter/nf_conntrack_standalone.c index 644dec6a8ef5..5003acf79794 100644 --- a/net/netfilter/nf_conntrack_standalone.c +++ b/net/netfilter/nf_conntrack_standalone.c @@ -176,19 +176,16 @@ static void ct_seq_stop(struct seq_file *s, void *v) static void ct_show_secctx(struct seq_file *s, const struct nf_conn *ct) { int ret; - u32 len; - char *secctx; struct lsmblob blob; struct lsmcontext context; lsmblob_init(&blob, ct->secmark); - ret = security_secid_to_secctx(&blob, &secctx, &len); + ret = security_secid_to_secctx(&blob, &context); if (ret) return; - seq_printf(s, "secctx=%s ", secctx); + seq_printf(s, "secctx=%s ", context.context); - lsmcontext_init(&context, secctx, len, 0); /* scaffolding */ security_release_secctx(&context); } #else diff --git a/net/netfilter/nfnetlink_queue.c b/net/netfilter/nfnetlink_queue.c index f69d5e997da2..35c3cde6bacd 100644 --- a/net/netfilter/nfnetlink_queue.c +++ b/net/netfilter/nfnetlink_queue.c @@ -306,6 +306,7 @@ static u32 nfqnl_get_sk_secctx(struct sk_buff *skb, char **secdata) u32 seclen = 0; #if IS_ENABLED(CONFIG_NETWORK_SECMARK) struct lsmblob blob; + struct lsmcontext context = { }; if (!skb || !sk_fullsock(skb->sk)) return 0; @@ -317,10 +318,12 @@ static u32 nfqnl_get_sk_secctx(struct sk_buff *skb, char **secdata) * blob. security_secid_to_secctx() will know which security * module to use to create the secctx. */ lsmblob_init(&blob, skb->secmark); - security_secid_to_secctx(&blob, secdata, &seclen); + security_secid_to_secctx(&blob, &context); + *secdata = context.context; } read_unlock_bh(&skb->sk->sk_callback_lock); + seclen = context.len; #endif return seclen; } diff --git a/net/netlabel/netlabel_unlabeled.c b/net/netlabel/netlabel_unlabeled.c index b3e3d920034d..12e5d508bd08 100644 --- a/net/netlabel/netlabel_unlabeled.c +++ b/net/netlabel/netlabel_unlabeled.c @@ -375,8 +375,6 @@ int netlbl_unlhsh_add(struct net *net, struct netlbl_unlhsh_iface *iface; struct audit_buffer *audit_buf = NULL; struct lsmcontext context; - char *secctx = NULL; - u32 secctx_len; struct lsmblob blob; if (addr_len != sizeof(struct in_addr) && @@ -444,12 +442,9 @@ int netlbl_unlhsh_add(struct net *net, * security_secid_to_secctx() will know which security module * to use to create the secctx. */ lsmblob_init(&blob, secid); - if (security_secid_to_secctx(&blob, - &secctx, - &secctx_len) == 0) { - audit_log_format(audit_buf, " sec_obj=%s", secctx); - /* scaffolding */ - lsmcontext_init(&context, secctx, secctx_len, 0); + if (security_secid_to_secctx(&blob, &context) == 0) { + audit_log_format(audit_buf, " sec_obj=%s", + context.context); security_release_secctx(&context); } audit_log_format(audit_buf, " res=%u", ret_val == 0 ? 1 : 0); @@ -482,8 +477,6 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, struct audit_buffer *audit_buf; struct net_device *dev; struct lsmcontext context; - char *secctx; - u32 secctx_len; struct lsmblob blob; spin_lock(&netlbl_unlhsh_lock); @@ -509,11 +502,9 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, if (entry != NULL) lsmblob_init(&blob, entry->secid); if (entry != NULL && - security_secid_to_secctx(&blob, - &secctx, &secctx_len) == 0) { - audit_log_format(audit_buf, " sec_obj=%s", secctx); - /* scaffolding */ - lsmcontext_init(&context, secctx, secctx_len, 0); + security_secid_to_secctx(&blob, &context) == 0) { + audit_log_format(audit_buf, " sec_obj=%s", + context.context); security_release_secctx(&context); } audit_log_format(audit_buf, " res=%u", entry != NULL ? 1 : 0); @@ -552,8 +543,6 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, struct audit_buffer *audit_buf; struct net_device *dev; struct lsmcontext context; - char *secctx; - u32 secctx_len; struct lsmblob blob; spin_lock(&netlbl_unlhsh_lock); @@ -578,10 +567,9 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, if (entry != NULL) lsmblob_init(&blob, entry->secid); if (entry != NULL && - security_secid_to_secctx(&blob, - &secctx, &secctx_len) == 0) { - audit_log_format(audit_buf, " sec_obj=%s", secctx); - lsmcontext_init(&context, secctx, secctx_len, 0); + security_secid_to_secctx(&blob, &context) == 0) { + audit_log_format(audit_buf, " sec_obj=%s", + context.context); security_release_secctx(&context); } audit_log_format(audit_buf, " res=%u", entry != NULL ? 1 : 0); @@ -1104,8 +1092,6 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, struct lsmcontext context; void *data; u32 secid; - char *secctx; - u32 secctx_len; struct lsmblob blob; data = genlmsg_put(cb_arg->skb, NETLINK_CB(cb_arg->nl_cb->skb).portid, @@ -1165,15 +1151,13 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, * security_secid_to_secctx() will know which security module * to use to create the secctx. */ lsmblob_init(&blob, secid); - ret_val = security_secid_to_secctx(&blob, &secctx, &secctx_len); + ret_val = security_secid_to_secctx(&blob, &context); if (ret_val != 0) goto list_cb_failure; ret_val = nla_put(cb_arg->skb, NLBL_UNLABEL_A_SECCTX, - secctx_len, - secctx); - /* scaffolding */ - lsmcontext_init(&context, secctx, secctx_len, 0); + context.len, + context.context); security_release_secctx(&context); if (ret_val != 0) goto list_cb_failure; diff --git a/net/netlabel/netlabel_user.c b/net/netlabel/netlabel_user.c index ef139d8ae7cd..951ba0639d20 100644 --- a/net/netlabel/netlabel_user.c +++ b/net/netlabel/netlabel_user.c @@ -85,8 +85,6 @@ struct audit_buffer *netlbl_audit_start_common(int type, { struct audit_buffer *audit_buf; struct lsmcontext context; - char *secctx; - u32 secctx_len; struct lsmblob blob; if (audit_enabled == AUDIT_OFF) @@ -102,9 +100,8 @@ struct audit_buffer *netlbl_audit_start_common(int type, lsmblob_init(&blob, audit_info->secid); if (audit_info->secid != 0 && - security_secid_to_secctx(&blob, &secctx, &secctx_len) == 0) { - audit_log_format(audit_buf, " subj=%s", secctx); - lsmcontext_init(&context, secctx, secctx_len, 0);/*scaffolding*/ + security_secid_to_secctx(&blob, &context) == 0) { + audit_log_format(audit_buf, " subj=%s", context.context); security_release_secctx(&context); } diff --git a/security/security.c b/security/security.c index e434f085afab..b52c7c55a092 100644 --- a/security/security.c +++ b/security/security.c @@ -2337,18 +2337,41 @@ int security_ismaclabel(const char *name) } EXPORT_SYMBOL(security_ismaclabel); -int security_secid_to_secctx(struct lsmblob *blob, char **secdata, u32 *seclen) +/** + * security_secid_to_secctx - convert secid to secctx + * @blob: set of secids + * @cp: lsm context into which result is put + * + * Translate secid information into a secctx string. + * Return a negative value on error. + * If cp is NULL return the length of the string. + * Otherwise, return 0. + */ +int security_secid_to_secctx(struct lsmblob *blob, struct lsmcontext *cp) { struct security_hook_list *hp; int ilsm = lsm_task_ilsm(current); + if (cp) + memset(cp, 0, sizeof(*cp)); + hlist_for_each_entry(hp, &security_hook_heads.secid_to_secctx, list) { if (WARN_ON(hp->lsmid->slot < 0 || hp->lsmid->slot >= lsm_slot)) continue; - if (ilsm == LSMBLOB_INVALID || ilsm == hp->lsmid->slot) + if (ilsm == LSMBLOB_INVALID || ilsm == hp->lsmid->slot) { + if (!cp) { + int len; + int rc; + rc = hp->hook.secid_to_secctx( + blob->secid[hp->lsmid->slot], + NULL, &len); + return rc ? rc : len; + } + cp->slot = hp->lsmid->slot; return hp->hook.secid_to_secctx( blob->secid[hp->lsmid->slot], - secdata, seclen); + &cp->context, &cp->len); + } } return LSM_RET_DEFAULT(secid_to_secctx); From patchwork Thu Jun 9 23:01:32 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876122 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id A2D45C43334 for ; Thu, 9 Jun 2022 23:11:56 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1345946AbiFIXLx (ORCPT ); Thu, 9 Jun 2022 19:11:53 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56972 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1345952AbiFIXLp (ORCPT ); Thu, 9 Jun 2022 19:11:45 -0400 Received: from sonic316-27.consmr.mail.ne1.yahoo.com (sonic316-27.consmr.mail.ne1.yahoo.com [66.163.187.153]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 2FC612ADB for ; Thu, 9 Jun 2022 16:11:43 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816302; bh=V+vPgvaKFDTnMpIdljAHcVYg6xkRL77vK84TmLoWvrc=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=nk1Mq/e2Wjhgp0cWVrrnONe2h8+My6wB5g3exedY62j0l3iem6pd+wKfLhlhMpVOs3mTpFAaZg946cBOtnRWxIoMqUh83AZ+MVJh//M0hWRReLopz06Ry4p16jUPQKCZAeJSPtALFrU9pAxJuaGFh5TU06lhzRZiWUEcQ04+pHkER+KwpPrK/xIryB8oU6DwnN6khRKixhld6BN4zLwS8as60MZ7svo+rXlHvih0Tkhl9Q6AzNDqdTB7LXSpGejqKzXBRMyWFrPD7ww1Rs9MlSkbuyqwprZhAKj5oDo9QmZhHpep9Bhad9bCl9VYAhgbhxaG2zvY/fcuFFHewY/LVw== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816302; bh=1hNYJYHmuIdzxwTv5xP+bHs35TcRhLcX109NwarGqvt=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=XC74rDwcc5ukkBTCDLlH/sMZGk6ZMk9a0+y6/jpvOSUWMQHOo0jSPRiI64exD29AuyEMd1ONW3NNlihbj/3ssyEE/1gNXe/cSVzU4qKpNbeLbPPV6heoreoyV87+qkBJSyU8W1jubGkIvVoPLZ8tuTjK46+HRi5TjVfIBpLtn/pBE6ap4DvN719c20Bc2S6fuoeXQ8Fwm0JcemPZawpX0YgA22B5pXINgnUoG98Eit09hHzReqqd0yxpopWwOQipr7FYHCofTqid6bQzIYuVpe40xztT03y24KCuy2elF0pmCPVpBoDaSYSyJoJNn2CGjf66ezJGoa5fGhtlpJVs7Q== X-YMail-OSG: i0TmqMMVM1m_1bhIAMbbSH.TDDSyQJK9Oh82501AjkB9XWBHCvB0Bk227zPAQrc jarQB4laGFkl7FkYMPXEOlw1VucH.9GJZ2tokwR_CA3diIlBPVltkacEMJ.BPTfGrBwtGfARqVaU 7BvDC50aLull1qckQ6pgvttj0po8HRVDyERsW4tF25gw7VMBYe7ehFQGQwSv1nBW76VP_R6RT8KZ MJwusE4Hcllx5Tmii_j0Fbf4yA304KPgBDoXwpJhtd_z21TKWhxPe9OeOQlPybQE.bJwqZyKsbTv nrWgJRupA9RfjZHCTBv_jAb4HFfCpgtmlG_wJvIv3Sg1X4e8MMKuvlAEMu7qXdbvZM6hYy2t9HOl HR8GDr4xqTRPn7vRw5bBo1Nt4P.erqxMBGflsdvXLB3_76wEAub20PZ1jFgvC9IDVI5ysvjGyukP DUm3nRLp.e_gzCosUnCWElvj19TkLDkF6Dr912HLGF2lBT.R0Hh2_TpWk5cPRmcrWVOtWiLICUDT JWbbzWzNWCwqx3p0f4YpwzbMBrGCFU0Kdca0pJRsRv55phufJ0st2VJ3zeVsYjQjJ2_YlM83mwu. 5g0p8TmHemj6GGOuRYGkYFiOCbwpzTuO2GpWT_DI7NNhFmamKy3XfG1dUtyBRkuYDbxwfDtcPw5h CtXqnhMBfLObM_WLw9yE1Eye_RE.AU7Ue57SZZMRwFw8rcucrxHx_RUOmkBOWdX_7NywqiOK97x8 3ltrXd5yjA5o7oR7Rulym_U.3Z0uwZ3CAfcxgZdRn7IuRv78NzXuwqsnM43ePucKB.TXmG5Wz7vZ _d4GC_wRHFuv7PgTGfhbkV.kOK568pnA.WL7ZES7vUpRizv8XB_bzZT9w2VGI4Y2sOfM5wCWEveU 7bVgRjU73Dm82AOWc187c2uqCLhp1PmKHjltfW2vN_zzH1brTzwia.sBuU9wOdoaI9rguEmdtK_N sJDUNt0S_393U9KsO9r8uYTJVvNne_s1ENrOjq_oSZM1mY5LM6516Wzrfpz0ck83jJ.cz1r2348W 89Y4DBClkfqys_7qZBYK4vNPfQidG9kmKcd.y9ZWk5YaAH2bMsuoC6BIJvFxDQA.4CM10ZMrdf.Z GThs93__U9n_fPjSewmj_M8tMNLZK0fYYFP6zZUAg07xkb1j_7zkxGJ52YGCXFTrXb9x4WmhPNSL ociKlPSbRaWvNz45m0vkBXDFwJG1lUaz59d0EfDivzd1BvmLejN5OL9MTsPeJp2f5EydW.sN3YHW gTQAhS7T.Vl4YFe_40LT73ut4CD6TfnwlkipHNqgRI5zDAve_05YrnAq2I0CY_HjS_bkhDD2e2Bo 0LyCRODoHD9hS1n6AZ9gdysKPv1IddVIHVKQdZOpcMttcbkUZZTkRrFHiLbHKCCw0oIjfT32CRAs WW4Wn5H.udnc06FutES_TREt9ATzlmIoo7YtYmkklZ3aV814HWIb1LC_R4LXqS_uTru2ZGg.50TX CDoDZmMk1IODtNCyYJVyajn6mT7fPBRSWQatHqDJl.ch65wTq2HRLtyU1RZlflSl4Iy4oPtQNSvI bXYmdJMgU1zaqD4K1JI8OBknJwpwxveiMUCf83fSaO1GK46EcsJ43Awj88jPBqWD_KNf2SYpvjfI 4Wz7bGcwHWsUlEgbc4WFZMtwhMNPd9X8u82_BuZE2XFJSfJIYvCRfdyoB1d03hIazMeGstGiPjC6 cfSSdqHpnzWcXKCifPRwMXQCoIu.YMgDx3h7h_2.GjqH8BCRqJ4ob_dssZEafWWj9xuM9NpafVr5 gAuNX1eX_4g44vTJK0hjzfQv0wqkhpLIxhdho1q.rhx58z7fYWFMVlczzemL5bG2FeytKLO3Fyna .38L0yFONAnHz00k366tj7qatc2dkGaKUxvQTZhWy4l2R1M1tLswW5JdPs4VoEMGYt1UXxEUvsE3 zPkqQ_bfEL2VuF1Vq5y62L53eHVRL_nZECfogBYm_hf_tuWca51WzNwcGp0eAvwvwkIv2xHCbJ2y _oYUZr3kEZszPDw8rCweMtAvada4vyZIGNdf9sJ4iK7fNFSSQ8YxYZVkU8aanrbvGKtr9sCzz4Hp VE4jmLl_MBMPZwrSMDWFSKU1nQhnd3RfcXr9M4b1ygcdx03lgnkDMHEe9AYYftoj7oFdYFZgHWJu S426l6BpxnHD2hb3HkR0peLFjEbdi21MigZZaYrtuarbrYm.HrXBluXFzpcGoBnucHELnoaTOHXw _alvytQ2V.iwGqcE1vxRoD1cD1KAlMljfTEoJru3KVM5Ala5FSGT41Qp6QjR0vIOehrlGbqzoPuC wbQeQL1fUbWgk8jXe8hv7AX.PQdk_5qNEaqzFkXvoAqqY6HqYyudbd1ljSiBW_G31FBJMze4GZao 41oAagsY- X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic316.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:11:42 +0000 Received: by hermes--canary-production-gq1-54945cc758-dgl4g (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID df8474cdcb3bbd72743eb86b005fa96d; Thu, 09 Jun 2022 23:11:39 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, Pablo Neira Ayuso , netdev@vger.kernel.org, netfilter-devel@vger.kernel.org Subject: [PATCH v36 19/33] LSM: security_secid_to_secctx in netlink netfilter Date: Thu, 9 Jun 2022 16:01:32 -0700 Message-Id: <20220609230146.319210-20-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Change netlink netfilter interfaces to use lsmcontext pointers, and remove scaffolding. Reviewed-by: Kees Cook Reviewed-by: John Johansen Acked-by: Paul Moore Acked-by: Stephen Smalley Acked-by: Pablo Neira Ayuso Signed-off-by: Casey Schaufler Cc: netdev@vger.kernel.org Cc: netfilter-devel@vger.kernel.org --- net/netfilter/nfnetlink_queue.c | 37 +++++++++++++-------------------- 1 file changed, 14 insertions(+), 23 deletions(-) diff --git a/net/netfilter/nfnetlink_queue.c b/net/netfilter/nfnetlink_queue.c index 35c3cde6bacd..f60a0b6240ff 100644 --- a/net/netfilter/nfnetlink_queue.c +++ b/net/netfilter/nfnetlink_queue.c @@ -301,15 +301,13 @@ static int nfqnl_put_sk_uidgid(struct sk_buff *skb, struct sock *sk) return -1; } -static u32 nfqnl_get_sk_secctx(struct sk_buff *skb, char **secdata) +static void nfqnl_get_sk_secctx(struct sk_buff *skb, struct lsmcontext *context) { - u32 seclen = 0; #if IS_ENABLED(CONFIG_NETWORK_SECMARK) struct lsmblob blob; - struct lsmcontext context = { }; if (!skb || !sk_fullsock(skb->sk)) - return 0; + return; read_lock_bh(&skb->sk->sk_callback_lock); @@ -318,14 +316,12 @@ static u32 nfqnl_get_sk_secctx(struct sk_buff *skb, char **secdata) * blob. security_secid_to_secctx() will know which security * module to use to create the secctx. */ lsmblob_init(&blob, skb->secmark); - security_secid_to_secctx(&blob, &context); - *secdata = context.context; + security_secid_to_secctx(&blob, context); } read_unlock_bh(&skb->sk->sk_callback_lock); - seclen = context.len; #endif - return seclen; + return; } static u32 nfqnl_get_bridge_size(struct nf_queue_entry *entry) @@ -397,12 +393,10 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, struct net_device *indev; struct net_device *outdev; struct nf_conn *ct = NULL; + struct lsmcontext context = { }; enum ip_conntrack_info ctinfo = 0; const struct nfnl_ct_hook *nfnl_ct; bool csum_verify; - struct lsmcontext scaff; /* scaffolding */ - char *secdata = NULL; - u32 seclen = 0; ktime_t tstamp; size = nlmsg_total_size(sizeof(struct nfgenmsg)) @@ -473,9 +467,9 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, } if ((queue->flags & NFQA_CFG_F_SECCTX) && entskb->sk) { - seclen = nfqnl_get_sk_secctx(entskb, &secdata); - if (seclen) - size += nla_total_size(seclen); + nfqnl_get_sk_secctx(entskb, &context); + if (context.len) + size += nla_total_size(context.len); } skb = alloc_skb(size, GFP_ATOMIC); @@ -610,7 +604,8 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, nfqnl_put_sk_uidgid(skb, entskb->sk) < 0) goto nla_put_failure; - if (seclen && nla_put(skb, NFQA_SECCTX, seclen, secdata)) + if (context.len && + nla_put(skb, NFQA_SECCTX, context.len, context.context)) goto nla_put_failure; if (ct && nfnl_ct->build(skb, ct, ctinfo, NFQA_CT, NFQA_CT_INFO) < 0) @@ -638,10 +633,8 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, } nlh->nlmsg_len = skb->len; - if (seclen) { - lsmcontext_init(&scaff, secdata, seclen, 0); - security_release_secctx(&scaff); - } + if (context.len) + security_release_secctx(&context); return skb; nla_put_failure: @@ -649,10 +642,8 @@ nfqnl_build_packet_message(struct net *net, struct nfqnl_instance *queue, kfree_skb(skb); net_err_ratelimited("nf_queue: error creating packet message\n"); nlmsg_failure: - if (seclen) { - lsmcontext_init(&scaff, secdata, seclen, 0); - security_release_secctx(&scaff); - } + if (context.len) + security_release_secctx(&context); return NULL; } From patchwork Thu Jun 9 23:01:33 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Casey Schaufler X-Patchwork-Id: 12876123 X-Patchwork-Delegate: kuba@kernel.org Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 548B0C433EF for ; Thu, 9 Jun 2022 23:11:57 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1345964AbiFIXLy (ORCPT ); Thu, 9 Jun 2022 19:11:54 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:57554 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1345957AbiFIXLw (ORCPT ); Thu, 9 Jun 2022 19:11:52 -0400 Received: from sonic301-38.consmr.mail.ne1.yahoo.com (sonic301-38.consmr.mail.ne1.yahoo.com [66.163.184.207]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id D6464B4AC for ; Thu, 9 Jun 2022 16:11:44 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816304; bh=o6IufmSzRJj0pAlCqYa+ffLikcJIYt0ihD1KLQmDBIQ=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From:Subject:Reply-To; b=VhBjMjGJKpIF3S9qMpL5J1NFRvbpSIDqw+jDPKqbOxz2tHa6jbww4VdGP3glOrc1XCqE1NbmLP/FIfd2aFZalZMv21YDT5l3gcpkv5EStpVKWLWb7DLSB3Nc/pnquhj4e5LXYOz9tTr4ktv9RKXiDm1GWT29KWDmgo8/IIAt21dcoOBkg4FpvtdLJvaW/X29kiCVix7nS6G29Gbws3kISbxL2hnPgLWo8+bFM3A/lbKJfVAlvNRme+R9UQr1PUX4ZC6QjVILBzyutIFkdJHR/dF/uTBbFj/CdfQg4dtGIc4wf6ZtA7X+iM+SrQILwISQafmzjriVM6rg8t838S2kJg== X-SONIC-DKIM-SIGN: v=1; a=rsa-sha256; c=relaxed/relaxed; d=yahoo.com; s=s2048; t=1654816304; bh=TOdfPmknfZhwCVfWX/3kYsfURSVSocGceJNcJP4DwzF=; h=X-Sonic-MF:From:To:Subject:Date:From:Subject; b=fRpGE67SdHYr+vWDnZSTmSDGEIVezlH6QRgxofiunGk2ELJe1sIHOhx4vAzuibI4C6nKy1j8gu2KaACphZFsgqM8NmsN4ClQkoxvKC2b9M+KjVNEPcP/6mmQXmfk84BV3tzVxuPcZxo6UugPprsTAv5dD1Isn3E3PJushVsFmgThtxMWOrUtdJ6bVwCmGGWa2MWIdEamaQU7ruURGDtt7wCDXTtEy46H+jnj79yrJVTARTyahCfnnIAbDyD0geAj97yS1oWbv0yw3olE2dpwEXzA8nhzUp9W8S9++MwjE4tKHN+NDBX4PhEempbvITzt+RpAr7E31xf1cc5sYH6eTg== X-YMail-OSG: xiitr1MVM1nz5m7Kovu7X42TEjdKUYaBOi9uucHamzZ7NVB_cyMjB1EqloAyNsc uhCo2wTArlvtt1bOdkKcTanCqc0phsFwRH806ZxG1Noi9roK0l68SKZWWgFsds2SUkYmx0WYv2XJ v6Jl.Wc6uuR7ljlIiBHwbIQ7ytbOg0b0syvnHXwth7dlphb_JtSYW50yKvjM3l12.iMnLJ2w3nck 30eGSifF.F0Hw_QC42vcf.O0XziK1DfAv93ZPGrF44B1kyxNBLDSYDo2RCnzg91c9mYkYna36W9S JmBOAzDSh1Y.LGIo7XBiLyiEw3z6hq7w.INQnlVwTKtgpgwO3JGg2p.ixUVSV55n6DH0V5dF8cFD yn_YNNjbvOkV7OjyG0eiEG.Ng8g45S4V5GdWWdB4nBAFvdwneN.uJ9wzY.pmN4Pf1gmkbKL1LUD8 t90sCs7HGakLkZ6z3QSWICbtW6VaCXjzYqYhBKrLoZ.IuGo6rMlHyc0PhVGV4t47Jfmzpl34sH_Y n3e9AOBBQ_hE8oHbMf42x9rUCyczFoCZ37Y2Ctwt3vAMLHZf3NMHa8D.5iO3RSSidPKZQ7ZCjMvU aWdrQuIG4cMQbMo1g41VFnK7A2mNLInzUXn5ULJ28movojl7ehVBelTTVpForISWw3fm2L4b8OBR ADB545g2sTQVWp5xAXY59M5ZAZSSBccjg8rCqaZ4exlhLYuPkDqKIT7F9jrN94saeZJ3OHONCYaF rfhxB6JGt026KxpHdM8P_UvdZ36T6EPlcKPS1CbiygNbJXAznd7RY8U5vxCXSfMtIKND_Ck3pYh3 9lMLtziFHqWKzGQsV9Q5Sai7zutUSHgkksoSoZSTEXRUzHtWznIbdDGogUcBUibrSiQJ7LBQs9Hv 9Khp.O2KHsfwLbGyl069HOk8upgVvYdujbcpxxe3ntV7If_jadLGxxl.AEPZVLDd5F7crHOn2Qn6 58GrecrVFU0dMI_ivsBn.31pdBqVp.r4yQCskPUoIU8rp6U8WZsQjOXqf2yZrs0p3KMhxtQI_FxI _QLKqDc.cCCDjIwxeKjprVcku.Sycp0J88NHA3HKaTkHmOLz_BBYakMcUWieNEfZrpQzupzu80FR 18DQpQRr3zKLnS2pL3S5nQvYJGZIRNazjMU4VOp5RSeLH5iMKyLLzKBSh6SpwsPUcUVn4_bM1.QV bldUEKxL_S8BQ_LRMwzR_2lJWf4JTGGx3QmT3a.ANF0ZATvlU_iPRPbdjZY0lu6FZCzzs0eHkPyN O8LA_LQJLXRVaaOMMEKA.2H4BSjLyGV5G.myGqVkb5kJ216ywitPbb6XGuZ0oPFl9VdCIS7iPWdy qhyrKxFiSkk402s1NzPnE9TS2lzlpWh6jNiUcdCT1xgX4pP3Pm1A_nCu1YrGHU7M39Up_BKz_EOM iK7su6yCJ.deRWZDT4jjGnFdfoD6Pv_MCjwL_ftsSCqLxK7KS8wT52tN4N_jrKx0w75S5RcyM6Cc e.sH1.1g7WtdAAnXyII0gBV1GVVrKxVBR05rluoISQDwQifadrkv1w9UclTX9Olu83ZbSRRWC.WF P8MSPuG.twKHO5lEZLLIOUAKCvqXCMMSL52kR_tzXtqrSu6BgMnNIJaidBg.59w7qPVsBaJaEnJ9 r2lByTYe6EoQG39QSvJfEAtHRXz3blvkimb5xAdk3vrkho3tIMqhdTUNdSkR6Mb22JaYj2O1bOOE X0kL8JkF6fO5l_X4_UIP7qMxpu.XgK.yEIo4kq1Sfeo.kWUptvJsskJdmojQwrZwMyqs6qBm1HTu 0.ItgPkBECMJlOiaHOlrtQzaOppN9rB05ISt5hak2s479MnN41EhqP_HIlIPUNTbl4dhSuZoaFgD XTo_VlCx04uCiyimYO09MtKws.zKscsQRMgexNr8fJiiCTEBFF2OtSqGGE8vWujJc9xYVgd3jfnR b2ezIALT1_Gk9DlZhz63CjU93N56XJrtaMvSE._XQ2dYvHcbZCj2DlpbEB.ZTsngqNoxjO0Q18eY io_wedyGvP_kgGQ9gYSjcbGpzowIn8yjLuG7b6qJoXtz.i5VqVxemXCqJoC91Cxvm6rXqXqC65kp 8E7RJY3fpB1wvnhJweNZA_.qy2bL_l5DqlX8S.Gwijz7nadMwbM7FQQs6KZvS9kQha8LvCvxt2g0 amPqDeYGrhOHecd2RBRnwR3UymNUyOvLZhtk_l6178bOI_IPPfyjxyUBiweh4GBD1pdYPrj2Hrzi dR7SGLQ9qAXIUqvIDVCgQKLogTEi6FBW4e8kOCMSz3meaaYLQzTOK38bQnI0JrfDQLQa.btJe2Y5 Bsvuy X-Sonic-MF: Received: from sonic.gate.mail.ne1.yahoo.com by sonic301.consmr.mail.ne1.yahoo.com with HTTP; Thu, 9 Jun 2022 23:11:44 +0000 Received: by hermes--canary-production-gq1-54945cc758-dgl4g (Yahoo Inc. Hermes SMTP Server) with ESMTPA ID df8474cdcb3bbd72743eb86b005fa96d; Thu, 09 Jun 2022 23:11:40 +0000 (UTC) From: Casey Schaufler To: casey.schaufler@intel.com, jmorris@namei.org, linux-security-module@vger.kernel.org, selinux@vger.kernel.org Cc: casey@schaufler-ca.com, linux-audit@redhat.com, keescook@chromium.org, john.johansen@canonical.com, penguin-kernel@i-love.sakura.ne.jp, paul@paul-moore.com, stephen.smalley.work@gmail.com, linux-kernel@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v36 20/33] NET: Store LSM netlabel data in a lsmblob Date: Thu, 9 Jun 2022 16:01:33 -0700 Message-Id: <20220609230146.319210-21-casey@schaufler-ca.com> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220609230146.319210-1-casey@schaufler-ca.com> References: <20220609230146.319210-1-casey@schaufler-ca.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org X-Patchwork-Delegate: kuba@kernel.org Netlabel uses LSM interfaces requiring an lsmblob and the internal storage is used to pass information between these interfaces, so change the internal data from a secid to a lsmblob. Update the netlabel interfaces and their callers to accommodate the change. This requires that the modules using netlabel use the lsm_id.slot to access the correct secid when using netlabel. Reviewed-by: Kees Cook Reviewed-by: John Johansen Acked-by: Stephen Smalley Acked-by: Paul Moore Signed-off-by: Casey Schaufler Cc: netdev@vger.kernel.org --- include/net/netlabel.h | 8 +-- net/ipv4/cipso_ipv4.c | 26 ++++++---- net/netlabel/netlabel_kapi.c | 6 +-- net/netlabel/netlabel_unlabeled.c | 79 +++++++++-------------------- net/netlabel/netlabel_unlabeled.h | 2 +- security/selinux/hooks.c | 2 +- security/selinux/include/security.h | 1 + security/selinux/netlabel.c | 2 +- security/selinux/ss/services.c | 4 +- security/smack/smack.h | 1 + security/smack/smack_access.c | 2 +- security/smack/smack_lsm.c | 11 ++-- security/smack/smackfs.c | 10 ++-- 13 files changed, 68 insertions(+), 86 deletions(-) diff --git a/include/net/netlabel.h b/include/net/netlabel.h index 43ae50337685..73fc25b4042b 100644 --- a/include/net/netlabel.h +++ b/include/net/netlabel.h @@ -166,7 +166,7 @@ struct netlbl_lsm_catmap { * @attr.mls: MLS sensitivity label * @attr.mls.cat: MLS category bitmap * @attr.mls.lvl: MLS sensitivity level - * @attr.secid: LSM specific secid token + * @attr.lsmblob: LSM specific data * * Description: * This structure is used to pass security attributes between NetLabel and the @@ -201,7 +201,7 @@ struct netlbl_lsm_secattr { struct netlbl_lsm_catmap *cat; u32 lvl; } mls; - u32 secid; + struct lsmblob lsmblob; } attr; }; @@ -415,7 +415,7 @@ int netlbl_cfg_unlbl_static_add(struct net *net, const void *addr, const void *mask, u16 family, - u32 secid, + struct lsmblob *lsmblob, struct netlbl_audit *audit_info); int netlbl_cfg_unlbl_static_del(struct net *net, const char *dev_name, @@ -523,7 +523,7 @@ static inline int netlbl_cfg_unlbl_static_add(struct net *net, const void *addr, const void *mask, u16 family, - u32 secid, + struct lsmblob *lsmblob, struct netlbl_audit *audit_info) { return -ENOSYS; diff --git a/net/ipv4/cipso_ipv4.c b/net/ipv4/cipso_ipv4.c index 62d5f99760aa..bb9c900da6b0 100644 --- a/net/ipv4/cipso_ipv4.c +++ b/net/ipv4/cipso_ipv4.c @@ -106,15 +106,17 @@ int cipso_v4_rbm_strictvalid = 1; /* Base length of the local tag (non-standard tag). * Tag definition (may change between kernel versions) * - * 0 8 16 24 32 - * +----------+----------+----------+----------+ - * | 10000000 | 00000110 | 32-bit secid value | - * +----------+----------+----------+----------+ - * | in (host byte order)| - * +----------+----------+ - * + * 0 8 16 16 + sizeof(struct lsmblob) + * +----------+----------+---------------------+ + * | 10000000 | 00000110 | LSM blob data | + * +----------+----------+---------------------+ + * + * All secid and flag fields are in host byte order. + * The lsmblob structure size varies depending on which + * Linux security modules are built in the kernel. + * The data is opaque. */ -#define CIPSO_V4_TAG_LOC_BLEN 6 +#define CIPSO_V4_TAG_LOC_BLEN (2 + sizeof(struct lsmblob)) /* * Helper Functions @@ -1460,7 +1462,11 @@ static int cipso_v4_gentag_loc(const struct cipso_v4_doi *doi_def, buffer[0] = CIPSO_V4_TAG_LOCAL; buffer[1] = CIPSO_V4_TAG_LOC_BLEN; - *(u32 *)&buffer[2] = secattr->attr.secid; + /* Ensure that there is sufficient space in the CIPSO header + * for the LSM data. */ + BUILD_BUG_ON(CIPSO_V4_TAG_LOC_BLEN > CIPSO_V4_OPT_LEN_MAX); + memcpy(&buffer[2], &secattr->attr.lsmblob, + sizeof(secattr->attr.lsmblob)); return CIPSO_V4_TAG_LOC_BLEN; } @@ -1480,7 +1486,7 @@ static int cipso_v4_parsetag_loc(const struct cipso_v4_doi *doi_def, const unsigned char *tag, struct netlbl_lsm_secattr *secattr) { - secattr->attr.secid = *(u32 *)&tag[2]; + memcpy(&secattr->attr.lsmblob, &tag[2], sizeof(secattr->attr.lsmblob)); secattr->flags |= NETLBL_SECATTR_SECID; return 0; diff --git a/net/netlabel/netlabel_kapi.c b/net/netlabel/netlabel_kapi.c index 54c083003947..14ebe0424811 100644 --- a/net/netlabel/netlabel_kapi.c +++ b/net/netlabel/netlabel_kapi.c @@ -196,7 +196,7 @@ int netlbl_cfg_unlbl_map_add(const char *domain, * @addr: IP address in network byte order (struct in[6]_addr) * @mask: address mask in network byte order (struct in[6]_addr) * @family: address family - * @secid: LSM secid value for the entry + * @lsmblob: LSM data value for the entry * @audit_info: NetLabel audit information * * Description: @@ -210,7 +210,7 @@ int netlbl_cfg_unlbl_static_add(struct net *net, const void *addr, const void *mask, u16 family, - u32 secid, + struct lsmblob *lsmblob, struct netlbl_audit *audit_info) { u32 addr_len; @@ -230,7 +230,7 @@ int netlbl_cfg_unlbl_static_add(struct net *net, return netlbl_unlhsh_add(net, dev_name, addr, mask, addr_len, - secid, audit_info); + lsmblob, audit_info); } /** diff --git a/net/netlabel/netlabel_unlabeled.c b/net/netlabel/netlabel_unlabeled.c index 12e5d508bd08..910a03f15b0d 100644 --- a/net/netlabel/netlabel_unlabeled.c +++ b/net/netlabel/netlabel_unlabeled.c @@ -66,7 +66,7 @@ struct netlbl_unlhsh_tbl { #define netlbl_unlhsh_addr4_entry(iter) \ container_of(iter, struct netlbl_unlhsh_addr4, list) struct netlbl_unlhsh_addr4 { - u32 secid; + struct lsmblob lsmblob; struct netlbl_af4list list; struct rcu_head rcu; @@ -74,7 +74,7 @@ struct netlbl_unlhsh_addr4 { #define netlbl_unlhsh_addr6_entry(iter) \ container_of(iter, struct netlbl_unlhsh_addr6, list) struct netlbl_unlhsh_addr6 { - u32 secid; + struct lsmblob lsmblob; struct netlbl_af6list list; struct rcu_head rcu; @@ -220,7 +220,7 @@ static struct netlbl_unlhsh_iface *netlbl_unlhsh_search_iface(int ifindex) * @iface: the associated interface entry * @addr: IPv4 address in network byte order * @mask: IPv4 address mask in network byte order - * @secid: LSM secid value for entry + * @lsmblob: LSM data value for entry * * Description: * Add a new address entry into the unlabeled connection hash table using the @@ -231,7 +231,7 @@ static struct netlbl_unlhsh_iface *netlbl_unlhsh_search_iface(int ifindex) static int netlbl_unlhsh_add_addr4(struct netlbl_unlhsh_iface *iface, const struct in_addr *addr, const struct in_addr *mask, - u32 secid) + struct lsmblob *lsmblob) { int ret_val; struct netlbl_unlhsh_addr4 *entry; @@ -243,7 +243,7 @@ static int netlbl_unlhsh_add_addr4(struct netlbl_unlhsh_iface *iface, entry->list.addr = addr->s_addr & mask->s_addr; entry->list.mask = mask->s_addr; entry->list.valid = 1; - entry->secid = secid; + entry->lsmblob = *lsmblob; spin_lock(&netlbl_unlhsh_lock); ret_val = netlbl_af4list_add(&entry->list, &iface->addr4_list); @@ -260,7 +260,7 @@ static int netlbl_unlhsh_add_addr4(struct netlbl_unlhsh_iface *iface, * @iface: the associated interface entry * @addr: IPv6 address in network byte order * @mask: IPv6 address mask in network byte order - * @secid: LSM secid value for entry + * @lsmblob: LSM data value for entry * * Description: * Add a new address entry into the unlabeled connection hash table using the @@ -271,7 +271,7 @@ static int netlbl_unlhsh_add_addr4(struct netlbl_unlhsh_iface *iface, static int netlbl_unlhsh_add_addr6(struct netlbl_unlhsh_iface *iface, const struct in6_addr *addr, const struct in6_addr *mask, - u32 secid) + struct lsmblob *lsmblob) { int ret_val; struct netlbl_unlhsh_addr6 *entry; @@ -287,7 +287,7 @@ static int netlbl_unlhsh_add_addr6(struct netlbl_unlhsh_iface *iface, entry->list.addr.s6_addr32[3] &= mask->s6_addr32[3]; entry->list.mask = *mask; entry->list.valid = 1; - entry->secid = secid; + entry->lsmblob = *lsmblob; spin_lock(&netlbl_unlhsh_lock); ret_val = netlbl_af6list_add(&entry->list, &iface->addr6_list); @@ -366,7 +366,7 @@ int netlbl_unlhsh_add(struct net *net, const void *addr, const void *mask, u32 addr_len, - u32 secid, + struct lsmblob *lsmblob, struct netlbl_audit *audit_info) { int ret_val; @@ -375,7 +375,6 @@ int netlbl_unlhsh_add(struct net *net, struct netlbl_unlhsh_iface *iface; struct audit_buffer *audit_buf = NULL; struct lsmcontext context; - struct lsmblob blob; if (addr_len != sizeof(struct in_addr) && addr_len != sizeof(struct in6_addr)) @@ -408,7 +407,7 @@ int netlbl_unlhsh_add(struct net *net, const struct in_addr *addr4 = addr; const struct in_addr *mask4 = mask; - ret_val = netlbl_unlhsh_add_addr4(iface, addr4, mask4, secid); + ret_val = netlbl_unlhsh_add_addr4(iface, addr4, mask4, lsmblob); if (audit_buf != NULL) netlbl_af4list_audit_addr(audit_buf, 1, dev_name, @@ -421,7 +420,7 @@ int netlbl_unlhsh_add(struct net *net, const struct in6_addr *addr6 = addr; const struct in6_addr *mask6 = mask; - ret_val = netlbl_unlhsh_add_addr6(iface, addr6, mask6, secid); + ret_val = netlbl_unlhsh_add_addr6(iface, addr6, mask6, lsmblob); if (audit_buf != NULL) netlbl_af6list_audit_addr(audit_buf, 1, dev_name, @@ -438,11 +437,7 @@ int netlbl_unlhsh_add(struct net *net, unlhsh_add_return: rcu_read_unlock(); if (audit_buf != NULL) { - /* lsmblob_init() puts secid into all of the secids in blob. - * security_secid_to_secctx() will know which security module - * to use to create the secctx. */ - lsmblob_init(&blob, secid); - if (security_secid_to_secctx(&blob, &context) == 0) { + if (security_secid_to_secctx(lsmblob, &context) == 0) { audit_log_format(audit_buf, " sec_obj=%s", context.context); security_release_secctx(&context); @@ -477,7 +472,6 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, struct audit_buffer *audit_buf; struct net_device *dev; struct lsmcontext context; - struct lsmblob blob; spin_lock(&netlbl_unlhsh_lock); list_entry = netlbl_af4list_remove(addr->s_addr, mask->s_addr, @@ -496,13 +490,8 @@ static int netlbl_unlhsh_remove_addr4(struct net *net, (dev != NULL ? dev->name : NULL), addr->s_addr, mask->s_addr); dev_put(dev); - /* lsmblob_init() puts entry->secid into all of the secids - * in blob. security_secid_to_secctx() will know which - * security module to use to create the secctx. */ - if (entry != NULL) - lsmblob_init(&blob, entry->secid); if (entry != NULL && - security_secid_to_secctx(&blob, &context) == 0) { + security_secid_to_secctx(&entry->lsmblob, &context) == 0) { audit_log_format(audit_buf, " sec_obj=%s", context.context); security_release_secctx(&context); @@ -543,7 +532,6 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, struct audit_buffer *audit_buf; struct net_device *dev; struct lsmcontext context; - struct lsmblob blob; spin_lock(&netlbl_unlhsh_lock); list_entry = netlbl_af6list_remove(addr, mask, &iface->addr6_list); @@ -561,13 +549,8 @@ static int netlbl_unlhsh_remove_addr6(struct net *net, (dev != NULL ? dev->name : NULL), addr, mask); dev_put(dev); - /* lsmblob_init() puts entry->secid into all of the secids - * in blob. security_secid_to_secctx() will know which - * security module to use to create the secctx. */ - if (entry != NULL) - lsmblob_init(&blob, entry->secid); if (entry != NULL && - security_secid_to_secctx(&blob, &context) == 0) { + security_secid_to_secctx(&entry->lsmblob, &context) == 0) { audit_log_format(audit_buf, " sec_obj=%s", context.context); security_release_secctx(&context); @@ -921,14 +904,8 @@ static int netlbl_unlabel_staticadd(struct sk_buff *skb, if (ret_val != 0) return ret_val; - /* netlbl_unlhsh_add will be changed to pass a struct lsmblob * - * instead of a u32 later in this patch set. security_secctx_to_secid() - * will only be setting one entry in the lsmblob struct, so it is - * safe to use lsmblob_value() to get that one value. */ - - return netlbl_unlhsh_add(&init_net, - dev_name, addr, mask, addr_len, - lsmblob_value(&blob), &audit_info); + return netlbl_unlhsh_add(&init_net, dev_name, addr, mask, addr_len, + &blob, &audit_info); } /** @@ -975,11 +952,8 @@ static int netlbl_unlabel_staticadddef(struct sk_buff *skb, if (ret_val != 0) return ret_val; - /* security_secctx_to_secid() will only put one secid into the lsmblob - * so it's safe to use lsmblob_value() to get the secid. */ - return netlbl_unlhsh_add(&init_net, - NULL, addr, mask, addr_len, - lsmblob_value(&blob), &audit_info); + return netlbl_unlhsh_add(&init_net, NULL, addr, mask, addr_len, &blob, + &audit_info); } /** @@ -1091,8 +1065,7 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, struct net_device *dev; struct lsmcontext context; void *data; - u32 secid; - struct lsmblob blob; + struct lsmblob *lsmb; data = genlmsg_put(cb_arg->skb, NETLINK_CB(cb_arg->nl_cb->skb).portid, cb_arg->seq, &netlbl_unlabel_gnl_family, @@ -1130,7 +1103,7 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, if (ret_val != 0) goto list_cb_failure; - secid = addr4->secid; + lsmb = (struct lsmblob *)&addr4->lsmblob; } else { ret_val = nla_put_in6_addr(cb_arg->skb, NLBL_UNLABEL_A_IPV6ADDR, @@ -1144,14 +1117,10 @@ static int netlbl_unlabel_staticlist_gen(u32 cmd, if (ret_val != 0) goto list_cb_failure; - secid = addr6->secid; + lsmb = (struct lsmblob *)&addr6->lsmblob; } - /* lsmblob_init() secid into all of the secids in blob. - * security_secid_to_secctx() will know which security module - * to use to create the secctx. */ - lsmblob_init(&blob, secid); - ret_val = security_secid_to_secctx(&blob, &context); + ret_val = security_secid_to_secctx(lsmb, &context); if (ret_val != 0) goto list_cb_failure; ret_val = nla_put(cb_arg->skb, @@ -1510,7 +1479,7 @@ int netlbl_unlabel_getattr(const struct sk_buff *skb, &iface->addr4_list); if (addr4 == NULL) goto unlabel_getattr_nolabel; - secattr->attr.secid = netlbl_unlhsh_addr4_entry(addr4)->secid; + secattr->attr.lsmblob = netlbl_unlhsh_addr4_entry(addr4)->lsmblob; break; } #if IS_ENABLED(CONFIG_IPV6) @@ -1523,7 +1492,7 @@ int netlbl_unlabel_getattr(const struct sk_buff *skb, &iface->addr6_list); if (addr6 == NULL) goto unlabel_getattr_nolabel; - secattr->attr.secid = netlbl_unlhsh_addr6_entry(addr6)->secid; + secattr->attr.lsmblob = netlbl_unlhsh_addr6_entry(addr6)->lsmblob; break; } #endif /* IPv6 */ diff --git a/net/netlabel/netlabel_unlabeled.h b/net/netlabel/netlabel_unlabeled.h index 058e3a285d56..168920780994 100644 --- a/net/netlabel/netlabel_unlabeled.h +++ b/net/netlabel/netlabel_unlabeled.h @@ -211,7 +211,7 @@ int netlbl_unlhsh_add(struct net *net, const void *addr, const void *mask, u32 addr_len, - u32 secid, + struct lsmblob *lsmblob, struct netlbl_audit *audit_info); int netlbl_unlhsh_remove(struct net *net, const char *dev_name, diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index 36929614c09c..d13024e30c49 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c @@ -7002,7 +7002,7 @@ static int selinux_uring_sqpoll(void) } #endif /* CONFIG_IO_URING */ -static struct lsm_id selinux_lsmid __lsm_ro_after_init = { +struct lsm_id selinux_lsmid __lsm_ro_after_init = { .lsm = "selinux", .slot = LSMBLOB_NEEDED }; diff --git a/security/selinux/include/security.h b/security/selinux/include/security.h index 393aff41d3ef..cfd6c1075b16 100644 --- a/security/selinux/include/security.h +++ b/security/selinux/include/security.h @@ -75,6 +75,7 @@ struct netlbl_lsm_secattr; extern int selinux_enabled_boot; +extern struct lsm_id selinux_lsmid; /* * type_datum properties diff --git a/security/selinux/netlabel.c b/security/selinux/netlabel.c index 800ab4b4239e..0b8f99703462 100644 --- a/security/selinux/netlabel.c +++ b/security/selinux/netlabel.c @@ -109,7 +109,7 @@ static struct netlbl_lsm_secattr *selinux_netlbl_sock_getattr( return NULL; if ((secattr->flags & NETLBL_SECATTR_SECID) && - (secattr->attr.secid == sid)) + (secattr->attr.lsmblob.secid[selinux_lsmid.slot] == sid)) return secattr; return NULL; diff --git a/security/selinux/ss/services.c b/security/selinux/ss/services.c index 69b2734311a6..b4a0570b48bb 100644 --- a/security/selinux/ss/services.c +++ b/security/selinux/ss/services.c @@ -3896,7 +3896,7 @@ int security_netlbl_secattr_to_sid(struct selinux_state *state, if (secattr->flags & NETLBL_SECATTR_CACHE) *sid = *(u32 *)secattr->cache->data; else if (secattr->flags & NETLBL_SECATTR_SECID) - *sid = secattr->attr.secid; + *sid = secattr->attr.lsmblob.secid[selinux_lsmid.slot]; else if (secattr->flags & NETLBL_SECATTR_MLS_LVL) { rc = -EIDRM; ctx = sidtab_search(sidtab, SECINITSID_NETMSG); @@ -3974,7 +3974,7 @@ int security_netlbl_sid_to_secattr(struct selinux_state *state, if (secattr->domain == NULL) goto out; - secattr->attr.secid = sid; + secattr->attr.lsmblob.secid[selinux_lsmid.slot] = sid; secattr->flags |= NETLBL_SECATTR_DOMAIN_CPY | NETLBL_SECATTR_SECID; mls_export_netlbl_lvl(policydb, ctx, secattr); rc = mls_export_netlbl_cat(policydb, ctx, secattr); diff --git a/security/smack/smack.h b/security/smack/smack.h index ef9d0b7b1954..ac79313ea95d 100644 --- a/security/smack/smack.h +++ b/security/smack/smack.h @@ -303,6 +303,7 @@ int smack_populate_secattr(struct smack_known *skp); * Shared data. */ extern int smack_enabled __initdata; +extern struct lsm_id smack_lsmid; extern int smack_cipso_direct; extern int smack_cipso_mapped; extern struct smack_known *smack_net_ambient; diff --git a/security/smack/smack_access.c b/security/smack/smack_access.c index d2186e2757be..c6dcafe18912 100644 --- a/security/smack/smack_access.c +++ b/security/smack/smack_access.c @@ -524,7 +524,7 @@ int smack_populate_secattr(struct smack_known *skp) { int slen; - skp->smk_netlabel.attr.secid = skp->smk_secid; + skp->smk_netlabel.attr.lsmblob.secid[smack_lsmid.slot] = skp->smk_secid; skp->smk_netlabel.domain = skp->smk_known; skp->smk_netlabel.cache = netlbl_secattr_cache_alloc(GFP_ATOMIC); if (skp->smk_netlabel.cache != NULL) { diff --git a/security/smack/smack_lsm.c b/security/smack/smack_lsm.c index 552c4d4d8fac..2190c03ae3d0 100644 --- a/security/smack/smack_lsm.c +++ b/security/smack/smack_lsm.c @@ -3728,11 +3728,12 @@ static struct smack_known *smack_from_secattr(struct netlbl_lsm_secattr *sap, if ((sap->flags & NETLBL_SECATTR_CACHE) != 0) return (struct smack_known *)sap->cache->data; + /* + * Looks like a fallback, which gives us a secid. + */ if ((sap->flags & NETLBL_SECATTR_SECID) != 0) - /* - * Looks like a fallback, which gives us a secid. - */ - return smack_from_secid(sap->attr.secid); + return smack_from_secid( + sap->attr.lsmblob.secid[smack_lsmid.slot]); if ((sap->flags & NETLBL_SECATTR_MLS_LVL) != 0) { /* @@ -4751,7 +4752,7 @@ struct lsm_blob_sizes smack_blob_sizes __lsm_ro_after_init = { .lbs_superblock = sizeof(struct superblock_smack), }; -static struct lsm_id smack_lsmid __lsm_ro_after_init = { +struct lsm_id smack_lsmid __lsm_ro_after_init = { .lsm = "smack", .slot = LSMBLOB_NEEDED }; diff --git a/security/smack/smackfs.c b/security/smack/smackfs.c index 4b58526450d4..314336463111 100644 --- a/security/smack/smackfs.c +++ b/security/smack/smackfs.c @@ -1144,6 +1144,7 @@ static void smk_net4addr_insert(struct smk_net4addr *new) static ssize_t smk_write_net4addr(struct file *file, const char __user *buf, size_t count, loff_t *ppos) { + struct lsmblob lsmblob; struct smk_net4addr *snp; struct sockaddr_in newname; char *smack; @@ -1274,10 +1275,13 @@ static ssize_t smk_write_net4addr(struct file *file, const char __user *buf, * this host so that incoming packets get labeled. * but only if we didn't get the special CIPSO option */ - if (rc == 0 && skp != NULL) + if (rc == 0 && skp != NULL) { + lsmblob_init(&lsmblob, 0); + lsmblob.secid[smack_lsmid.slot] = snp->smk_label->smk_secid; rc = netlbl_cfg_unlbl_static_add(&init_net, NULL, - &snp->smk_host, &snp->smk_mask, PF_INET, - snp->smk_label->smk_secid, &audit_info); + &snp->smk_host, &snp->smk_mask, PF_INET, &lsmblob, + &audit_info); + } if (rc == 0) rc = count;