[PATCH, RFC 25/62] keys/mktme: Instantiate and destroy MKTME keys

From: Kirill A. Shutemov
Date: Wed May 08 2019 - 10:51:52 EST


From: Alison Schofield <alison.schofield@xxxxxxxxx>

Instantiating and destroying are two Kernel Key Service methods
that are invoked by the kernel key service when a key is added
(add_key, request_key) or removed (invalidate, revoke, timeout).

During instantiation, MKTME needs to allocate an available hardware
KeyID and map it to the Userspace Key.

During destroy, MKTME wil returned the hardware KeyID to the pool of
available keys.

Signed-off-by: Alison Schofield <alison.schofield@xxxxxxxxx>
Signed-off-by: Kirill A. Shutemov <kirill.shutemov@xxxxxxxxxxxxxxx>
---
security/keys/mktme_keys.c | 24 ++++++++++++++++++++++++
1 file changed, 24 insertions(+)

diff --git a/security/keys/mktme_keys.c b/security/keys/mktme_keys.c
index 92a047caa829..14bc4e600978 100644
--- a/security/keys/mktme_keys.c
+++ b/security/keys/mktme_keys.c
@@ -14,6 +14,8 @@

#include "internal.h"

+static DEFINE_SPINLOCK(mktme_lock);
+
/* 1:1 Mapping between Userspace Keys (struct key) and Hardware KeyIDs */
struct mktme_mapping {
unsigned int mapped_keyids;
@@ -95,6 +97,26 @@ struct mktme_payload {
u8 tweak_key[MKTME_AES_XTS_SIZE];
};

+/* Key Service Method called when a Userspace Key is garbage collected. */
+static void mktme_destroy_key(struct key *key)
+{
+ mktme_release_keyid(mktme_keyid_from_key(key));
+}
+
+/* Key Service Method to create a new key. Payload is preparsed. */
+int mktme_instantiate_key(struct key *key, struct key_preparsed_payload *prep)
+{
+ unsigned long flags;
+ int keyid;
+
+ spin_lock_irqsave(&mktme_lock, flags);
+ keyid = mktme_reserve_keyid(key);
+ spin_unlock_irqrestore(&mktme_lock, flags);
+ if (!keyid)
+ return -ENOKEY;
+ return 0;
+}
+
/* Make sure arguments are correct for the TYPE of key requested */
static int mktme_check_options(struct mktme_payload *payload,
unsigned long token_mask, enum mktme_type type)
@@ -236,7 +258,9 @@ struct key_type key_type_mktme = {
.name = "mktme",
.preparse = mktme_preparse_payload,
.free_preparse = mktme_free_preparsed_payload,
+ .instantiate = mktme_instantiate_key,
.describe = user_describe,
+ .destroy = mktme_destroy_key,
};

static int __init init_mktme(void)
--
2.20.1