1 /* 2 * Copyright (c) 2025, Arm Limited. All rights reserved. 3 * 4 * SPDX-License-Identifier: BSD-3-Clause 5 */ 6 7 #include <assert.h> 8 #include <stdarg.h> 9 #include <stdint.h> 10 11 #include <plat/common/common_def.h> 12 #include <plat/common/platform.h> 13 #include <platform_def.h> 14 15 #include <tpm2.h> 16 #include <tpm2_chip.h> 17 18 #include <drivers/auth/crypto_mod.h> 19 #include <drivers/delay_timer.h> 20 #include <drivers/gpio_spi.h> 21 #include <drivers/measured_boot/metadata.h> 22 #include <drivers/tpm/tpm2_slb9670/slb9670_gpio.h> 23 #include <event_measure.h> 24 #include <event_print.h> 25 #include <tools_share/tbbr_oid.h> 26 27 #include "./include/rpi3_measured_boot.h" 28 29 /* RPI3 table with platform specific image IDs, names and PCRs */ 30 const event_log_metadata_t rpi3_event_log_metadata[] = { 31 { BL31_IMAGE_ID, MBOOT_BL31_IMAGE_STRING, PCR_0 }, 32 { BL33_IMAGE_ID, MBOOT_BL33_IMAGE_STRING, PCR_0 }, 33 { NT_FW_CONFIG_ID, MBOOT_NT_FW_CONFIG_STRING, PCR_0 }, 34 35 { EVLOG_INVALID_ID, NULL, (unsigned int)(-1) } /* Terminator */ 36 }; 37 38 #if DISCRETE_TPM 39 extern struct tpm_chip_data tpm_chip_data; 40 41 static void rpi3_bl2_tpm_early_interface_setup(void) 42 { 43 #if TPM_INTERFACE_FIFO_SPI 44 struct spi_plat *spidev; 45 const struct tpm_timeout_ops timeout_ops = { 46 .timeout_init_us = timeout_init_us, 47 .timeout_elapsed = timeout_elapsed 48 }; 49 50 const struct gpio_spi_config *tpm_rpi3_gpio_data = 51 tpm2_slb9670_get_config(); 52 int rc; 53 54 tpm2_slb9670_gpio_init(tpm_rpi3_gpio_data); 55 56 spidev = gpio_spi_init(tpm_rpi3_gpio_data); 57 58 rc = tpm_interface_init(spidev, &timeout_ops, &tpm_chip_data, 0); 59 if (rc != 0) { 60 ERROR("BL2: TPM interface init failed\n"); 61 panic(); 62 } 63 64 #endif 65 } 66 #endif 67 68 static uint8_t *event_log_start; 69 static size_t event_log_size; 70 71 void bl2_plat_mboot_init(void) 72 { 73 int rc; 74 #if DISCRETE_TPM 75 rpi3_bl2_tpm_early_interface_setup(); 76 #endif 77 78 rpi3_mboot_fetch_eventlog_info(&event_log_start, &event_log_size); 79 80 rc = event_log_init_and_reg( 81 event_log_start, event_log_start + PLAT_ARM_EVENT_LOG_MAX_SIZE, 82 event_log_size, crypto_mod_tcg_hash); 83 if (rc < 0) { 84 ERROR("Failed to initialize event log (%d).\n", rc); 85 panic(); 86 } 87 } 88 89 void bl2_plat_mboot_finish(void) 90 { 91 int rc; 92 93 /* Event Log address in Non-Secure memory */ 94 uintptr_t ns_log_addr; 95 96 /* Event Log filled size */ 97 size_t event_log_cur_size; 98 99 event_log_cur_size = event_log_get_cur_size((uint8_t *)event_log_start); 100 101 /* write the eventlog addr and size to NT_FW_CONFIG TPM entry */ 102 rc = rpi3_set_nt_fw_info(event_log_cur_size, &ns_log_addr); 103 if (rc != 0) { 104 ERROR("%s(): Unable to update %s_FW_CONFIG\n", 105 __func__, "NT"); 106 /* 107 * fatal error due to Bl33 maintaining the assumption 108 * that the eventlog is successfully passed via 109 * NT_FW_CONFIG. 110 */ 111 panic(); 112 } 113 114 /* Copy Event Log to Non-secure memory */ 115 (void)memcpy((void *)ns_log_addr, (const void *)event_log_start, 116 event_log_cur_size); 117 118 /* Ensure that the Event Log is visible in Non-secure memory */ 119 flush_dcache_range(ns_log_addr, event_log_cur_size); 120 121 /* Dump Event Log for user view */ 122 event_log_dump((uint8_t *)event_log_start, event_log_cur_size); 123 124 #if DISCRETE_TPM 125 /* relinquish control of TPM locality 0 and close interface */ 126 rc = tpm_interface_close(&tpm_chip_data, 0); 127 if (rc != 0) { 128 ERROR("BL2: TPM interface close failed\n"); 129 panic(); 130 } 131 #endif 132 } 133