[PATCH 02/17] nvme-keyring: define a 'psk' keytype

Hannes Reinecke hare at suse.de
Mon May 8 06:56:06 PDT 2023


On 5/8/23 10:59, Max Gurtovoy wrote:
> Hi Hannes,
> 
> On 19/04/2023 9:56, Hannes Reinecke wrote:
>> Define a 'psk' keytype to hold the NVMe TLS PSKs.
>>
>> Signed-off-by: Hannes Reinecke <hare at suse.de>
>> ---
>>   drivers/nvme/common/keyring.c | 94 +++++++++++++++++++++++++++++++++++
>>   1 file changed, 94 insertions(+)
>>
>> diff --git a/drivers/nvme/common/keyring.c 
>> b/drivers/nvme/common/keyring.c
>> index 5cf64b278119..494dd365052e 100644
>> --- a/drivers/nvme/common/keyring.c
>> +++ b/drivers/nvme/common/keyring.c
>> @@ -8,6 +8,8 @@
>>   #include <linux/key-type.h>
>>   #include <keys/user-type.h>
>>   #include <linux/nvme.h>
>> +#include <linux/nvme-tcp.h>
>> +#include <linux/nvme-keyring.h>
>>   static struct key *nvme_keyring;
>> @@ -17,8 +19,94 @@ key_serial_t nvme_keyring_id(void)
>>   }
>>   EXPORT_SYMBOL_GPL(nvme_keyring_id);
>> +static void nvme_tls_psk_describe(const struct key *key, struct 
>> seq_file *m)
>> +{
>> +    seq_puts(m, key->description);
>> +    seq_printf(m, ": %u", key->datalen);
>> +}
>> +
>> +static bool nvme_tls_psk_match(const struct key *key,
>> +                   const struct key_match_data *match_data)
>> +{
>> +    const char *match_id;
>> +    size_t match_len;
>> +
>> +    if (!key->description) {
>> +        pr_debug("%s: no key description\n", __func__);
>> +        return false;
>> +    }
>> +    match_len = strlen(key->description);
>> +    pr_debug("%s: id %s len %zd\n", __func__, key->description, 
>> match_len);
>> +
>> +    if (!match_data->raw_data) {
>> +        pr_debug("%s: no match data\n", __func__);
>> +        return false;
>> +    }
>> +    match_id = match_data->raw_data;
>> +    pr_debug("%s: match '%s' '%s' len %zd\n",
>> +         __func__, match_id, key->description, match_len);
>> +    return !memcmp(key->description, match_id, match_len);
>> +}
>> +
>> +static int nvme_tls_psk_match_preparse(struct key_match_data 
>> *match_data)
>> +{
>> +    match_data->lookup_type = KEYRING_SEARCH_LOOKUP_ITERATE;
>> +    match_data->cmp = nvme_tls_psk_match;
>> +    return 0;
>> +}
>> +
>> +static struct key_type nvme_tls_psk_key_type = {
>> +    .name           = "psk",
>> +    .flags          = KEY_TYPE_NET_DOMAIN,
>> +    .preparse       = user_preparse,
>> +    .free_preparse  = user_free_preparse,
>> +    .match_preparse = nvme_tls_psk_match_preparse,
>> +    .instantiate    = generic_key_instantiate,
>> +    .revoke         = user_revoke,
>> +    .destroy        = user_destroy,
>> +    .describe       = nvme_tls_psk_describe,
>> +    .read           = user_read,
>> +};
>> +
>> +static struct key *nvme_tls_psk_lookup(struct key *keyring,
>> +        const char *hostnqn, const char *subnqn,
>> +        int hmac, bool generated)
>> +{
>> +    char *identity;
>> +    size_t identity_len = (NVMF_NQN_SIZE) * 2 + 11;
>> +    key_ref_t keyref;
>> +    key_serial_t keyring_id;
>> +
>> +    identity = kzalloc(identity_len, GFP_KERNEL);
>> +    if (!identity)
>> +        return ERR_PTR(-ENOMEM);
>> +
>> +    snprintf(identity, identity_len, "NVMe0%c%02d %s %s",
>> +         generated ? 'G' : 'R', hmac, hostnqn, subnqn);
>> +
>> +    if (!keyring)
>> +        keyring = nvme_keyring;
>> +    keyring_id = key_serial(keyring);
>> +    pr_debug("keyring %x lookup tls psk '%s'\n",
>> +         keyring_id, identity);
>> +    keyref = keyring_search(make_key_ref(keyring, true),
>> +                &nvme_tls_psk_key_type,
>> +                identity, false);
>> +    if (IS_ERR(keyref)) {
>> +        pr_debug("lookup tls psk '%s' failed, error %ld\n",
>> +             identity, PTR_ERR(keyref));
>> +        kfree(identity);
>> +        return ERR_PTR(-ENOKEY);
>> +    }
>> +    kfree(identity);
>> +
>> +    return key_ref_to_ptr(keyref);
>> +}
>> +
>>   int nvme_keyring_init(void)
>>   {
>> +    int err;
>> +
>>       nvme_keyring = keyring_alloc(".nvme",
>>                        GLOBAL_ROOT_UID, GLOBAL_ROOT_GID,
>>                        current_cred(),
>> @@ -28,12 +116,18 @@ int nvme_keyring_init(void)
>>       if (IS_ERR(nvme_keyring))
>>           return PTR_ERR(nvme_keyring);
>> +    err = register_key_type(&nvme_tls_psk_key_type);
>> +    if (err) {
>> +        key_put(nvme_keyring);
> 
> I see in the nvme_keyring_exit you call "key_revoke(nvme_keyring);"
> Should we call it here as well ?
> 
Mysteries of the keyring subsystem.
But yeah, I guess we should.

Cheers,

Hannes
-- 
Dr. Hannes Reinecke                Kernel Storage Architect
hare at suse.de                              +49 911 74053 688
SUSE Software Solutions GmbH, Maxfeldstr. 5, 90409 Nürnberg
HRB 36809 (AG Nürnberg), Geschäftsführer: Ivo Totev, Andrew
Myers, Andrew McDonald, Martje Boudien Moerman




More information about the Linux-nvme mailing list