blob: 450a8a05ac905f90cea0d047e3124148015ea830 [file] [log] [blame]
Angel Ponsbbc99cf2020-04-04 18:51:23 +02001/* SPDX-License-Identifier: GPL-2.0-only */
Julius Werner33df4952014-12-16 22:48:26 -08002
Kyösti Mälkki13f66502019-03-03 08:01:05 +02003#include <device/mmio.h>
Julius Werner33df4952014-12-16 22:48:26 -08004#include <assert.h>
Elyes HAOUAS20eaef02019-03-29 17:45:28 +01005#include <console/console.h>
Julius Werner33df4952014-12-16 22:48:26 -08006#include <delay.h>
7#include <soc/addressmap.h>
8#include <soc/soc.h>
9#include <types.h>
10#include <vb2_api.h>
11
12enum rk3288_crypto_interrupt_bits {
13 PKA_DONE = 1 << 5,
14 HASH_DONE = 1 << 4,
15 HRDMA_ERR = 1 << 3,
16 HRDMA_DONE = 1 << 2,
17 BCDMA_ERR = 1 << 1,
18 BCDMA_DONE = 1 << 0,
19};
20
21struct rk3288_crypto {
22 u32 intsts;
23 u32 intena;
24 u32 ctrl;
25 u32 conf;
26 u32 brdmas;
27 u32 btdmas;
28 u32 btdmal;
29 u32 hrdmas;
30 u32 hrdmal;
31 u8 _res0[0x80 - 0x24];
32 u32 aes_ctrl;
33 u32 aes_sts;
34 u32 aes_din[4];
35 u32 aes_dout[4];
36 u32 aes_iv[4];
37 u32 aes_key[8];
38 u32 aes_cnt[4];
39 u8 _res1[0x100 - 0xe8];
40 u32 tdes_ctrl;
41 u32 tdes_sts;
42 u32 tdes_din[2];
43 u32 tdes_dout[2];
44 u32 tdes_iv[2];
45 u32 tdes_key[3][2];
46 u8 _res2[0x180 - 0x138];
47 u32 hash_ctrl;
48 u32 hash_sts;
49 u32 hash_msg_len;
50 u32 hash_dout[8];
51 u32 hash_seed[5];
52 u8 _res3[0x200 - 0x1c0];
53 u32 trng_ctrl;
54 u32 trng_dout[8];
55} *crypto = (void *)CRYPTO_BASE;
56check_member(rk3288_crypto, trng_dout[7], 0x220);
57
Joel Kitching220ac042019-07-31 14:19:00 +080058vb2_error_t vb2ex_hwcrypto_digest_init(enum vb2_hash_algorithm hash_alg,
59 uint32_t data_size)
Julius Werner33df4952014-12-16 22:48:26 -080060{
Julius Werner99a99282022-08-09 18:46:50 -070061 if (hash_alg != VB2_HASH_SHA256 || !data_size)
Julius Werner33df4952014-12-16 22:48:26 -080062 return VB2_ERROR_EX_HWCRYPTO_UNSUPPORTED;
Julius Werner33df4952014-12-16 22:48:26 -080063
Julius Werner2f37bd62015-02-19 14:51:15 -080064 write32(&crypto->ctrl, RK_SETBITS(1 << 6)); /* Assert HASH_FLUSH */
Julius Werner33df4952014-12-16 22:48:26 -080065 udelay(1); /* for 10+ cycles to */
Julius Werner2f37bd62015-02-19 14:51:15 -080066 write32(&crypto->ctrl, RK_CLRBITS(1 << 6)); /* clear out old hash */
Julius Werner33df4952014-12-16 22:48:26 -080067
68 /* Enable DMA byte swapping for little-endian bus (Byteswap_??FIFO) */
Julius Werner2f37bd62015-02-19 14:51:15 -080069 write32(&crypto->conf, 1 << 5 | 1 << 4 | 1 << 3);
Julius Werner33df4952014-12-16 22:48:26 -080070
Julius Werner2f37bd62015-02-19 14:51:15 -080071 write32(&crypto->intena, HRDMA_ERR | HRDMA_DONE); /* enable interrupt */
Julius Werner33df4952014-12-16 22:48:26 -080072
Julius Werner2f37bd62015-02-19 14:51:15 -080073 write32(&crypto->hash_msg_len, data_size); /* program total size */
74 write32(&crypto->hash_ctrl, 1 << 3 | 0x2); /* swap DOUT, SHA256 */
Julius Werner33df4952014-12-16 22:48:26 -080075
76 printk(BIOS_DEBUG, "Initialized RK3288 HW crypto for %u byte SHA256\n",
77 data_size);
78 return VB2_SUCCESS;
79}
80
Joel Kitching220ac042019-07-31 14:19:00 +080081vb2_error_t vb2ex_hwcrypto_digest_extend(const uint8_t *buf, uint32_t size)
Julius Werner33df4952014-12-16 22:48:26 -080082{
83 uint32_t intsts;
84
Julius Werner2f37bd62015-02-19 14:51:15 -080085 write32(&crypto->intsts, HRDMA_ERR | HRDMA_DONE); /* clear interrupts */
Julius Werner33df4952014-12-16 22:48:26 -080086
87 /* NOTE: This assumes that the DMA is reading from uncached SRAM. */
Julius Werner2f37bd62015-02-19 14:51:15 -080088 write32(&crypto->hrdmas, (uint32_t)buf);
89 write32(&crypto->hrdmal, size / sizeof(uint32_t));
90 write32(&crypto->ctrl, RK_SETBITS(1 << 3)); /* Set HASH_START */
Julius Werner33df4952014-12-16 22:48:26 -080091 do {
92 intsts = read32(&crypto->intsts);
93 if (intsts & HRDMA_ERR) {
Julius Wernere9665952022-01-21 17:06:20 -080094 printk(BIOS_ERR, "DMA error during HW crypto\n");
Julius Werner33df4952014-12-16 22:48:26 -080095 return VB2_ERROR_UNKNOWN;
96 }
97 } while (!(intsts & HRDMA_DONE)); /* wait for DMA to finish */
98
99 return VB2_SUCCESS;
100}
101
Joel Kitching220ac042019-07-31 14:19:00 +0800102vb2_error_t vb2ex_hwcrypto_digest_finalize(uint8_t *digest,
103 uint32_t digest_size)
Julius Werner33df4952014-12-16 22:48:26 -0800104{
105 uint32_t *dest = (uint32_t *)digest;
106 uint32_t *src = crypto->hash_dout;
107 assert(digest_size == sizeof(crypto->hash_dout));
108
109 while (!(read32(&crypto->hash_sts) & 0x1))
110 /* wait for crypto engine to set HASH_DONE bit */;
111
112 while ((uint8_t *)dest < digest + digest_size)
113 *dest++ = read32(src++);
114
115 return VB2_SUCCESS;
116}