12 #include "otp_ctrl_regs.h"
23 static bool checks_are_locked(
const dif_otp_ctrl_t *otp,
bool check_config) {
24 ptrdiff_t reg_offset = check_config
25 ? OTP_CTRL_CHECK_REGWEN_REG_OFFSET
26 : OTP_CTRL_CHECK_TRIGGER_REGWEN_REG_OFFSET;
28 check_config ? OTP_CTRL_CHECK_REGWEN_CHECK_REGWEN_BIT
29 : OTP_CTRL_CHECK_TRIGGER_REGWEN_CHECK_TRIGGER_REGWEN_BIT;
30 uint32_t locked = mmio_region_read32(otp->base_addr, reg_offset);
39 if (checks_are_locked(otp,
true)) {
43 mmio_region_write32(otp->base_addr, OTP_CTRL_CHECK_TIMEOUT_REG_OFFSET,
45 mmio_region_write32(otp->base_addr,
46 OTP_CTRL_INTEGRITY_CHECK_PERIOD_REG_OFFSET,
48 mmio_region_write32(otp->base_addr,
49 OTP_CTRL_CONSISTENCY_CHECK_PERIOD_REG_OFFSET,
59 if (checks_are_locked(otp,
false)) {
65 mmio_region_write32(otp->base_addr, OTP_CTRL_CHECK_TRIGGER_REG_OFFSET, reg);
74 if (checks_are_locked(otp,
false)) {
80 mmio_region_write32(otp->base_addr, OTP_CTRL_CHECK_TRIGGER_REG_OFFSET, reg);
91 0, OTP_CTRL_DIRECT_ACCESS_REGWEN_DIRECT_ACCESS_REGWEN_BIT,
false);
92 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_REGWEN_REG_OFFSET,
100 if (otp == NULL || is_locked == NULL) {
104 uint32_t reg = mmio_region_read32(otp->base_addr,
105 OTP_CTRL_DIRECT_ACCESS_REGWEN_REG_OFFSET);
107 reg, OTP_CTRL_DIRECT_ACCESS_REGWEN_DIRECT_ACCESS_REGWEN_BIT);
119 mmio_region_write32(otp->base_addr, OTP_CTRL_CHECK_REGWEN_REG_OFFSET, reg);
126 if (otp == NULL || is_locked == NULL) {
130 *is_locked = checks_are_locked(otp,
true);
140 0, OTP_CTRL_CHECK_TRIGGER_REGWEN_CHECK_TRIGGER_REGWEN_BIT,
false);
141 mmio_region_write32(otp->base_addr, OTP_CTRL_CHECK_TRIGGER_REGWEN_REG_OFFSET,
149 if (otp == NULL || is_locked == NULL) {
153 *is_locked = checks_are_locked(otp,
false);
158 ptrdiff_t *reg_offset,
162 *reg_offset = OTP_CTRL_VENDOR_TEST_READ_LOCK_REG_OFFSET;
163 *index = OTP_CTRL_VENDOR_TEST_READ_LOCK_VENDOR_TEST_READ_LOCK_BIT;
166 *reg_offset = OTP_CTRL_CREATOR_SW_CFG_READ_LOCK_REG_OFFSET;
167 *index = OTP_CTRL_CREATOR_SW_CFG_READ_LOCK_CREATOR_SW_CFG_READ_LOCK_BIT;
170 *reg_offset = OTP_CTRL_OWNER_SW_CFG_READ_LOCK_REG_OFFSET;
171 *index = OTP_CTRL_OWNER_SW_CFG_READ_LOCK_OWNER_SW_CFG_READ_LOCK_BIT;
173 #if defined(OPENTITAN_IS_EARLGREY)
174 case kDifOtpCtrlPartitionRotCreatorAuthCodesign:
175 *reg_offset = OTP_CTRL_ROT_CREATOR_AUTH_CODESIGN_READ_LOCK_REG_OFFSET;
177 OTP_CTRL_ROT_CREATOR_AUTH_CODESIGN_READ_LOCK_ROT_CREATOR_AUTH_CODESIGN_READ_LOCK_BIT;
179 case kDifOtpCtrlPartitionRotCreatorAuthState:
180 *reg_offset = OTP_CTRL_ROT_CREATOR_AUTH_STATE_READ_LOCK_REG_OFFSET;
182 OTP_CTRL_ROT_CREATOR_AUTH_STATE_READ_LOCK_ROT_CREATOR_AUTH_STATE_READ_LOCK_BIT;
184 #elif defined(OPENTITAN_IS_DARJEELING)
185 case kDifOtpCtrlPartitionOwnershipSlotState:
186 *reg_offset = OTP_CTRL_OWNERSHIP_SLOT_STATE_READ_LOCK_REG_OFFSET;
188 OTP_CTRL_OWNERSHIP_SLOT_STATE_READ_LOCK_OWNERSHIP_SLOT_STATE_READ_LOCK_BIT;
190 case kDifOtpCtrlPartitionRotCreatorAuth:
191 *reg_offset = OTP_CTRL_ROT_CREATOR_AUTH_READ_LOCK_REG_OFFSET;
193 OTP_CTRL_ROT_CREATOR_AUTH_READ_LOCK_ROT_CREATOR_AUTH_READ_LOCK_BIT;
195 case kDifOtpCtrlPartitionRotOwnerAuthSlot0:
196 *reg_offset = OTP_CTRL_ROT_OWNER_AUTH_SLOT0_READ_LOCK_REG_OFFSET;
198 OTP_CTRL_ROT_OWNER_AUTH_SLOT0_READ_LOCK_ROT_OWNER_AUTH_SLOT0_READ_LOCK_BIT;
200 case kDifOtpCtrlPartitionRotOwnerAuthSlot1:
201 *reg_offset = OTP_CTRL_ROT_OWNER_AUTH_SLOT1_READ_LOCK_REG_OFFSET;
203 OTP_CTRL_ROT_OWNER_AUTH_SLOT1_READ_LOCK_ROT_OWNER_AUTH_SLOT1_READ_LOCK_BIT;
205 case kDifOtpCtrlPartitionPlatIntegAuthSlot0:
206 *reg_offset = OTP_CTRL_PLAT_INTEG_AUTH_SLOT0_READ_LOCK_REG_OFFSET;
208 OTP_CTRL_PLAT_INTEG_AUTH_SLOT0_READ_LOCK_PLAT_INTEG_AUTH_SLOT0_READ_LOCK_BIT;
210 case kDifOtpCtrlPartitionPlatIntegAuthSlot1:
211 *reg_offset = OTP_CTRL_PLAT_INTEG_AUTH_SLOT1_READ_LOCK_REG_OFFSET;
213 OTP_CTRL_PLAT_INTEG_AUTH_SLOT1_READ_LOCK_PLAT_INTEG_AUTH_SLOT1_READ_LOCK_BIT;
215 case kDifOtpCtrlPartitionPlatOwnerAuthSlot0:
216 *reg_offset = OTP_CTRL_PLAT_OWNER_AUTH_SLOT0_READ_LOCK_REG_OFFSET;
218 OTP_CTRL_PLAT_OWNER_AUTH_SLOT0_READ_LOCK_PLAT_OWNER_AUTH_SLOT0_READ_LOCK_BIT;
220 case kDifOtpCtrlPartitionPlatOwnerAuthSlot1:
221 *reg_offset = OTP_CTRL_PLAT_OWNER_AUTH_SLOT1_READ_LOCK_REG_OFFSET;
223 OTP_CTRL_PLAT_OWNER_AUTH_SLOT1_READ_LOCK_PLAT_OWNER_AUTH_SLOT1_READ_LOCK_BIT;
225 case kDifOtpCtrlPartitionPlatOwnerAuthSlot2:
226 *reg_offset = OTP_CTRL_PLAT_OWNER_AUTH_SLOT2_READ_LOCK_REG_OFFSET;
228 OTP_CTRL_PLAT_OWNER_AUTH_SLOT2_READ_LOCK_PLAT_OWNER_AUTH_SLOT2_READ_LOCK_BIT;
230 case kDifOtpCtrlPartitionPlatOwnerAuthSlot3:
231 *reg_offset = OTP_CTRL_PLAT_OWNER_AUTH_SLOT3_READ_LOCK_REG_OFFSET;
233 OTP_CTRL_PLAT_OWNER_AUTH_SLOT3_READ_LOCK_PLAT_OWNER_AUTH_SLOT3_READ_LOCK_BIT;
235 case kDifOtpCtrlPartitionExtNvm:
236 *reg_offset = OTP_CTRL_EXT_NVM_READ_LOCK_REG_OFFSET;
237 *index = OTP_CTRL_EXT_NVM_READ_LOCK_EXT_NVM_READ_LOCK_BIT;
239 case kDifOtpCtrlPartitionRomPatch:
240 *reg_offset = OTP_CTRL_ROM_PATCH_READ_LOCK_REG_OFFSET;
241 *index = OTP_CTRL_ROM_PATCH_READ_LOCK_ROM_PATCH_READ_LOCK_BIT;
244 #error "dif_otp_ctrl does not support this top"
260 if (!sw_read_lock_reg_offset(partition, &offset, &index)) {
265 mmio_region_write32(otp->base_addr, offset, reg);
273 if (otp == NULL || is_locked == NULL) {
279 if (!sw_read_lock_reg_offset(partition, &offset, &index)) {
283 uint32_t reg = mmio_region_read32(otp->base_addr, offset);
290 if (otp == NULL ||
status == NULL) {
296 OTP_CTRL_STATUS_VENDOR_TEST_ERROR_BIT,
298 OTP_CTRL_STATUS_CREATOR_SW_CFG_ERROR_BIT,
300 OTP_CTRL_STATUS_OWNER_SW_CFG_ERROR_BIT,
301 #if defined(OPENTITAN_IS_EARLGREY)
302 [kDifOtpCtrlStatusCodeRotCreatorAuthCodesignError] =
303 OTP_CTRL_STATUS_ROT_CREATOR_AUTH_CODESIGN_ERROR_BIT,
304 [kDifOtpCtrlStatusCodeRotCreatorAuthStateError] =
305 OTP_CTRL_STATUS_ROT_CREATOR_AUTH_STATE_ERROR_BIT,
306 #elif defined(OPENTITAN_IS_DARJEELING)
307 [kDifOtpCtrlStatusCodeOwnershipSlotStateError] =
308 OTP_CTRL_STATUS_OWNERSHIP_SLOT_STATE_ERROR_BIT,
309 [kDifOtpCtrlStatusCodeRotCreatorAuthError] =
310 OTP_CTRL_STATUS_ROT_CREATOR_AUTH_ERROR_BIT,
311 [kDifOtpCtrlStatusCodeRotOwnerAuthSlot0Error] =
312 OTP_CTRL_STATUS_ROT_OWNER_AUTH_SLOT0_ERROR_BIT,
313 [kDifOtpCtrlStatusCodeRotOwnerAuthSlot1Error] =
314 OTP_CTRL_STATUS_ROT_OWNER_AUTH_SLOT1_ERROR_BIT,
315 [kDifOtpCtrlStatusCodePlatIntegAuthSlot0Error] =
316 OTP_CTRL_STATUS_PLAT_INTEG_AUTH_SLOT0_ERROR_BIT,
317 [kDifOtpCtrlStatusCodePlatIntegAuthSlot1Error] =
318 OTP_CTRL_STATUS_PLAT_INTEG_AUTH_SLOT1_ERROR_BIT,
319 [kDifOtpCtrlStatusCodePlatOwnerAuthSlot0Error] =
320 OTP_CTRL_STATUS_PLAT_OWNER_AUTH_SLOT0_ERROR_BIT,
321 [kDifOtpCtrlStatusCodePlatOwnerAuthSlot1Error] =
322 OTP_CTRL_STATUS_PLAT_OWNER_AUTH_SLOT1_ERROR_BIT,
323 [kDifOtpCtrlStatusCodePlatOwnerAuthSlot2Error] =
324 OTP_CTRL_STATUS_PLAT_OWNER_AUTH_SLOT2_ERROR_BIT,
325 [kDifOtpCtrlStatusCodePlatOwnerAuthSlot3Error] =
326 OTP_CTRL_STATUS_PLAT_OWNER_AUTH_SLOT3_ERROR_BIT,
327 [kDifOtpCtrlStatusCodeExtNvmError] = OTP_CTRL_STATUS_EXT_NVM_ERROR_BIT,
328 [kDifOtpCtrlStatusCodeRomPatchError] = OTP_CTRL_STATUS_ROM_PATCH_ERROR_BIT,
330 #error "dif_otp_ctrl does not support this top"
337 #if defined(OPENTITAN_IS_DARJEELING)
338 [kDifOtpCtrlStatusCodeSecret3Error] = OTP_CTRL_STATUS_SECRET3_ERROR_BIT,
339 #elif defined(OPENTITAN_IS_EARLGREY)
342 #error "dif_otp_ctrl does not support this top"
345 OTP_CTRL_STATUS_LIFE_CYCLE_ERROR_BIT,
351 OTP_CTRL_STATUS_SCRAMBLING_FSM_ERROR_BIT,
359 uint32_t status_code =
360 mmio_region_read32(otp->base_addr, OTP_CTRL_STATUS_REG_OFFSET);
361 for (
int i = 0; i <
ARRAYSIZE(kIndices); ++i) {
377 .
mask = OTP_CTRL_ERR_CODE_0_ERR_CODE_0_MASK,
378 .index = OTP_CTRL_ERR_CODE_0_ERR_CODE_0_OFFSET,
382 OTP_CTRL_ERR_CODE_0_REG_OFFSET + i * (ptrdiff_t)
sizeof(uint32_t);
383 uint32_t error_code = mmio_region_read32(otp->base_addr, address);
387 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_NO_ERROR:
390 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_MACRO_ERROR:
393 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_MACRO_ECC_CORR_ERROR:
396 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_MACRO_ECC_UNCORR_ERROR:
399 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_MACRO_WRITE_BLANK_ERROR:
402 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_ACCESS_ERROR:
405 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_CHECK_FAIL_ERROR:
408 case OTP_CTRL_ERR_CODE_0_ERR_CODE_0_VALUE_FSM_STATE_ERROR:
463 .
start_addr = OTP_CTRL_PARAM_VENDOR_TEST_OFFSET,
464 .len = OTP_CTRL_PARAM_VENDOR_TEST_SIZE,
468 .is_lifecycle =
false},
470 .start_addr = OTP_CTRL_PARAM_CREATOR_SW_CFG_OFFSET,
471 .len = OTP_CTRL_PARAM_CREATOR_SW_CFG_SIZE,
475 .is_lifecycle =
false},
477 .start_addr = OTP_CTRL_PARAM_OWNER_SW_CFG_OFFSET,
478 .len = OTP_CTRL_PARAM_OWNER_SW_CFG_SIZE,
482 .is_lifecycle =
false},
483 #if defined(OPENTITAN_IS_EARLGREY)
484 [kDifOtpCtrlPartitionRotCreatorAuthCodesign] = {
485 .start_addr = OTP_CTRL_PARAM_ROT_CREATOR_AUTH_CODESIGN_OFFSET,
486 .len = OTP_CTRL_PARAM_ROT_CREATOR_AUTH_CODESIGN_SIZE,
490 .is_lifecycle =
false},
491 [kDifOtpCtrlPartitionRotCreatorAuthState] = {
492 .start_addr = OTP_CTRL_PARAM_ROT_CREATOR_AUTH_STATE_OFFSET,
493 .len = OTP_CTRL_PARAM_ROT_CREATOR_AUTH_STATE_SIZE,
497 .is_lifecycle =
false},
498 #elif defined(OPENTITAN_IS_DARJEELING)
499 [kDifOtpCtrlPartitionOwnershipSlotState] = {
500 .start_addr = OTP_CTRL_PARAM_OWNERSHIP_SLOT_STATE_OFFSET,
501 .len = OTP_CTRL_PARAM_OWNERSHIP_SLOT_STATE_SIZE,
505 .is_lifecycle =
false},
506 [kDifOtpCtrlPartitionRotCreatorAuth] = {
507 .start_addr = OTP_CTRL_PARAM_ROT_CREATOR_AUTH_OFFSET,
508 .len = OTP_CTRL_PARAM_ROT_CREATOR_AUTH_SIZE,
512 .is_lifecycle =
false},
513 [kDifOtpCtrlPartitionRotOwnerAuthSlot0] = {
514 .start_addr = OTP_CTRL_PARAM_ROT_OWNER_AUTH_SLOT0_OFFSET,
515 .len = OTP_CTRL_PARAM_ROT_OWNER_AUTH_SLOT0_SIZE,
519 .is_lifecycle =
false},
520 [kDifOtpCtrlPartitionRotOwnerAuthSlot1] = {
521 .start_addr = OTP_CTRL_PARAM_ROT_OWNER_AUTH_SLOT1_OFFSET,
522 .len = OTP_CTRL_PARAM_ROT_OWNER_AUTH_SLOT1_SIZE,
526 .is_lifecycle =
false},
527 [kDifOtpCtrlPartitionPlatIntegAuthSlot0] = {
528 .start_addr = OTP_CTRL_PARAM_PLAT_INTEG_AUTH_SLOT0_OFFSET,
529 .len = OTP_CTRL_PARAM_PLAT_INTEG_AUTH_SLOT0_SIZE,
533 .is_lifecycle =
false},
534 [kDifOtpCtrlPartitionPlatIntegAuthSlot1] = {
535 .start_addr = OTP_CTRL_PARAM_PLAT_INTEG_AUTH_SLOT1_OFFSET,
536 .len = OTP_CTRL_PARAM_PLAT_INTEG_AUTH_SLOT1_SIZE,
540 .is_lifecycle =
false},
541 [kDifOtpCtrlPartitionPlatOwnerAuthSlot0] = {
542 .start_addr = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT0_OFFSET,
543 .len = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT0_SIZE,
547 .is_lifecycle =
false},
548 [kDifOtpCtrlPartitionPlatOwnerAuthSlot1] = {
549 .start_addr = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT1_OFFSET,
550 .len = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT1_SIZE,
554 .is_lifecycle =
false},
555 [kDifOtpCtrlPartitionPlatOwnerAuthSlot2] = {
556 .start_addr = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT2_OFFSET,
557 .len = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT2_SIZE,
561 .is_lifecycle =
false},
562 [kDifOtpCtrlPartitionPlatOwnerAuthSlot3] = {
563 .start_addr = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT3_OFFSET,
564 .len = OTP_CTRL_PARAM_PLAT_OWNER_AUTH_SLOT3_SIZE,
568 .is_lifecycle =
false},
569 [kDifOtpCtrlPartitionExtNvm] = {
570 .start_addr = OTP_CTRL_PARAM_EXT_NVM_OFFSET,
571 .len = OTP_CTRL_PARAM_EXT_NVM_SIZE,
575 .is_lifecycle =
false},
576 [kDifOtpCtrlPartitionRomPatch] = {
577 .start_addr = OTP_CTRL_PARAM_ROM_PATCH_OFFSET,
578 .len = OTP_CTRL_PARAM_ROM_PATCH_SIZE,
582 .is_lifecycle =
false},
584 #error "dif_otp_ctrl does not support this top"
587 .start_addr = OTP_CTRL_PARAM_HW_CFG0_OFFSET,
588 .len = OTP_CTRL_PARAM_HW_CFG0_SIZE,
590 .is_software =
false,
592 .is_lifecycle =
false},
594 .start_addr = OTP_CTRL_PARAM_HW_CFG1_OFFSET,
595 .len = OTP_CTRL_PARAM_HW_CFG1_SIZE,
597 .is_software =
false,
599 .is_lifecycle =
false},
601 .start_addr = OTP_CTRL_PARAM_SECRET0_OFFSET,
602 .len = OTP_CTRL_PARAM_SECRET0_SIZE,
604 .is_software =
false,
606 .is_lifecycle =
false},
608 .start_addr = OTP_CTRL_PARAM_SECRET1_OFFSET,
609 .len = OTP_CTRL_PARAM_SECRET1_SIZE,
611 .is_software =
false,
613 .is_lifecycle =
false},
615 .start_addr = OTP_CTRL_PARAM_SECRET2_OFFSET,
616 .len = OTP_CTRL_PARAM_SECRET2_SIZE,
618 .is_software =
false,
620 .is_lifecycle =
false},
621 #if defined(OPENTITAN_IS_DARJEELING)
622 [kDifOtpCtrlPartitionSecret3] = {
623 .start_addr = OTP_CTRL_PARAM_SECRET3_OFFSET,
624 .len = OTP_CTRL_PARAM_SECRET3_SIZE,
626 .is_software =
false,
628 .is_lifecycle =
false},
629 #elif defined(OPENTITAN_IS_EARLGREY)
632 #error "dif_otp_ctrl does not support this top"
635 .start_addr = OTP_CTRL_PARAM_LIFE_CYCLE_OFFSET,
636 .len = OTP_CTRL_PARAM_LIFE_CYCLE_SIZE,
638 .is_software =
false,
640 .is_lifecycle =
true},
645 uint32_t abs_address,
646 uint32_t *relative_address) {
647 *relative_address = 0;
649 if (partition >=
ARRAYSIZE(kPartitions)) {
653 if ((abs_address & kPartitions[partition].align_mask) != 0) {
657 if (abs_address < kPartitions[partition].start_addr) {
661 *relative_address = abs_address - kPartitions[partition].
start_addr;
662 if (*relative_address >= kPartitions[partition].len) {
663 *relative_address = 0;
673 if (otp == NULL || partition >=
ARRAYSIZE(kPartitions)) {
677 if ((address & kPartitions[partition].align_mask) != 0) {
681 if (address >= kPartitions[partition].len) {
686 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_ADDRESS_REG_OFFSET,
691 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_CMD_REG_OFFSET,
699 if (otp == NULL || value == NULL) {
703 *value = mmio_region_read32(otp->base_addr,
704 OTP_CTRL_DIRECT_ACCESS_RDATA_0_REG_OFFSET);
710 if (otp == NULL || value == NULL) {
714 *value = mmio_region_read32(otp->base_addr,
715 OTP_CTRL_DIRECT_ACCESS_RDATA_1_REG_OFFSET);
717 *value |= mmio_region_read32(otp->base_addr,
718 OTP_CTRL_DIRECT_ACCESS_RDATA_0_REG_OFFSET);
724 uint32_t address, uint32_t value) {
725 if (otp == NULL || partition >=
ARRAYSIZE(kPartitions)) {
734 if (kPartitions[partition].align_mask != 0x3 ||
735 kPartitions[partition].is_lifecycle) {
739 if ((address & kPartitions[partition].align_mask) != 0) {
746 size_t digest_size = kPartitions[partition].
has_digest *
sizeof(uint64_t);
747 if (address >= kPartitions[partition].len - digest_size) {
752 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_ADDRESS_REG_OFFSET,
755 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_WDATA_0_REG_OFFSET,
760 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_CMD_REG_OFFSET,
768 uint32_t address, uint64_t value) {
769 if (otp == NULL || partition >=
ARRAYSIZE(kPartitions)) {
775 if (kPartitions[partition].align_mask != 0x7) {
779 if ((address & kPartitions[partition].align_mask) != 0) {
785 size_t digest_size =
sizeof(uint64_t);
786 if (address >= kPartitions[partition].len - digest_size) {
791 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_ADDRESS_REG_OFFSET,
794 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_WDATA_0_REG_OFFSET,
796 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_WDATA_1_REG_OFFSET,
801 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_CMD_REG_OFFSET,
810 if (otp == NULL || partition >=
ARRAYSIZE(kPartitions)) {
815 if (!kPartitions[partition].has_digest) {
822 if (is_sw == (digest == 0)) {
826 uint32_t address = kPartitions[partition].
start_addr;
828 address += kPartitions[partition].
len -
sizeof(digest);
830 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_ADDRESS_REG_OFFSET,
834 mmio_region_write32(otp->base_addr,
835 OTP_CTRL_DIRECT_ACCESS_WDATA_0_REG_OFFSET,
836 digest & 0xffffffff);
837 mmio_region_write32(otp->base_addr,
838 OTP_CTRL_DIRECT_ACCESS_WDATA_1_REG_OFFSET,
843 ? OTP_CTRL_DIRECT_ACCESS_CMD_WR_BIT
844 : OTP_CTRL_DIRECT_ACCESS_CMD_DIGEST_BIT;
846 mmio_region_write32(otp->base_addr, OTP_CTRL_DIRECT_ACCESS_CMD_REG_OFFSET,
856 *reg0 = OTP_CTRL_VENDOR_TEST_DIGEST_0_REG_OFFSET;
857 *reg1 = OTP_CTRL_VENDOR_TEST_DIGEST_1_REG_OFFSET;
860 *reg0 = OTP_CTRL_CREATOR_SW_CFG_DIGEST_0_REG_OFFSET;
861 *reg1 = OTP_CTRL_CREATOR_SW_CFG_DIGEST_1_REG_OFFSET;
864 *reg0 = OTP_CTRL_OWNER_SW_CFG_DIGEST_0_REG_OFFSET;
865 *reg1 = OTP_CTRL_OWNER_SW_CFG_DIGEST_1_REG_OFFSET;
867 #if defined(OPENTITAN_IS_EARLGREY)
868 case kDifOtpCtrlPartitionRotCreatorAuthCodesign:
869 *reg0 = OTP_CTRL_ROT_CREATOR_AUTH_CODESIGN_DIGEST_0_REG_OFFSET;
870 *reg1 = OTP_CTRL_ROT_CREATOR_AUTH_CODESIGN_DIGEST_1_REG_OFFSET;
872 case kDifOtpCtrlPartitionRotCreatorAuthState:
873 *reg0 = OTP_CTRL_ROT_CREATOR_AUTH_STATE_DIGEST_0_REG_OFFSET;
874 *reg1 = OTP_CTRL_ROT_CREATOR_AUTH_STATE_DIGEST_1_REG_OFFSET;
876 #elif defined(OPENTITAN_IS_DARJEELING)
877 case kDifOtpCtrlPartitionRotCreatorAuth:
878 *reg0 = OTP_CTRL_ROT_CREATOR_AUTH_DIGEST_0_REG_OFFSET;
879 *reg1 = OTP_CTRL_ROT_CREATOR_AUTH_DIGEST_1_REG_OFFSET;
881 case kDifOtpCtrlPartitionRotOwnerAuthSlot0:
882 *reg0 = OTP_CTRL_ROT_OWNER_AUTH_SLOT0_DIGEST_0_REG_OFFSET;
883 *reg1 = OTP_CTRL_ROT_OWNER_AUTH_SLOT0_DIGEST_1_REG_OFFSET;
885 case kDifOtpCtrlPartitionRotOwnerAuthSlot1:
886 *reg0 = OTP_CTRL_ROT_OWNER_AUTH_SLOT1_DIGEST_0_REG_OFFSET;
887 *reg1 = OTP_CTRL_ROT_OWNER_AUTH_SLOT1_DIGEST_1_REG_OFFSET;
889 case kDifOtpCtrlPartitionPlatIntegAuthSlot0:
890 *reg0 = OTP_CTRL_PLAT_INTEG_AUTH_SLOT0_DIGEST_0_REG_OFFSET;
891 *reg1 = OTP_CTRL_PLAT_INTEG_AUTH_SLOT0_DIGEST_1_REG_OFFSET;
893 case kDifOtpCtrlPartitionPlatIntegAuthSlot1:
894 *reg0 = OTP_CTRL_PLAT_INTEG_AUTH_SLOT1_DIGEST_0_REG_OFFSET;
895 *reg1 = OTP_CTRL_PLAT_INTEG_AUTH_SLOT1_DIGEST_1_REG_OFFSET;
897 case kDifOtpCtrlPartitionPlatOwnerAuthSlot0:
898 *reg0 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT0_DIGEST_0_REG_OFFSET;
899 *reg1 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT0_DIGEST_1_REG_OFFSET;
901 case kDifOtpCtrlPartitionPlatOwnerAuthSlot1:
902 *reg0 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT1_DIGEST_0_REG_OFFSET;
903 *reg1 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT1_DIGEST_1_REG_OFFSET;
905 case kDifOtpCtrlPartitionPlatOwnerAuthSlot2:
906 *reg0 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT2_DIGEST_0_REG_OFFSET;
907 *reg1 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT2_DIGEST_1_REG_OFFSET;
909 case kDifOtpCtrlPartitionPlatOwnerAuthSlot3:
910 *reg0 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT3_DIGEST_0_REG_OFFSET;
911 *reg1 = OTP_CTRL_PLAT_OWNER_AUTH_SLOT3_DIGEST_1_REG_OFFSET;
913 case kDifOtpCtrlPartitionRomPatch:
914 *reg0 = OTP_CTRL_ROM_PATCH_DIGEST_0_REG_OFFSET;
915 *reg1 = OTP_CTRL_ROM_PATCH_DIGEST_1_REG_OFFSET;
918 #error "dif_otp_ctrl does not support this top"
921 *reg0 = OTP_CTRL_HW_CFG0_DIGEST_0_REG_OFFSET;
922 *reg1 = OTP_CTRL_HW_CFG0_DIGEST_1_REG_OFFSET;
925 *reg0 = OTP_CTRL_HW_CFG1_DIGEST_0_REG_OFFSET;
926 *reg1 = OTP_CTRL_HW_CFG1_DIGEST_1_REG_OFFSET;
929 *reg0 = OTP_CTRL_SECRET0_DIGEST_0_REG_OFFSET;
930 *reg1 = OTP_CTRL_SECRET0_DIGEST_1_REG_OFFSET;
933 *reg0 = OTP_CTRL_SECRET1_DIGEST_0_REG_OFFSET;
934 *reg1 = OTP_CTRL_SECRET1_DIGEST_1_REG_OFFSET;
937 *reg0 = OTP_CTRL_SECRET2_DIGEST_0_REG_OFFSET;
938 *reg1 = OTP_CTRL_SECRET2_DIGEST_1_REG_OFFSET;
940 #if defined(OPENTITAN_IS_DARJEELING)
941 case kDifOtpCtrlPartitionSecret3:
942 *reg0 = OTP_CTRL_SECRET3_DIGEST_0_REG_OFFSET;
943 *reg1 = OTP_CTRL_SECRET3_DIGEST_1_REG_OFFSET;
945 #elif defined(OPENTITAN_IS_EARLGREY)
948 #error "dif_otp_ctrl does not support this top"
960 if (otp == NULL || is_computed == NULL) {
964 ptrdiff_t reg0, reg1;
965 if (!get_digest_regs(partition, ®0, ®1)) {
969 uint64_t value = mmio_region_read32(otp->base_addr, reg1);
971 value |= mmio_region_read32(otp->base_addr, reg0);
973 *is_computed = value != 0;
981 if (otp == NULL || digest == NULL) {
985 ptrdiff_t reg0, reg1;
986 if (!get_digest_regs(partition, ®0, ®1)) {
990 uint64_t value = mmio_region_read32(otp->base_addr, reg1);
992 value |= mmio_region_read32(otp->base_addr, reg0);
1004 uint32_t address, uint32_t *buf,
1006 if (otp == NULL || partition >=
ARRAYSIZE(kPartitions) || buf == NULL) {
1010 if (!kPartitions[partition].is_software) {
1014 if ((address & kPartitions[partition].align_mask) != 0) {
1018 if (address + len >= kPartitions[partition].len) {
1022 uint32_t reg_offset = OTP_CTRL_SW_CFG_WINDOW_REG_OFFSET +
1025 len *
sizeof(uint32_t));