All of lore.kernel.org
 help / color / mirror / Atom feed
From: <krzysztof.struczynski@huawei.com>
To: <linux-integrity@vger.kernel.org>, <linux-kernel@vger.kernel.org>,
	<containers@lists.linux-foundation.org>,
	<linux-security-module@vger.kernel.org>
Cc: <zohar@linux.ibm.com>, <stefanb@linux.vnet.ibm.com>,
	<sunyuqiong1988@gmail.com>, <mkayaalp@cs.binghamton.edu>,
	<dmitry.kasatkin@gmail.com>, <serge@hallyn.com>,
	<jmorris@namei.org>, <christian@brauner.io>,
	<silviu.vlasceanu@huawei.com>, <roberto.sassu@huawei.com>,
	Krzysztof Struczynski <krzysztof.struczynski@huawei.com>
Subject: [RFC PATCH 28/30] ima: Load per ima namespace x509 certificate
Date: Tue, 18 Aug 2020 17:42:28 +0200	[thread overview]
Message-ID: <20200818154230.14016-19-krzysztof.struczynski@huawei.com> (raw)
In-Reply-To: <20200818154230.14016-1-krzysztof.struczynski@huawei.com>

From: Krzysztof Struczynski <krzysztof.struczynski@huawei.com>

If configured, load the x509 certificate when the first process is
born into the new ima namespace. User can set the path to the
certificate by writing to the x509_for_children entry in the ima
securityfs.

Signed-off-by: Krzysztof Struczynski <krzysztof.struczynski@huawei.com>
---
 security/integrity/digsig.c     |  6 +--
 security/integrity/ima/ima_ns.c | 69 ++++++++++++++++++++++++++++-----
 security/integrity/integrity.h  |  2 +-
 3 files changed, 63 insertions(+), 14 deletions(-)

diff --git a/security/integrity/digsig.c b/security/integrity/digsig.c
index 523fc786c4d7..8cd54bc83892 100644
--- a/security/integrity/digsig.c
+++ b/security/integrity/digsig.c
@@ -170,8 +170,8 @@ int __init integrity_init_keyring(const unsigned int id)
 	return __integrity_init_keyring(id, perm, restriction);
 }
 
-int __init integrity_add_key(const unsigned int id, const void *data,
-			     off_t size, key_perm_t perm)
+int integrity_add_key(const unsigned int id, const void *data,
+		      off_t size, key_perm_t perm)
 {
 	key_ref_t key;
 	int rc = 0;
@@ -195,7 +195,7 @@ int __init integrity_add_key(const unsigned int id, const void *data,
 
 }
 
-int __init integrity_load_x509(const unsigned int id, const char *path)
+int integrity_load_x509(const unsigned int id, const char *path)
 {
 	void *data;
 	loff_t size;
diff --git a/security/integrity/ima/ima_ns.c b/security/integrity/ima/ima_ns.c
index 872dc6a96a96..11e1d896f603 100644
--- a/security/integrity/ima/ima_ns.c
+++ b/security/integrity/ima/ima_ns.c
@@ -48,6 +48,30 @@ static void dec_ima_namespaces(struct ucounts *ucounts)
 	return dec_ucount(ucounts, UCOUNT_IMA_NAMESPACES);
 }
 
+#ifdef CONFIG_IMA_LOAD_X509
+static int ima_ns_load_x509(struct ima_namespace *ima_ns)
+{
+	int res = 0;
+	int unset_flags =
+		ima_ns->policy_data->ima_policy_flag & IMA_APPRAISE;
+
+	if (!ima_ns->x509_path_for_children)
+		return res;
+
+	ima_ns->policy_data->ima_policy_flag &= ~unset_flags;
+	res = integrity_load_x509(INTEGRITY_KEYRING_IMA,
+				  ima_ns->x509_path_for_children);
+	ima_ns->policy_data->ima_policy_flag |= unset_flags;
+
+	return res;
+}
+#else
+static inline int ima_ns_load_x509(struct ima_namespace *ima_ns)
+{
+	return 0;
+}
+#endif
+
 static struct ima_namespace *ima_ns_alloc(void)
 {
 	struct ima_namespace *ima_ns;
@@ -365,6 +389,10 @@ static int imans_activate(struct ima_namespace *ima_ns)
 	if (res < 0)
 		goto out;
 
+	res = ima_ns_load_x509(ima_ns);
+	if (res < 0)
+		goto out;
+
 	ima_ns->frozen = true;
 
 	/* Set current last element as list's head */
@@ -388,6 +416,7 @@ static int imans_install(struct nsset *nsset, struct ns_common *new)
 	int res;
 	struct nsproxy *nsproxy = nsset->nsproxy;
 	struct ima_namespace *ns = to_ima_ns(new);
+	struct ima_namespace *old_ns = nsproxy->ima_ns;
 
 	if (!current_is_single_threaded())
 		return -EUSERS;
@@ -396,14 +425,24 @@ static int imans_install(struct nsset *nsset, struct ns_common *new)
 	    !ns_capable(nsset->cred->user_ns, CAP_SYS_ADMIN))
 		return -EPERM;
 
-	res = imans_activate(ns);
-	if (res)
-		return res;
-
 	get_ima_ns(ns);
-	put_ima_ns(nsproxy->ima_ns);
+	put_ima_ns(old_ns);
 	nsproxy->ima_ns = ns;
 
+	/* The activation has to take place, after attaching the new namespace
+	 * to the nsproxy. This is because one part of the activation process,
+	 * is loading the appraisal keys, which temporary disables appraisal in
+	 * the current ima namespace, and it must not happen for the "old" ima
+	 * namespace.
+	 */
+	res = imans_activate(ns);
+	if (res) {
+		get_ima_ns(old_ns);
+		put_ima_ns(ns);
+		nsproxy->ima_ns = old_ns;
+		return res;
+	}
+
 	get_ima_ns(ns);
 	put_ima_ns(nsproxy->ima_ns_for_children);
 	nsproxy->ima_ns_for_children = ns;
@@ -416,6 +455,7 @@ int imans_on_fork(struct nsproxy *nsproxy, struct task_struct *tsk,
 {
 	int res;
 	struct ima_namespace *ima_ns = nsproxy->ima_ns_for_children;
+	struct ima_namespace *old_ima_ns = nsproxy->ima_ns;
 
 	/* create_new_namespaces() already incremented the ref counter */
 	if (nsproxy->ima_ns == ima_ns)
@@ -431,14 +471,23 @@ int imans_on_fork(struct nsproxy *nsproxy, struct task_struct *tsk,
 			return res;
 	}
 
-	res = imans_activate(ima_ns);
-	if (res)
-		return res;
-
 	get_ima_ns(ima_ns);
-	put_ima_ns(nsproxy->ima_ns);
+	put_ima_ns(old_ima_ns);
 	nsproxy->ima_ns = ima_ns;
 
+	/* The activation has to take place, after attaching the new namespace
+	 * to the nsproxy. This is because one part of the activation process,
+	 * is loading the appraisal keys, which temporary disables appraisal in
+	 * the current ima namespace, and it must not happen for the "old" ima
+	 * namespace.
+	 */
+	res = imans_activate(ima_ns);
+	if (res) {
+		get_ima_ns(old_ima_ns);
+		put_ima_ns(ima_ns);
+		nsproxy->ima_ns = old_ima_ns;
+	}
+
 	return res;
 }
 
diff --git a/security/integrity/integrity.h b/security/integrity/integrity.h
index 207a1aef28e4..9b080b9fe242 100644
--- a/security/integrity/integrity.h
+++ b/security/integrity/integrity.h
@@ -179,7 +179,7 @@ int integrity_digsig_verify(const unsigned int id, const char *sig, int siglen,
 int integrity_modsig_verify(unsigned int id, const struct modsig *modsig);
 
 int __init integrity_init_keyring(const unsigned int id);
-int __init integrity_load_x509(const unsigned int id, const char *path);
+int integrity_load_x509(const unsigned int id, const char *path);
 int __init integrity_load_cert(const unsigned int id, const char *source,
 			       const void *data, size_t len, key_perm_t perm);
 #else
-- 
2.20.1


  parent reply	other threads:[~2020-08-18 15:52 UTC|newest]

Thread overview: 21+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-08-18 15:42 [RFC PATCH 10/30] ima: Add ima namespace ID to the ima ML related structures krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 11/30] ima: Keep track of the measurment list per ima namespace krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 12/30] ima: Check ima namespace ID during digest entry lookup krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 13/30] ima: Add a new ima template that includes namespace ID krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 14/30] ima: Add per namespace view of the measurement list krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 15/30] ima: Add a reader counter to the integrity inode data krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 16/30] ima: Extend permissions to the ima securityfs entries krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 17/30] ima: Add the violation counter to the namespace krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 18/30] ima: Change the owning user namespace of the ima namespace if necessary krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 19/30] ima: Configure the new ima namespace from securityfs krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 20/30] ima: Parse per ima namespace policy file krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 21/30] user namespace: Add function that checks if the UID map is defined krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 22/30] ima: Remap IDs of subject based rules if necessary krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 23/30] keys: Add domain tag to the keyring search criteria krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 24/30] keys: Include key domain tag in the iterative search krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 25/30] keys: Allow to set key domain tag separately from the key type krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 26/30] ima: Add key domain to the ima namespace krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 27/30] integrity: Add key domain tag to the search criteria krzysztof.struczynski
2020-08-18 15:42 ` krzysztof.struczynski [this message]
2020-08-18 15:42 ` [RFC PATCH 29/30] ima: Add dummy boot aggregate to per ima namespace measurement list krzysztof.struczynski
2020-08-18 15:42 ` [RFC PATCH 30/30] ima: Set ML template per ima namespace krzysztof.struczynski

Reply instructions:

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

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

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

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

  git send-email \
    --in-reply-to=20200818154230.14016-19-krzysztof.struczynski@huawei.com \
    --to=krzysztof.struczynski@huawei.com \
    --cc=christian@brauner.io \
    --cc=containers@lists.linux-foundation.org \
    --cc=dmitry.kasatkin@gmail.com \
    --cc=jmorris@namei.org \
    --cc=linux-integrity@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-security-module@vger.kernel.org \
    --cc=mkayaalp@cs.binghamton.edu \
    --cc=roberto.sassu@huawei.com \
    --cc=serge@hallyn.com \
    --cc=silviu.vlasceanu@huawei.com \
    --cc=stefanb@linux.vnet.ibm.com \
    --cc=sunyuqiong1988@gmail.com \
    --cc=zohar@linux.ibm.com \
    /path/to/YOUR_REPLY

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

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