1b1e0b11cSLionel Debieve /* 2*68039f2dSNicolas Toromanoff * Copyright (c) 2019-2022, STMicroelectronics - All Rights Reserved 3b1e0b11cSLionel Debieve * 4b1e0b11cSLionel Debieve * SPDX-License-Identifier: BSD-3-Clause 5b1e0b11cSLionel Debieve */ 6b1e0b11cSLionel Debieve 7b1e0b11cSLionel Debieve #include <assert.h> 8b1e0b11cSLionel Debieve #include <errno.h> 9b1e0b11cSLionel Debieve #include <stdint.h> 10b1e0b11cSLionel Debieve 11b1e0b11cSLionel Debieve #include <arch_helpers.h> 12b1e0b11cSLionel Debieve #include <common/debug.h> 1333667d29SYann Gautier #include <drivers/clk.h> 14b1e0b11cSLionel Debieve #include <drivers/delay_timer.h> 15b1e0b11cSLionel Debieve #include <drivers/st/stm32_hash.h> 16b1e0b11cSLionel Debieve #include <drivers/st/stm32mp_reset.h> 17b1e0b11cSLionel Debieve #include <lib/mmio.h> 18b1e0b11cSLionel Debieve #include <lib/utils.h> 19*68039f2dSNicolas Toromanoff #include <libfdt.h> 20b1e0b11cSLionel Debieve #include <plat/common/platform.h> 21b1e0b11cSLionel Debieve 22*68039f2dSNicolas Toromanoff #include <platform_def.h> 23*68039f2dSNicolas Toromanoff 24*68039f2dSNicolas Toromanoff #if STM32_HASH_VER == 2 25b1e0b11cSLionel Debieve #define DT_HASH_COMPAT "st,stm32f756-hash" 26*68039f2dSNicolas Toromanoff #endif 27*68039f2dSNicolas Toromanoff #if STM32_HASH_VER == 4 28*68039f2dSNicolas Toromanoff #define DT_HASH_COMPAT "st,stm32mp13-hash" 29*68039f2dSNicolas Toromanoff #endif 30b1e0b11cSLionel Debieve 31b1e0b11cSLionel Debieve #define HASH_CR 0x00U 32b1e0b11cSLionel Debieve #define HASH_DIN 0x04U 33b1e0b11cSLionel Debieve #define HASH_STR 0x08U 34b1e0b11cSLionel Debieve #define HASH_SR 0x24U 35b1e0b11cSLionel Debieve #define HASH_HREG(x) (0x310U + ((x) * 0x04U)) 36b1e0b11cSLionel Debieve 37b1e0b11cSLionel Debieve /* Control Register */ 38b1e0b11cSLionel Debieve #define HASH_CR_INIT BIT(2) 39b1e0b11cSLionel Debieve #define HASH_CR_DATATYPE_SHIFT U(4) 40*68039f2dSNicolas Toromanoff #if STM32_HASH_VER == 2 41b1e0b11cSLionel Debieve #define HASH_CR_ALGO_SHA1 0x0U 42b1e0b11cSLionel Debieve #define HASH_CR_ALGO_MD5 BIT(7) 43b1e0b11cSLionel Debieve #define HASH_CR_ALGO_SHA224 BIT(18) 44b1e0b11cSLionel Debieve #define HASH_CR_ALGO_SHA256 (BIT(18) | BIT(7)) 45*68039f2dSNicolas Toromanoff #endif 46*68039f2dSNicolas Toromanoff #if STM32_HASH_VER == 4 47*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHIFT U(17) 48*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA1 (0x0U << HASH_CR_ALGO_SHIFT) 49*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA224 (0x2U << HASH_CR_ALGO_SHIFT) 50*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA256 (0x3U << HASH_CR_ALGO_SHIFT) 51*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA384 (0xCU << HASH_CR_ALGO_SHIFT) 52*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA512_224 (0xDU << HASH_CR_ALGO_SHIFT) 53*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA512_256 (0xEU << HASH_CR_ALGO_SHIFT) 54*68039f2dSNicolas Toromanoff #define HASH_CR_ALGO_SHA512 (0xFU << HASH_CR_ALGO_SHIFT) 55*68039f2dSNicolas Toromanoff #endif 56b1e0b11cSLionel Debieve 57b1e0b11cSLionel Debieve /* Status Flags */ 58b1e0b11cSLionel Debieve #define HASH_SR_DCIS BIT(1) 59b1e0b11cSLionel Debieve #define HASH_SR_BUSY BIT(3) 60b1e0b11cSLionel Debieve 61b1e0b11cSLionel Debieve /* STR Register */ 62b1e0b11cSLionel Debieve #define HASH_STR_NBLW_MASK GENMASK(4, 0) 63b1e0b11cSLionel Debieve #define HASH_STR_DCAL BIT(8) 64b1e0b11cSLionel Debieve 65b1e0b11cSLionel Debieve #define MD5_DIGEST_SIZE 16U 66b1e0b11cSLionel Debieve #define SHA1_DIGEST_SIZE 20U 67b1e0b11cSLionel Debieve #define SHA224_DIGEST_SIZE 28U 68b1e0b11cSLionel Debieve #define SHA256_DIGEST_SIZE 32U 69*68039f2dSNicolas Toromanoff #define SHA384_DIGEST_SIZE 48U 70*68039f2dSNicolas Toromanoff #define SHA512_224_DIGEST_SIZE 28U 71*68039f2dSNicolas Toromanoff #define SHA512_256_DIGEST_SIZE 32U 72*68039f2dSNicolas Toromanoff #define SHA512_DIGEST_SIZE 64U 73b1e0b11cSLionel Debieve 7445c70e68SEtienne Carriere #define RESET_TIMEOUT_US_1MS 1000U 75b1e0b11cSLionel Debieve #define HASH_TIMEOUT_US 10000U 76b1e0b11cSLionel Debieve 77b1e0b11cSLionel Debieve enum stm32_hash_data_format { 78b1e0b11cSLionel Debieve HASH_DATA_32_BITS, 79b1e0b11cSLionel Debieve HASH_DATA_16_BITS, 80b1e0b11cSLionel Debieve HASH_DATA_8_BITS, 81b1e0b11cSLionel Debieve HASH_DATA_1_BIT 82b1e0b11cSLionel Debieve }; 83b1e0b11cSLionel Debieve 84b1e0b11cSLionel Debieve struct stm32_hash_instance { 85b1e0b11cSLionel Debieve uintptr_t base; 86b1e0b11cSLionel Debieve unsigned int clock; 87b1e0b11cSLionel Debieve size_t digest_size; 88b1e0b11cSLionel Debieve }; 89b1e0b11cSLionel Debieve 90b1e0b11cSLionel Debieve struct stm32_hash_remain { 91b1e0b11cSLionel Debieve uint32_t buffer; 92b1e0b11cSLionel Debieve size_t length; 93b1e0b11cSLionel Debieve }; 94b1e0b11cSLionel Debieve 95b1e0b11cSLionel Debieve /* Expect a single HASH peripheral */ 96b1e0b11cSLionel Debieve static struct stm32_hash_instance stm32_hash; 97b1e0b11cSLionel Debieve static struct stm32_hash_remain stm32_remain; 98b1e0b11cSLionel Debieve 99b1e0b11cSLionel Debieve static uintptr_t hash_base(void) 100b1e0b11cSLionel Debieve { 101b1e0b11cSLionel Debieve return stm32_hash.base; 102b1e0b11cSLionel Debieve } 103b1e0b11cSLionel Debieve 104b1e0b11cSLionel Debieve static int hash_wait_busy(void) 105b1e0b11cSLionel Debieve { 106b1e0b11cSLionel Debieve uint64_t timeout = timeout_init_us(HASH_TIMEOUT_US); 107b1e0b11cSLionel Debieve 108b1e0b11cSLionel Debieve while ((mmio_read_32(hash_base() + HASH_SR) & HASH_SR_BUSY) != 0U) { 109b1e0b11cSLionel Debieve if (timeout_elapsed(timeout)) { 110b1e0b11cSLionel Debieve ERROR("%s: busy timeout\n", __func__); 111b1e0b11cSLionel Debieve return -ETIMEDOUT; 112b1e0b11cSLionel Debieve } 113b1e0b11cSLionel Debieve } 114b1e0b11cSLionel Debieve 115b1e0b11cSLionel Debieve return 0; 116b1e0b11cSLionel Debieve } 117b1e0b11cSLionel Debieve 118b1e0b11cSLionel Debieve static int hash_wait_computation(void) 119b1e0b11cSLionel Debieve { 120b1e0b11cSLionel Debieve uint64_t timeout = timeout_init_us(HASH_TIMEOUT_US); 121b1e0b11cSLionel Debieve 122b1e0b11cSLionel Debieve while ((mmio_read_32(hash_base() + HASH_SR) & HASH_SR_DCIS) == 0U) { 123b1e0b11cSLionel Debieve if (timeout_elapsed(timeout)) { 124b1e0b11cSLionel Debieve ERROR("%s: busy timeout\n", __func__); 125b1e0b11cSLionel Debieve return -ETIMEDOUT; 126b1e0b11cSLionel Debieve } 127b1e0b11cSLionel Debieve } 128b1e0b11cSLionel Debieve 129b1e0b11cSLionel Debieve return 0; 130b1e0b11cSLionel Debieve } 131b1e0b11cSLionel Debieve 132b1e0b11cSLionel Debieve static int hash_write_data(uint32_t data) 133b1e0b11cSLionel Debieve { 134b1e0b11cSLionel Debieve int ret; 135b1e0b11cSLionel Debieve 136b1e0b11cSLionel Debieve ret = hash_wait_busy(); 137b1e0b11cSLionel Debieve if (ret != 0) { 138b1e0b11cSLionel Debieve return ret; 139b1e0b11cSLionel Debieve } 140b1e0b11cSLionel Debieve 141b1e0b11cSLionel Debieve mmio_write_32(hash_base() + HASH_DIN, data); 142b1e0b11cSLionel Debieve 143b1e0b11cSLionel Debieve return 0; 144b1e0b11cSLionel Debieve } 145b1e0b11cSLionel Debieve 146b1e0b11cSLionel Debieve static void hash_hw_init(enum stm32_hash_algo_mode mode) 147b1e0b11cSLionel Debieve { 148b1e0b11cSLionel Debieve uint32_t reg; 149b1e0b11cSLionel Debieve 150b1e0b11cSLionel Debieve reg = HASH_CR_INIT | (HASH_DATA_8_BITS << HASH_CR_DATATYPE_SHIFT); 151b1e0b11cSLionel Debieve 152b1e0b11cSLionel Debieve switch (mode) { 153*68039f2dSNicolas Toromanoff #if STM32_HASH_VER == 2 154b1e0b11cSLionel Debieve case HASH_MD5SUM: 155b1e0b11cSLionel Debieve reg |= HASH_CR_ALGO_MD5; 156b1e0b11cSLionel Debieve stm32_hash.digest_size = MD5_DIGEST_SIZE; 157b1e0b11cSLionel Debieve break; 158*68039f2dSNicolas Toromanoff #endif 159b1e0b11cSLionel Debieve case HASH_SHA1: 160b1e0b11cSLionel Debieve reg |= HASH_CR_ALGO_SHA1; 161b1e0b11cSLionel Debieve stm32_hash.digest_size = SHA1_DIGEST_SIZE; 162b1e0b11cSLionel Debieve break; 163b1e0b11cSLionel Debieve case HASH_SHA224: 164b1e0b11cSLionel Debieve reg |= HASH_CR_ALGO_SHA224; 165b1e0b11cSLionel Debieve stm32_hash.digest_size = SHA224_DIGEST_SIZE; 166b1e0b11cSLionel Debieve break; 167*68039f2dSNicolas Toromanoff #if STM32_HASH_VER == 4 168*68039f2dSNicolas Toromanoff case HASH_SHA384: 169*68039f2dSNicolas Toromanoff reg |= HASH_CR_ALGO_SHA384; 170*68039f2dSNicolas Toromanoff stm32_hash.digest_size = SHA384_DIGEST_SIZE; 171*68039f2dSNicolas Toromanoff break; 172*68039f2dSNicolas Toromanoff case HASH_SHA512: 173*68039f2dSNicolas Toromanoff reg |= HASH_CR_ALGO_SHA512; 174*68039f2dSNicolas Toromanoff stm32_hash.digest_size = SHA512_DIGEST_SIZE; 175*68039f2dSNicolas Toromanoff break; 176*68039f2dSNicolas Toromanoff #endif 177b1e0b11cSLionel Debieve /* Default selected algo is SHA256 */ 178b1e0b11cSLionel Debieve case HASH_SHA256: 179b1e0b11cSLionel Debieve default: 180b1e0b11cSLionel Debieve reg |= HASH_CR_ALGO_SHA256; 181b1e0b11cSLionel Debieve stm32_hash.digest_size = SHA256_DIGEST_SIZE; 182b1e0b11cSLionel Debieve break; 183b1e0b11cSLionel Debieve } 184b1e0b11cSLionel Debieve 185b1e0b11cSLionel Debieve mmio_write_32(hash_base() + HASH_CR, reg); 186b1e0b11cSLionel Debieve } 187b1e0b11cSLionel Debieve 188b1e0b11cSLionel Debieve static int hash_get_digest(uint8_t *digest) 189b1e0b11cSLionel Debieve { 190b1e0b11cSLionel Debieve int ret; 191b1e0b11cSLionel Debieve uint32_t i; 192b1e0b11cSLionel Debieve uint32_t dsg; 193b1e0b11cSLionel Debieve 194b1e0b11cSLionel Debieve ret = hash_wait_computation(); 195b1e0b11cSLionel Debieve if (ret != 0) { 196b1e0b11cSLionel Debieve return ret; 197b1e0b11cSLionel Debieve } 198b1e0b11cSLionel Debieve 199b1e0b11cSLionel Debieve for (i = 0U; i < (stm32_hash.digest_size / sizeof(uint32_t)); i++) { 200b1e0b11cSLionel Debieve dsg = __builtin_bswap32(mmio_read_32(hash_base() + 201b1e0b11cSLionel Debieve HASH_HREG(i))); 202b1e0b11cSLionel Debieve memcpy(digest + (i * sizeof(uint32_t)), &dsg, sizeof(uint32_t)); 203b1e0b11cSLionel Debieve } 204b1e0b11cSLionel Debieve 205b1e0b11cSLionel Debieve #if defined(IMAGE_BL2) 206b1e0b11cSLionel Debieve /* 207b1e0b11cSLionel Debieve * Clean hardware context as HASH could be used later 208b1e0b11cSLionel Debieve * by non-secure software 209b1e0b11cSLionel Debieve */ 210b1e0b11cSLionel Debieve hash_hw_init(HASH_SHA256); 211b1e0b11cSLionel Debieve #endif 212b1e0b11cSLionel Debieve return 0; 213b1e0b11cSLionel Debieve } 214b1e0b11cSLionel Debieve 215b1e0b11cSLionel Debieve int stm32_hash_update(const uint8_t *buffer, size_t length) 216b1e0b11cSLionel Debieve { 217b1e0b11cSLionel Debieve size_t remain_length = length; 218b1e0b11cSLionel Debieve int ret = 0; 219b1e0b11cSLionel Debieve 220b1e0b11cSLionel Debieve if ((length == 0U) || (buffer == NULL)) { 221b1e0b11cSLionel Debieve return 0; 222b1e0b11cSLionel Debieve } 223b1e0b11cSLionel Debieve 22433667d29SYann Gautier clk_enable(stm32_hash.clock); 225b1e0b11cSLionel Debieve 226b1e0b11cSLionel Debieve if (stm32_remain.length != 0U) { 227b1e0b11cSLionel Debieve uint32_t copysize; 228b1e0b11cSLionel Debieve 229b1e0b11cSLionel Debieve copysize = MIN((sizeof(uint32_t) - stm32_remain.length), 230b1e0b11cSLionel Debieve length); 231b1e0b11cSLionel Debieve memcpy(((uint8_t *)&stm32_remain.buffer) + stm32_remain.length, 232b1e0b11cSLionel Debieve buffer, copysize); 233b1e0b11cSLionel Debieve remain_length -= copysize; 234b1e0b11cSLionel Debieve buffer += copysize; 235b1e0b11cSLionel Debieve if (stm32_remain.length == sizeof(uint32_t)) { 236b1e0b11cSLionel Debieve ret = hash_write_data(stm32_remain.buffer); 237b1e0b11cSLionel Debieve if (ret != 0) { 238b1e0b11cSLionel Debieve goto exit; 239b1e0b11cSLionel Debieve } 240b1e0b11cSLionel Debieve 241b1e0b11cSLionel Debieve zeromem(&stm32_remain, sizeof(stm32_remain)); 242b1e0b11cSLionel Debieve } 243b1e0b11cSLionel Debieve } 244b1e0b11cSLionel Debieve 245b1e0b11cSLionel Debieve while (remain_length / sizeof(uint32_t) != 0U) { 246b1e0b11cSLionel Debieve uint32_t tmp_buf; 247b1e0b11cSLionel Debieve 248b1e0b11cSLionel Debieve memcpy(&tmp_buf, buffer, sizeof(uint32_t)); 249b1e0b11cSLionel Debieve ret = hash_write_data(tmp_buf); 250b1e0b11cSLionel Debieve if (ret != 0) { 251b1e0b11cSLionel Debieve goto exit; 252b1e0b11cSLionel Debieve } 253b1e0b11cSLionel Debieve 254b1e0b11cSLionel Debieve buffer += sizeof(uint32_t); 255b1e0b11cSLionel Debieve remain_length -= sizeof(uint32_t); 256b1e0b11cSLionel Debieve } 257b1e0b11cSLionel Debieve 258b1e0b11cSLionel Debieve if (remain_length != 0U) { 259b1e0b11cSLionel Debieve assert(stm32_remain.length == 0U); 260b1e0b11cSLionel Debieve 261b1e0b11cSLionel Debieve memcpy((uint8_t *)&stm32_remain.buffer, buffer, remain_length); 262b1e0b11cSLionel Debieve stm32_remain.length = remain_length; 263b1e0b11cSLionel Debieve } 264b1e0b11cSLionel Debieve 265b1e0b11cSLionel Debieve exit: 26633667d29SYann Gautier clk_disable(stm32_hash.clock); 267b1e0b11cSLionel Debieve 268b1e0b11cSLionel Debieve return ret; 269b1e0b11cSLionel Debieve } 270b1e0b11cSLionel Debieve 271b1e0b11cSLionel Debieve int stm32_hash_final(uint8_t *digest) 272b1e0b11cSLionel Debieve { 273b1e0b11cSLionel Debieve int ret; 274b1e0b11cSLionel Debieve 27533667d29SYann Gautier clk_enable(stm32_hash.clock); 276b1e0b11cSLionel Debieve 277b1e0b11cSLionel Debieve if (stm32_remain.length != 0U) { 278b1e0b11cSLionel Debieve ret = hash_write_data(stm32_remain.buffer); 279b1e0b11cSLionel Debieve if (ret != 0) { 28033667d29SYann Gautier clk_disable(stm32_hash.clock); 281b1e0b11cSLionel Debieve return ret; 282b1e0b11cSLionel Debieve } 283b1e0b11cSLionel Debieve 284b1e0b11cSLionel Debieve mmio_clrsetbits_32(hash_base() + HASH_STR, HASH_STR_NBLW_MASK, 285b1e0b11cSLionel Debieve 8U * stm32_remain.length); 286b1e0b11cSLionel Debieve zeromem(&stm32_remain, sizeof(stm32_remain)); 287662c1f5cSLionel Debieve } else { 288662c1f5cSLionel Debieve mmio_clrbits_32(hash_base() + HASH_STR, HASH_STR_NBLW_MASK); 289b1e0b11cSLionel Debieve } 290b1e0b11cSLionel Debieve 291b1e0b11cSLionel Debieve mmio_setbits_32(hash_base() + HASH_STR, HASH_STR_DCAL); 292b1e0b11cSLionel Debieve 293b1e0b11cSLionel Debieve ret = hash_get_digest(digest); 294b1e0b11cSLionel Debieve 29533667d29SYann Gautier clk_disable(stm32_hash.clock); 296b1e0b11cSLionel Debieve 297b1e0b11cSLionel Debieve return ret; 298b1e0b11cSLionel Debieve } 299b1e0b11cSLionel Debieve 300b1e0b11cSLionel Debieve int stm32_hash_final_update(const uint8_t *buffer, uint32_t length, 301b1e0b11cSLionel Debieve uint8_t *digest) 302b1e0b11cSLionel Debieve { 303b1e0b11cSLionel Debieve int ret; 304b1e0b11cSLionel Debieve 305b1e0b11cSLionel Debieve ret = stm32_hash_update(buffer, length); 306b1e0b11cSLionel Debieve if (ret != 0) { 307b1e0b11cSLionel Debieve return ret; 308b1e0b11cSLionel Debieve } 309b1e0b11cSLionel Debieve 310b1e0b11cSLionel Debieve return stm32_hash_final(digest); 311b1e0b11cSLionel Debieve } 312b1e0b11cSLionel Debieve 313b1e0b11cSLionel Debieve void stm32_hash_init(enum stm32_hash_algo_mode mode) 314b1e0b11cSLionel Debieve { 31533667d29SYann Gautier clk_enable(stm32_hash.clock); 316b1e0b11cSLionel Debieve 317b1e0b11cSLionel Debieve hash_hw_init(mode); 318b1e0b11cSLionel Debieve 31933667d29SYann Gautier clk_disable(stm32_hash.clock); 320b1e0b11cSLionel Debieve 321b1e0b11cSLionel Debieve zeromem(&stm32_remain, sizeof(stm32_remain)); 322b1e0b11cSLionel Debieve } 323b1e0b11cSLionel Debieve 324b1e0b11cSLionel Debieve int stm32_hash_register(void) 325b1e0b11cSLionel Debieve { 326b1e0b11cSLionel Debieve struct dt_node_info hash_info; 327b1e0b11cSLionel Debieve int node; 328b1e0b11cSLionel Debieve 329b1e0b11cSLionel Debieve for (node = dt_get_node(&hash_info, -1, DT_HASH_COMPAT); 330b1e0b11cSLionel Debieve node != -FDT_ERR_NOTFOUND; 331b1e0b11cSLionel Debieve node = dt_get_node(&hash_info, node, DT_HASH_COMPAT)) { 332b1e0b11cSLionel Debieve #if defined(IMAGE_BL2) 333b1e0b11cSLionel Debieve if (hash_info.status != DT_DISABLED) { 334b1e0b11cSLionel Debieve break; 335b1e0b11cSLionel Debieve } 336b1e0b11cSLionel Debieve #else 3373d0d0a1bSEtienne Carriere /* BL32 uses hash if it is assigned only to secure world */ 338b1e0b11cSLionel Debieve if (hash_info.status == DT_SECURE) { 3393d0d0a1bSEtienne Carriere stm32mp_register_secure_periph_iomem(hash_info.base); 340b1e0b11cSLionel Debieve break; 341b1e0b11cSLionel Debieve } 342b1e0b11cSLionel Debieve #endif 343b1e0b11cSLionel Debieve } 344b1e0b11cSLionel Debieve 345b1e0b11cSLionel Debieve if (node == -FDT_ERR_NOTFOUND) { 346b1e0b11cSLionel Debieve return -ENODEV; 347b1e0b11cSLionel Debieve } 348b1e0b11cSLionel Debieve 349b1e0b11cSLionel Debieve if (hash_info.clock < 0) { 350b1e0b11cSLionel Debieve return -EINVAL; 351b1e0b11cSLionel Debieve } 352b1e0b11cSLionel Debieve 353b1e0b11cSLionel Debieve stm32_hash.base = hash_info.base; 354b1e0b11cSLionel Debieve stm32_hash.clock = hash_info.clock; 355b1e0b11cSLionel Debieve 35633667d29SYann Gautier clk_enable(stm32_hash.clock); 357b1e0b11cSLionel Debieve 358b1e0b11cSLionel Debieve if (hash_info.reset >= 0) { 35945c70e68SEtienne Carriere uint32_t id = (uint32_t)hash_info.reset; 36045c70e68SEtienne Carriere 36145c70e68SEtienne Carriere if (stm32mp_reset_assert(id, RESET_TIMEOUT_US_1MS) != 0) { 36245c70e68SEtienne Carriere panic(); 36345c70e68SEtienne Carriere } 364b1e0b11cSLionel Debieve udelay(20); 36545c70e68SEtienne Carriere if (stm32mp_reset_deassert(id, RESET_TIMEOUT_US_1MS) != 0) { 36645c70e68SEtienne Carriere panic(); 36745c70e68SEtienne Carriere } 368b1e0b11cSLionel Debieve } 369b1e0b11cSLionel Debieve 37033667d29SYann Gautier clk_disable(stm32_hash.clock); 371b1e0b11cSLionel Debieve 372b1e0b11cSLionel Debieve return 0; 373b1e0b11cSLionel Debieve } 374