blob: da18c31d0f83e0f1d6c8e7ad5f98a27c740d4165 [file] [log] [blame]
Sheetal Tigadoliad0943e2019-12-18 19:44:43 +05301/*
2 * Copyright 2015 - 2020 Broadcom
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7#include <assert.h>
Manish Pandey9b384b32021-11-12 12:59:09 +00008#include <inttypes.h>
Sheetal Tigadoliad0943e2019-12-18 19:44:43 +05309#include <stdint.h>
10#include <string.h>
11
12#include <common/debug.h>
13#include <lib/mmio.h>
14#include <plat/common/platform.h>
15#include <tools_share/tbbr_oid.h>
16
17#include <sbl_util.h>
18#include <sotp.h>
19
20/* Weak definition may be overridden in specific platform */
21#pragma weak plat_match_rotpk
22#pragma weak plat_get_nv_ctr
23#pragma weak plat_set_nv_ctr
24
25/* SHA256 algorithm */
26#define SHA256_BYTES 32
27
28/* ROTPK locations */
29#define ARM_ROTPK_REGS_ID 1
30#define ARM_ROTPK_DEVEL_RSA_ID 2
31#define BRCM_ROTPK_SOTP_RSA_ID 3
32
33#if !ARM_ROTPK_LOCATION_ID
34 #error "ARM_ROTPK_LOCATION_ID not defined"
35#endif
36
37static const unsigned char rotpk_hash_hdr[] =
38 "\x30\x31\x30\x0D\x06\x09\x60\x86\x48"
39 "\x01\x65\x03\x04\x02\x01\x05\x00\x04\x20";
40static const unsigned int rotpk_hash_hdr_len = sizeof(rotpk_hash_hdr) - 1;
41static unsigned char rotpk_hash_der[sizeof(rotpk_hash_hdr) - 1 + SHA256_BYTES];
42
43#if (ARM_ROTPK_LOCATION_ID == ARM_ROTPK_DEVEL_RSA_ID)
44static const unsigned char arm_devel_rotpk_hash[] =
45 "\xB0\xF3\x82\x09\x12\x97\xD8\x3A"
46 "\x37\x7A\x72\x47\x1B\xEC\x32\x73"
47 "\xE9\x92\x32\xE2\x49\x59\xF6\x5E"
48 "\x8B\x4A\x4A\x46\xD8\x22\x9A\xDA";
49#endif
50
51#pragma weak plat_rotpk_hash
52const unsigned char plat_rotpk_hash[] =
53 "\xdb\x06\x67\x95\x4f\x88\x2b\x88"
54 "\x49\xbf\x70\x3f\xde\x50\x4a\x96"
55 "\xd8\x17\x69\xd4\xa0\x6c\xba\xee"
56 "\x66\x3e\x71\x82\x2d\x95\x69\xe4";
57
58#pragma weak rom_slice
59const unsigned char rom_slice[] =
60 "\x77\x06\xbc\x98\x40\xbe\xfd\xab"
61 "\x60\x4b\x74\x3c\x9a\xb3\x80\x75"
62 "\x39\xb6\xda\x27\x07\x2e\x5b\xbf"
63 "\x5c\x47\x91\xc9\x95\x26\x26\x0c";
64
65#if (ARM_ROTPK_LOCATION_ID == BRCM_ROTPK_SOTP_RSA_ID)
66static int plat_is_trusted_boot(void)
67{
68 uint64_t section3_row0_data;
69
70 section3_row0_data = sotp_mem_read(SOTP_DEVICE_SECURE_CFG0_ROW, 0);
71
72 if ((section3_row0_data & SOTP_DEVICE_SECURE_CFG0_AB_MASK) == 0) {
73 INFO("NOT AB\n");
74 return 0;
75 }
76
77 INFO("AB\n");
78 return TRUSTED_BOARD_BOOT;
79}
80
81/*
82 * FAST AUTH is enabled if all following conditions are met:
83 * - AB part
84 * - SOTP.DEV != 0
85 * - SOTP.CID != 0
86 * - SOTP.ENC_DEV_TYPE = ENC_AB_DEV
87 * - Manuf_debug strap set high
88 */
89static int plat_fast_auth_enabled(void)
90{
91 uint32_t chip_state;
92 uint64_t section3_row0_data;
93 uint64_t section3_row1_data;
94
95 section3_row0_data =
96 sotp_mem_read(SOTP_DEVICE_SECURE_CFG0_ROW, 0);
97 section3_row1_data =
98 sotp_mem_read(SOTP_DEVICE_SECURE_CFG1_ROW, 0);
99
100 chip_state = mmio_read_32(SOTP_REGS_SOTP_CHIP_STATES);
101
102 if (plat_is_trusted_boot() &&
103 (section3_row0_data & SOTP_DEVICE_SECURE_CFG0_DEV_MASK) &&
104 (section3_row0_data & SOTP_DEVICE_SECURE_CFG0_CID_MASK) &&
105 ((section3_row1_data & SOTP_ENC_DEV_TYPE_MASK) ==
106 SOTP_ENC_DEV_TYPE_AB_DEV) &&
107 (chip_state & SOTP_CHIP_STATES_MANU_DEBUG_MASK))
108 return 1;
109
110 return 0;
111}
112#endif
113
114/*
115 * Return the ROTPK hash in the following ASN.1 structure in DER format:
116 *
117 * AlgorithmIdentifier ::= SEQUENCE {
118 * algorithm OBJECT IDENTIFIER,
119 * parameters ANY DEFINED BY algorithm OPTIONAL
120 * }
121 *
122 * DigestInfo ::= SEQUENCE {
123 * digestAlgorithm AlgorithmIdentifier,
124 * digest OCTET STRING
125 * }
126 */
127int plat_get_rotpk_info(void *cookie, void **key_ptr, unsigned int *key_len,
128 unsigned int *flags)
129{
130 uint8_t *dst;
131
132 assert(key_ptr != NULL);
133 assert(key_len != NULL);
134 assert(flags != NULL);
135
136 *flags = 0;
137
138 /* Copy the DER header */
139 memcpy(rotpk_hash_der, rotpk_hash_hdr, rotpk_hash_hdr_len);
140 dst = (uint8_t *)&rotpk_hash_der[rotpk_hash_hdr_len];
141
142#if (ARM_ROTPK_LOCATION_ID == ARM_ROTPK_DEVEL_RSA_ID)
143 memcpy(dst, arm_devel_rotpk_hash, SHA256_BYTES);
144#elif (ARM_ROTPK_LOCATION_ID == ARM_ROTPK_REGS_ID)
145 uint32_t *src, tmp;
146 unsigned int words, i;
147
148 /*
149 * Append the hash from Trusted Root-Key Storage registers. The hash has
150 * not been written linearly into the registers, so we have to do a bit
151 * of byte swapping:
152 *
153 * 0x00 0x04 0x08 0x0C 0x10 0x14 0x18 0x1C
154 * +---------------------------------------------------------------+
155 * | Reg0 | Reg1 | Reg2 | Reg3 | Reg4 | Reg5 | Reg6 | Reg7 |
156 * +---------------------------------------------------------------+
157 * | ... ... | | ... ... |
158 * | +--------------------+ | +-------+
159 * | | | |
160 * +----------------------------+ +----------------------------+
161 * | | | |
162 * +-------+ | +--------------------+ |
163 * | | | |
164 * v v v v
165 * +---------------------------------------------------------------+
166 * | | |
167 * +---------------------------------------------------------------+
168 * 0 15 16 31
169 *
170 * Additionally, we have to access the registers in 32-bit words
171 */
172 words = SHA256_BYTES >> 3;
173
174 /* Swap bytes 0-15 (first four registers) */
175 src = (uint32_t *)TZ_PUB_KEY_HASH_BASE;
176 for (i = 0 ; i < words ; i++) {
177 tmp = src[words - 1 - i];
178 /* Words are read in little endian */
179 *dst++ = (uint8_t)((tmp >> 24) & 0xFF);
180 *dst++ = (uint8_t)((tmp >> 16) & 0xFF);
181 *dst++ = (uint8_t)((tmp >> 8) & 0xFF);
182 *dst++ = (uint8_t)(tmp & 0xFF);
183 }
184
185 /* Swap bytes 16-31 (last four registers) */
186 src = (uint32_t *)(TZ_PUB_KEY_HASH_BASE + SHA256_BYTES / 2);
187 for (i = 0 ; i < words ; i++) {
188 tmp = src[words - 1 - i];
189 *dst++ = (uint8_t)((tmp >> 24) & 0xFF);
190 *dst++ = (uint8_t)((tmp >> 16) & 0xFF);
191 *dst++ = (uint8_t)((tmp >> 8) & 0xFF);
192 *dst++ = (uint8_t)(tmp & 0xFF);
193 }
194#elif (ARM_ROTPK_LOCATION_ID == BRCM_ROTPK_SOTP_RSA_ID)
195{
196 int i;
197 int ret = -1;
198
199 /*
200 * In non-AB mode, we do not read the key.
201 * In AB mode:
202 * - The Dauth is in BL11 if SBL is enabled
203 * - The Dauth is in SOTP if SBL is disabled.
204 */
205 if (plat_is_trusted_boot() == 0) {
206
207 INFO("NON-AB: Do not read DAUTH!\n");
208 *flags = ROTPK_NOT_DEPLOYED;
209 ret = 0;
210
211 } else if ((sbl_status() == SBL_ENABLED) &&
212 (mmio_read_32(BL11_DAUTH_BASE) == BL11_DAUTH_ID)) {
213
214 /* Read hash from BL11 */
215 INFO("readKeys (DAUTH) from BL11\n");
216
217 memcpy(dst,
218 (void *)(BL11_DAUTH_BASE + sizeof(uint32_t)),
219 SHA256_BYTES);
220
221 for (i = 0; i < SHA256_BYTES; i++)
222 if (dst[i] != 0)
223 break;
224
225 if (i >= SHA256_BYTES)
226 ERROR("Hash not valid from BL11\n");
227 else
228 ret = 0;
229
230 } else if (sotp_key_erased()) {
231
232 memcpy(dst, plat_rotpk_hash, SHA256_BYTES);
233
234 INFO("SOTP erased, Use internal key hash.\n");
235 ret = 0;
236
237 } else if (plat_fast_auth_enabled()) {
238
239 INFO("AB DEV: FAST AUTH!\n");
240 *flags = ROTPK_NOT_DEPLOYED;
241 ret = 0;
242
243 } else if (!(mmio_read_32(SOTP_STATUS_1) & SOTP_DAUTH_ECC_ERROR_MASK)) {
244
245 /* Read hash from SOTP */
246 ret = sotp_read_key(dst,
247 SHA256_BYTES,
248 SOTP_DAUTH_ROW,
249 SOTP_K_HMAC_ROW-1);
250
251 INFO("sotp_read_key (DAUTH): %i\n", ret);
252
253 } else {
254
255 uint64_t row_data;
256 uint32_t k;
257
258 for (k = 0; k < (SOTP_K_HMAC_ROW - SOTP_DAUTH_ROW); k++) {
259 row_data = sotp_mem_read(SOTP_DAUTH_ROW + k,
260 SOTP_ROW_NO_ECC);
261
262 if (row_data != 0)
263 break;
264 }
265
266 if (k == (SOTP_K_HMAC_ROW - SOTP_DAUTH_ROW)) {
267 INFO("SOTP NOT PROGRAMMED: Do not use DAUTH!\n");
268
269 if (sotp_mem_read(SOTP_ATF2_CFG_ROW_ID,
270 SOTP_ROW_NO_ECC) & SOTP_ROMKEY_MASK) {
271 memcpy(dst, plat_rotpk_hash, SHA256_BYTES);
272
273 INFO("Use internal key hash.\n");
274 ret = 0;
275 } else {
276 *flags = ROTPK_NOT_DEPLOYED;
277 ret = 0;
278 }
279 } else {
280 INFO("No hash found in SOTP\n");
281 }
282 }
283 if (ret)
284 return ret;
285}
286#endif
287
288 *key_ptr = (void *)rotpk_hash_der;
289 *key_len = (unsigned int)sizeof(rotpk_hash_der);
290 *flags |= ROTPK_IS_HASH;
291
292 return 0;
293}
294
295#define SOTP_NUM_BITS_PER_ROW 41
296#define SOTP_NVCTR_ROW_ALL_ONES 0x1ffffffffff
297#define SOTP_NVCTR_TRUSTED_IN_USE \
298 ((uint64_t)0x3 << (SOTP_NUM_BITS_PER_ROW-2))
299#define SOTP_NVCTR_NON_TRUSTED_IN_USE ((uint64_t)0x3)
300#define SOTP_NVCTR_TRUSTED_NEAR_END SOTP_NVCTR_NON_TRUSTED_IN_USE
301#define SOTP_NVCTR_NON_TRUSTED_NEAR_END SOTP_NVCTR_TRUSTED_IN_USE
302
303#define SOTP_NVCTR_ROW_START 64
304#define SOTP_NVCTR_ROW_END 75
305
306/*
307 * SOTP NVCTR are stored in section 10 of SOTP (rows 64-75).
308 * Each row of SOTP is 41 bits.
309 * NVCTR's are stored in a bitstream format.
310 * We are tolerant to consecutive bit errors.
311 * Trusted NVCTR starts at the top of row 64 in bitstream format.
312 * Non Trusted NVCTR starts at the bottom of row 75 in reverse bitstream.
313 * Each row can only be used by 1 of the 2 counters. This is determined
314 * by 2 zeros remaining at the beginning or end of the last available row.
315 * If one counter has already starting using a row, the other will be
316 * prevent from writing to that row.
317 *
318 * Example counter values for SOTP programmed below:
319 * Trusted Counter (rows64-69) = 5 * 41 + 40 = 245
320 * NonTrusted Counter (row75-71) = 3 * 41 + 4 = 127
321 * 40 39 38 37 36 ..... 5 4 3 2 1 0
322 * row 64 1 1 1 1 1 1 1 1 1 1 1
323 * row 65 1 1 1 1 1 1 1 1 1 1 1
324 * row 66 1 1 1 1 1 1 1 1 1 1 1
325 * row 67 1 1 1 1 1 1 1 1 1 1 1
326 * row 68 1 1 1 1 1 1 1 1 1 1 1
327 * row 69 1 1 1 1 1 1 1 1 1 1 0
328 * row 71 0 0 0 0 0 0 0 0 0 0 0
329 * row 71 0 0 0 0 0 0 0 0 0 0 0
330 * row 71 0 0 0 0 0 0 0 1 1 1 1
331 * row 73 1 1 1 1 1 1 1 1 1 1 1
332 * row 74 1 1 1 1 1 1 1 1 1 1 1
333 * row 75 1 1 1 1 1 1 1 1 1 1 1
334 *
335 */
336
337#if (DEBUG == 1)
338/*
339 * Dump sotp rows
340 */
341void sotp_dump_rows(uint32_t start_row, uint32_t end_row)
342{
343 int32_t rownum;
344 uint64_t rowdata;
345
346 for (rownum = start_row; rownum <= end_row; rownum++) {
347 rowdata = sotp_mem_read(rownum, SOTP_ROW_NO_ECC);
Manish Pandey9b384b32021-11-12 12:59:09 +0000348 INFO("%d 0x%" PRIx64 "\n", rownum, rowdata);
Sheetal Tigadoliad0943e2019-12-18 19:44:43 +0530349 }
350}
351#endif
352
353/*
354 * Get SOTP Trusted nvctr
355 */
356unsigned int sotp_get_trusted_nvctr(void)
357{
358 uint64_t rowdata;
359 uint64_t nextrowdata;
360 uint32_t rownum;
361 unsigned int nvctr;
362
363 rownum = SOTP_NVCTR_ROW_START;
364 nvctr = SOTP_NUM_BITS_PER_ROW;
365
366 /*
367 * Determine what row has last valid data for trusted ctr
368 */
369 rowdata = sotp_mem_read(rownum, SOTP_ROW_NO_ECC);
370 while ((rowdata & SOTP_NVCTR_TRUSTED_IN_USE) &&
371 (rowdata & SOTP_NVCTR_TRUSTED_NEAR_END) &&
372 (rownum < SOTP_NVCTR_ROW_END)) {
373 /*
374 * Current row in use and has data in last 2 bits as well.
375 * Check if next row also has data for this counter
376 */
377 nextrowdata = sotp_mem_read(rownum+1, SOTP_ROW_NO_ECC);
378 if (nextrowdata & SOTP_NVCTR_TRUSTED_IN_USE) {
379 /* Next row also has data so increment rownum */
380 rownum++;
381 nvctr += SOTP_NUM_BITS_PER_ROW;
382 rowdata = nextrowdata;
383 } else {
384 /* Next row does not have data */
385 break;
386 }
387 }
388
389 if (rowdata & SOTP_NVCTR_TRUSTED_IN_USE) {
390 while ((rowdata & 0x1) == 0) {
391 nvctr--;
392 rowdata >>= 1;
393 }
394 } else
395 nvctr -= SOTP_NUM_BITS_PER_ROW;
396
397 INFO("CTR %i\n", nvctr);
398 return nvctr;
399}
400
401/*
402 * Get SOTP NonTrusted nvctr
403 */
404unsigned int sotp_get_nontrusted_nvctr(void)
405{
406 uint64_t rowdata;
407 uint64_t nextrowdata;
408 uint32_t rownum;
409 unsigned int nvctr;
410
411 nvctr = SOTP_NUM_BITS_PER_ROW;
412 rownum = SOTP_NVCTR_ROW_END;
413
414 /*
415 * Determine what row has last valid data for nontrusted ctr
416 */
417 rowdata = sotp_mem_read(rownum, SOTP_ROW_NO_ECC);
418 while ((rowdata & SOTP_NVCTR_NON_TRUSTED_NEAR_END) &&
419 (rowdata & SOTP_NVCTR_NON_TRUSTED_IN_USE) &&
420 (rownum > SOTP_NVCTR_ROW_START)) {
421 /*
422 * Current row in use and has data in last 2 bits as well.
423 * Check if next row also has data for this counter
424 */
425 nextrowdata = sotp_mem_read(rownum-1, SOTP_ROW_NO_ECC);
426 if (nextrowdata & SOTP_NVCTR_NON_TRUSTED_IN_USE) {
427 /* Next row also has data so decrement rownum */
428 rownum--;
429 nvctr += SOTP_NUM_BITS_PER_ROW;
430 rowdata = nextrowdata;
431 } else {
432 /* Next row does not have data */
433 break;
434 }
435 }
436
437 if (rowdata & SOTP_NVCTR_NON_TRUSTED_IN_USE) {
438 while ((rowdata & ((uint64_t)0x1 << (SOTP_NUM_BITS_PER_ROW-1)))
439 ==
440 0) {
441 nvctr--;
442 rowdata <<= 1;
443 }
444 } else
445 nvctr -= SOTP_NUM_BITS_PER_ROW;
446
447 INFO("NCTR %i\n", nvctr);
448 return nvctr;
449}
450
451/*
452 * Set SOTP Trusted nvctr
453 */
454int sotp_set_trusted_nvctr(unsigned int nvctr)
455{
456 int numrows_available;
457 uint32_t nontrusted_rownum;
458 uint32_t trusted_rownum;
459 uint64_t rowdata;
460 unsigned int maxnvctr;
461
462 /*
463 * Read SOTP to find out how many rows are used by the
464 * NON Trusted nvctr
465 */
466 nontrusted_rownum = SOTP_NVCTR_ROW_END;
467 do {
468 rowdata = sotp_mem_read(nontrusted_rownum, SOTP_ROW_NO_ECC);
469 if (rowdata & SOTP_NVCTR_NON_TRUSTED_IN_USE)
470 nontrusted_rownum--;
471 else
472 break;
473 } while (nontrusted_rownum >= SOTP_NVCTR_ROW_START);
474
475 /*
476 * Calculate maximum value we can have for nvctr based on
477 * number of available rows.
478 */
479 numrows_available = nontrusted_rownum - SOTP_NVCTR_ROW_START + 1;
480 maxnvctr = numrows_available * SOTP_NUM_BITS_PER_ROW;
481 if (maxnvctr) {
482 /*
483 * Last 2 bits of counter can't be written or it will
484 * overflow with nontrusted counter
485 */
486 maxnvctr -= 2;
487 }
488
489 if (nvctr > maxnvctr) {
490 /* Error - not enough room */
491 WARN("tctr not set\n");
492 return 1;
493 }
494
495 /*
496 * It is safe to write the nvctr, fill all 1's up to the
497 * last row and then fill the last row with partial bitstream
498 */
499 trusted_rownum = SOTP_NVCTR_ROW_START;
500 rowdata = SOTP_NVCTR_ROW_ALL_ONES;
501
502 while (nvctr >= SOTP_NUM_BITS_PER_ROW) {
503 sotp_mem_write(trusted_rownum, SOTP_ROW_NO_ECC, rowdata);
504 nvctr -= SOTP_NUM_BITS_PER_ROW;
505 trusted_rownum++;
506 }
507 rowdata <<= (SOTP_NUM_BITS_PER_ROW - nvctr);
508 sotp_mem_write(trusted_rownum, SOTP_ROW_NO_ECC, rowdata);
509 return 0;
510}
511
512/*
513 * Set SOTP NonTrusted nvctr
514 */
515int sotp_set_nontrusted_nvctr(unsigned int nvctr)
516{
517 int numrows_available;
518 uint32_t nontrusted_rownum;
519 uint32_t trusted_rownum;
520 uint64_t rowdata;
521 unsigned int maxnvctr;
522
523 /*
524 * Read SOTP to find out how many rows are used by the
525 * Trusted nvctr
526 */
527 trusted_rownum = SOTP_NVCTR_ROW_START;
528 do {
529 rowdata = sotp_mem_read(trusted_rownum, SOTP_ROW_NO_ECC);
530 if (rowdata & SOTP_NVCTR_TRUSTED_IN_USE)
531 trusted_rownum++;
532 else
533 break;
534 } while (trusted_rownum <= SOTP_NVCTR_ROW_END);
535
536 /*
537 * Calculate maximum value we can have for nvctr based on
538 * number of available rows.
539 */
540 numrows_available = SOTP_NVCTR_ROW_END - trusted_rownum + 1;
541 maxnvctr = numrows_available * SOTP_NUM_BITS_PER_ROW;
542 if (maxnvctr) {
543 /*
544 * Last 2 bits of counter can't be written or it will
545 * overflow with nontrusted counter
546 */
547 maxnvctr -= 2;
548 }
549
550 if (nvctr > maxnvctr) {
551 /* Error - not enough room */
552 WARN("nctr not set\n");
553 return 1;
554 }
555
556 /*
557 * It is safe to write the nvctr, fill all 1's up to the
558 * last row and then fill the last row with partial bitstream
559 */
560 nontrusted_rownum = SOTP_NVCTR_ROW_END;
561 rowdata = SOTP_NVCTR_ROW_ALL_ONES;
562
563 while (nvctr >= SOTP_NUM_BITS_PER_ROW) {
564 sotp_mem_write(nontrusted_rownum, SOTP_ROW_NO_ECC, rowdata);
565 nvctr -= SOTP_NUM_BITS_PER_ROW;
566 nontrusted_rownum--;
567 }
568 rowdata >>= (SOTP_NUM_BITS_PER_ROW - nvctr);
569 sotp_mem_write(nontrusted_rownum, SOTP_ROW_NO_ECC, rowdata);
570 return 0;
571}
572
573/*
574 * Return the non-volatile counter value stored in the platform. The cookie
575 * will contain the OID of the counter in the certificate.
576 *
577 * Return: 0 = success, Otherwise = error
578 */
579int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr)
580{
581 const char *oid;
582
583 assert(cookie != NULL);
584 assert(nv_ctr != NULL);
585
586 *nv_ctr = 0;
587 if ((sotp_mem_read(SOTP_ATF_CFG_ROW_ID, SOTP_ROW_NO_ECC) &
588 SOTP_ATF_NVCOUNTER_ENABLE_MASK)) {
589 oid = (const char *)cookie;
590 if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0)
591 *nv_ctr = sotp_get_trusted_nvctr();
592 else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0)
593 *nv_ctr = sotp_get_nontrusted_nvctr();
594 else
595 return 1;
596 }
597 return 0;
598}
599
600/*
601 * Store a new non-volatile counter value.
602 *
603 * Return: 0 = success, Otherwise = error
604 */
605int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
606{
607 const char *oid;
608
609 if (sotp_mem_read(SOTP_ATF_CFG_ROW_ID, SOTP_ROW_NO_ECC) &
610 SOTP_ATF_NVCOUNTER_ENABLE_MASK) {
611 INFO("set CTR %i\n", nv_ctr);
612 oid = (const char *)cookie;
613 if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0)
614 return sotp_set_trusted_nvctr(nv_ctr);
615 else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0)
616 return sotp_set_nontrusted_nvctr(nv_ctr);
617 return 1;
618 }
619 return 0;
620}
621
622int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
623{
624 return get_mbedtls_heap_helper(heap_addr, heap_size);
625}