// SPDX-License-Identifier: GPL-2.0-only /* * Copyright (C) 2021 Pengutronix, Ahmad Fatoum <kernel@pengutronix.de> */ #include <keys/trusted_caam.h> #include <keys/trusted-type.h> #include <linux/build_bug.h> #include <linux/key-type.h> #include <soc/fsl/caam-blob.h> static struct caam_blob_priv *blobifier; #define KEYMOD "SECURE_KEY" static_assert(MAX_KEY_SIZE + CAAM_BLOB_OVERHEAD <= CAAM_BLOB_MAX_LEN); static_assert(MAX_BLOB_SIZE <= CAAM_BLOB_MAX_LEN); static int trusted_caam_seal(struct trusted_key_payload *p, char *datablob) { int ret; struct caam_blob_info info = { .input = p->key, .input_len = p->key_len, .output = p->blob, .output_len = MAX_BLOB_SIZE, .key_mod = KEYMOD, .key_mod_len = sizeof(KEYMOD) - 1, }; ret = caam_encap_blob(blobifier, &info); if (ret) return ret; p->blob_len = info.output_len; return 0; } static int trusted_caam_unseal(struct trusted_key_payload *p, char *datablob) { int ret; struct caam_blob_info info = { .input = p->blob, .input_len = p->blob_len, .output = p->key, .output_len = MAX_KEY_SIZE, .key_mod = KEYMOD, .key_mod_len = sizeof(KEYMOD) - 1, }; ret = caam_decap_blob(blobifier, &info); if (ret) return ret; p->key_len = info.output_len; return 0; } static int trusted_caam_init(void) { int ret; blobifier = caam_blob_gen_init(); if (IS_ERR(blobifier)) return PTR_ERR(blobifier); ret = register_key_type(&key_type_trusted); if (ret) caam_blob_gen_exit(blobifier); return ret; } static void trusted_caam_exit(void) { unregister_key_type(&key_type_trusted); caam_blob_gen_exit(blobifier); } struct trusted_key_ops trusted_key_caam_ops = { .migratable = 0, /* non-migratable */ .init = trusted_caam_init, .seal = trusted_caam_seal, .unseal = trusted_caam_unseal, .exit = trusted_caam_exit, };