xref: /optee_os/core/crypto/signed_hdr.c (revision 064663e8bd2781d693bc04b6118efa3bbf5ee9c2)
1*064663e8SJens Wiklander /*
2*064663e8SJens Wiklander  * Copyright (c) 2015-2017, Linaro Limited
3*064663e8SJens Wiklander  *
4*064663e8SJens Wiklander  * SPDX-License-Identifier: BSD-2-Clause
5*064663e8SJens Wiklander  */
6*064663e8SJens Wiklander 
7*064663e8SJens Wiklander #include <crypto/crypto.h>
8*064663e8SJens Wiklander #include <signed_hdr.h>
9*064663e8SJens Wiklander #include <stdlib.h>
10*064663e8SJens Wiklander #include <string.h>
11*064663e8SJens Wiklander #include <ta_pub_key.h>
12*064663e8SJens Wiklander #include <tee_api_types.h>
13*064663e8SJens Wiklander #include <tee/tee_cryp_utl.h>
14*064663e8SJens Wiklander #include <utee_defines.h>
15*064663e8SJens Wiklander 
16*064663e8SJens Wiklander struct shdr *shdr_alloc_and_copy(const struct shdr *img, size_t img_size)
17*064663e8SJens Wiklander {
18*064663e8SJens Wiklander 	size_t shdr_size;
19*064663e8SJens Wiklander 	struct shdr *shdr;
20*064663e8SJens Wiklander 
21*064663e8SJens Wiklander 	if (img_size < sizeof(struct shdr))
22*064663e8SJens Wiklander 		NULL;
23*064663e8SJens Wiklander 	shdr_size = SHDR_GET_SIZE(img);
24*064663e8SJens Wiklander 	if (img_size < shdr_size)
25*064663e8SJens Wiklander 		NULL;
26*064663e8SJens Wiklander 
27*064663e8SJens Wiklander 	shdr = malloc(shdr_size);
28*064663e8SJens Wiklander 	if (!shdr)
29*064663e8SJens Wiklander 		return NULL;
30*064663e8SJens Wiklander 	memcpy(shdr, img, shdr_size);
31*064663e8SJens Wiklander 
32*064663e8SJens Wiklander 	/* Check that the data wasn't modified before the copy was completed */
33*064663e8SJens Wiklander 	if (shdr_size != SHDR_GET_SIZE(shdr)) {
34*064663e8SJens Wiklander 		free(shdr);
35*064663e8SJens Wiklander 		return NULL;
36*064663e8SJens Wiklander 	}
37*064663e8SJens Wiklander 
38*064663e8SJens Wiklander 	return shdr;
39*064663e8SJens Wiklander }
40*064663e8SJens Wiklander 
41*064663e8SJens Wiklander TEE_Result shdr_verify_signature(const struct shdr *shdr)
42*064663e8SJens Wiklander {
43*064663e8SJens Wiklander 	struct rsa_public_key key;
44*064663e8SJens Wiklander 	TEE_Result res;
45*064663e8SJens Wiklander 	uint32_t e = TEE_U32_TO_BIG_ENDIAN(ta_pub_key_exponent);
46*064663e8SJens Wiklander 	size_t hash_size;
47*064663e8SJens Wiklander 
48*064663e8SJens Wiklander 	if (shdr->magic != SHDR_MAGIC)
49*064663e8SJens Wiklander 		return TEE_ERROR_SECURITY;
50*064663e8SJens Wiklander 
51*064663e8SJens Wiklander 	if (TEE_ALG_GET_MAIN_ALG(shdr->algo) != TEE_MAIN_ALGO_RSA)
52*064663e8SJens Wiklander 		return TEE_ERROR_SECURITY;
53*064663e8SJens Wiklander 
54*064663e8SJens Wiklander 	res = tee_hash_get_digest_size(TEE_DIGEST_HASH_TO_ALGO(shdr->algo),
55*064663e8SJens Wiklander 				       &hash_size);
56*064663e8SJens Wiklander 	if (res)
57*064663e8SJens Wiklander 		return TEE_ERROR_SECURITY;
58*064663e8SJens Wiklander 	if (hash_size != shdr->hash_size)
59*064663e8SJens Wiklander 		return TEE_ERROR_SECURITY;
60*064663e8SJens Wiklander 
61*064663e8SJens Wiklander 	res = crypto_acipher_alloc_rsa_public_key(&key, shdr->sig_size);
62*064663e8SJens Wiklander 	if (res)
63*064663e8SJens Wiklander 		return TEE_ERROR_SECURITY;
64*064663e8SJens Wiklander 
65*064663e8SJens Wiklander 	res = crypto_bignum_bin2bn((uint8_t *)&e, sizeof(e), key.e);
66*064663e8SJens Wiklander 	if (res)
67*064663e8SJens Wiklander 		goto out;
68*064663e8SJens Wiklander 	res = crypto_bignum_bin2bn(ta_pub_key_modulus, ta_pub_key_modulus_size,
69*064663e8SJens Wiklander 				   key.n);
70*064663e8SJens Wiklander 	if (res)
71*064663e8SJens Wiklander 		goto out;
72*064663e8SJens Wiklander 
73*064663e8SJens Wiklander 	res = crypto_acipher_rsassa_verify(shdr->algo, &key, -1,
74*064663e8SJens Wiklander 					   SHDR_GET_HASH(shdr), shdr->hash_size,
75*064663e8SJens Wiklander 					   SHDR_GET_SIG(shdr), shdr->sig_size);
76*064663e8SJens Wiklander out:
77*064663e8SJens Wiklander 	crypto_acipher_free_rsa_public_key(&key);
78*064663e8SJens Wiklander 	if (res)
79*064663e8SJens Wiklander 		return TEE_ERROR_SECURITY;
80*064663e8SJens Wiklander 	return TEE_SUCCESS;
81*064663e8SJens Wiklander }
82