Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8119c341 authored by qctecmdr's avatar qctecmdr Committed by Gerrit - the friendly Code Review server
Browse files

Merge "soc: qcom: hwkm: Re-format cmd packet for system kdf"

parents 6e625d33 fd16bf96
Loading
Loading
Loading
Loading
+9 −14
Original line number Diff line number Diff line
@@ -9,6 +9,7 @@
#include <linux/crypto-qti-common.h>
#include <linux/hwkm.h>
#include <linux/module.h>
#include <linux/kernel.h>

#include "crypto-qti-ice-regs.h"
#include "crypto-qti-platform.h"
@@ -19,6 +20,8 @@

#define QTI_HWKM_INIT_DONE		0x1
#define SLOT_EMPTY_ERROR		0x1000
#define INLINECRYPT_CTX			"inline encryption key"
#define BYTE_ORDER_VAL			8

union crypto_cfg {
	__le32 regval[2];
@@ -65,19 +68,10 @@ int crypto_qti_program_key(struct crypto_vops_qti_entry *ice_entry,
		.km_by_nsec_allowed = true,
	};
	struct hwkm_bsve bsve_kdf = {
		.enabled = false,
		.enabled = true,
		.km_swc_en = true,
		.km_child_key_policy_en = true,
	};
	u8 ctx[] = {
		0xee, 0xb6, 0xa4, 0xc8, 0x6f, 0x22, 0x5f, 0xda,
		0x18, 0xff, 0x61, 0x07, 0xfb, 0x88, 0x17, 0x7f,
		0xe4, 0x89, 0x8f, 0xed, 0xdb, 0x0c, 0x68, 0xb2,
		0x18, 0xe7, 0x58, 0xd0, 0xf7, 0x79, 0x61, 0xad,
		0x77, 0xc6, 0x4d, 0x2b, 0x53, 0x93, 0x4f, 0x34,
		0xaf, 0x51, 0xab, 0xda, 0x24, 0xa0, 0xa4, 0x76,
		0xf4, 0x09, 0xed, 0xa3, 0x2c, 0xa1, 0x8b, 0xcd,
		0x01, 0xe7, 0x0a, 0x3e, 0x9d, 0x73, 0xac, 0x96,
	};

	union crypto_cfg cfg;

	if ((key->size) <= RAW_SECRET_SIZE) {
@@ -143,8 +137,9 @@ int crypto_qti_program_key(struct crypto_vops_qti_entry *ice_entry,
	cmd_kdf.kdf.kdk = GP_KEYSLOT;
	cmd_kdf.kdf.policy = policy_kdf;
	cmd_kdf.kdf.bsve = bsve_kdf;
	cmd_kdf.kdf.sz = 64;
	memcpy(cmd_kdf.kdf.ctx, ctx, HWKM_MAX_CTX_SIZE);
	cmd_kdf.kdf.sz = round_up(strlen(INLINECRYPT_CTX), BYTE_ORDER_VAL);
	memset(cmd_kdf.kdf.ctx, 0, HWKM_MAX_CTX_SIZE);
	memcpy(cmd_kdf.kdf.ctx, INLINECRYPT_CTX, strlen(INLINECRYPT_CTX));

	memset(&cfg, 0, sizeof(cfg));
	cfg.dusize = data_unit_mask;
+49 −9
Original line number Diff line number Diff line
@@ -49,6 +49,7 @@ for (retries = 0; !(cond) && (retries < MAX_RETRIES); retries++)
#define ICEMEM_SLAVE_TPKEY_VAL	0x192
#define ICEMEM_SLAVE_TPKEY_SLOT	0x92
#define KM_MASTER_TPKEY_SLOT	10
#define BYTE_ORDER_VAL		8

struct hwkm_clk_info {
	struct list_head list;
@@ -436,15 +437,38 @@ static void deserialize_policy(struct hwkm_key_policy *out,
	out->km_by_spu_allowed = policy->key_management_by_spu_allowed;
}

static void reverse_key(u8 *key, size_t keylen)

static void reverse_bytes(u8 *bytes, size_t len)
{
	size_t left = 0;
	size_t right = 0;

	for (left = 0, right = keylen - 1; left < right; left++, right--) {
		key[left] ^= key[right];
		key[right] ^= key[left];
		key[left] ^= key[right];
	for (left = 0, right = len - 1; left < right; left++, right--) {
		bytes[left] ^= bytes[right];
		bytes[right] ^= bytes[left];
		bytes[left] ^= bytes[right];
	}
}

static void reorder_ctx(u8 *ctx, size_t ctxlen)
{
	int i = 0;
	int len = 0;

	len = ctxlen / BYTE_ORDER_VAL;

	/* Reverse ctx at 8 byte boundary */
	for (i = 0; i < len; i++)
		reverse_bytes(ctx + i*BYTE_ORDER_VAL, BYTE_ORDER_VAL);

	/*
	 * If context is not a multiple of 8 bytes, reverse the last bytes
	 * only. This simulates prepending the last 8 bytes with zeroes,
	 * and then reversing the 8 bytes.
	 */
	if (ctxlen % BYTE_ORDER_VAL != 0) {
		reverse_bytes(ctx + len*BYTE_ORDER_VAL,
				ctxlen % BYTE_ORDER_VAL);
	}
}

@@ -590,6 +614,15 @@ static int qti_handle_system_kdf(const struct hwkm_cmd *cmd_in,

	serialize_policy(&policy, &cmd_in->kdf.policy);

	/*
	 * If context is not a multiple of 8 bytes, but a multiple
	 * of 4 bytes, add a zero word at the end, to have a context multiple
	 * of 8 bytes. This is to facilitate the context reordering that will
	 * happen later
	 */
	if ((cmd_in->kdf.sz) % BYTE_ORDER_VAL == (BYTE_ORDER_VAL/2))
		operation.context_len += 1;

	WRITE_TO_KDF_PACKET(cmd_ptr, &operation, OPERATION_INFO_LENGTH);
	WRITE_TO_KDF_PACKET(cmd_ptr, &policy, KEY_POLICY_LENGTH);

@@ -599,10 +632,16 @@ static int qti_handle_system_kdf(const struct hwkm_cmd *cmd_in,
		serialize_kdf_bsve(&bsve, &cmd_in->kdf.bsve, cmd_in->kdf.mks);
		WRITE_TO_KDF_PACKET(cmd_ptr, &bsve, MAX_BSVE_LENGTH);
	} else {
		// Skip the remaining 3 bytes of the current word
		cmd_ptr += 3 * (sizeof(u8));
		// Skip 4 bytes to align to start of context.
		cmd_ptr += 4 * (sizeof(u8));
	}

	/*
	 * Reorder context to reverse context bytes at the 8 byte
	 * boundary. This is because crypto lib reads at this
	 * boundary when populating the AD.
	 */
	reorder_ctx((u8 *) cmd_in->kdf.ctx, cmd_in->kdf.sz);
	WRITE_TO_KDF_PACKET(cmd_ptr, cmd_in->kdf.ctx, cmd_in->kdf.sz);

	status = qti_hwkm_run_transaction(ICEMEM_SLAVE, cmd,
@@ -724,7 +763,7 @@ static int qti_handle_keyslot_rdwr(const struct hwkm_cmd *cmd_in,
				cmd_in->rdwr.sz);
		// Need to reverse the key because the HW expects it in reverse
		// byte order
		reverse_key((u8 *) (cmd + COMMAND_KEY_VALUE_IDX),
		reverse_bytes((u8 *) (cmd + COMMAND_KEY_VALUE_IDX),
				HWKM_MAX_KEY_SIZE);
	}

@@ -750,7 +789,8 @@ static int qti_handle_keyslot_rdwr(const struct hwkm_cmd *cmd_in,
			rsp + RESPONSE_KEY_VALUE_IDX, RESPONSE_KEY_LENGTH);
		// Need to reverse the key because the HW returns it in
		// reverse byte order
		reverse_key(rsp_in->rdwr.key, HWKM_MAX_KEY_SIZE);
		reverse_bytes(rsp_in->rdwr.key, HWKM_MAX_KEY_SIZE);
		rsp_in->rdwr.sz = RESPONSE_KEY_LENGTH;
		deserialize_policy(&rsp_in->rdwr.policy, &policy);
	}