mirror of
https://github.com/ARM-software/arm-trusted-firmware.git
synced 2025-04-11 15:14:21 +00:00
Merge changes I1dfb95aa,I9eb61c48 into integration
* changes: feat(intel): support FCS commands with SiPSVC V3 framework feat(intel): implementation of SiPSVC-V3 protocol framework
This commit is contained in:
commit
e86efe4b14
11 changed files with 2709 additions and 199 deletions
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* Copyright (c) 2019-2020, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2019-2022, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2024, Altera Corporation. All rights reserved.
|
||||
* Copyright (c) 2024-2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -175,6 +175,16 @@ void bl31_platform_setup(void)
|
|||
mmio_write_64(PLAT_CPU_RELEASE_ADDR,
|
||||
(uint64_t)plat_secondary_cpus_bl31_entry);
|
||||
|
||||
#if SIP_SVC_V3
|
||||
/*
|
||||
* Re-initialize the mailbox to include V3 specific routines.
|
||||
* In V3, this re-initialize is required because prior to BL31, U-Boot
|
||||
* SPL has its own mailbox settings and this initialization will
|
||||
* override to those settings as required by the V3 framework.
|
||||
*/
|
||||
mailbox_init();
|
||||
#endif
|
||||
|
||||
mailbox_hps_stage_notify(HPS_EXECUTION_STATE_SSBL);
|
||||
}
|
||||
|
||||
|
|
|
@ -177,6 +177,17 @@ void bl31_platform_setup(void)
|
|||
gicv3_distif_init();
|
||||
gicv3_rdistif_init(plat_my_core_pos());
|
||||
gicv3_cpuif_enable(plat_my_core_pos());
|
||||
|
||||
#if SIP_SVC_V3
|
||||
/*
|
||||
* Re-initialize the mailbox to include V3 specific routines.
|
||||
* In V3, this re-initialize is required because prior to BL31, U-Boot
|
||||
* SPL has its own mailbox settings and this initialization will
|
||||
* override to those settings as required by the V3 framework.
|
||||
*/
|
||||
mailbox_init();
|
||||
#endif
|
||||
|
||||
mailbox_hps_stage_notify(HPS_EXECUTION_STATE_SSBL);
|
||||
}
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/*
|
||||
* Copyright (c) 2019-2022, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2019-2023, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2024, Altera Corporation. All rights reserved.
|
||||
* Copyright (c) 2024-2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -207,6 +207,9 @@
|
|||
#define MAX_IO_DEVICES 4
|
||||
#define MAX_IO_BLOCK_DEVICES 2
|
||||
|
||||
/* Define this, to support the SiPSVC V3 implementation. */
|
||||
#define SIP_SVC_V3 1
|
||||
|
||||
#ifndef __ASSEMBLER__
|
||||
struct socfpga_bl31_params {
|
||||
param_header_t h;
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
/*
|
||||
* Copyright (c) 2020-2022, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -88,12 +89,22 @@
|
|||
#define FCS_ECDSA_HASH_SIG_VERIFY_CMD_MAX_WORD_SIZE 52U
|
||||
#define FCS_ECDH_REQUEST_CMD_MAX_WORD_SIZE 29U
|
||||
|
||||
#define FCS_CRYPTO_ECB_BUFFER_SIZE 12U
|
||||
#define FCS_CRYPTO_CBC_CTR_BUFFER_SIZE 28U
|
||||
#define FCS_CRYPTO_BLOCK_MODE_MASK 0x07
|
||||
#define FCS_CRYPTO_ECB_MODE 0x00
|
||||
#define FCS_CRYPTO_CBC_MODE 0x01
|
||||
#define FCS_CRYPTO_CTR_MODE 0x02
|
||||
#define FCS_CRYPTO_ECB_BUFFER_SIZE 12U
|
||||
#define FCS_CRYPTO_CBC_CTR_BUFFER_SIZE 28U
|
||||
#define FCS_CRYPTO_BLOCK_MODE_MASK 0x07
|
||||
#define FCS_CRYPTO_ECB_MODE 0x00
|
||||
#define FCS_CRYPTO_CBC_MODE 0x01
|
||||
#define FCS_CRYPTO_CTR_MODE 0x02
|
||||
#define FCS_CRYPTO_GCM_MODE 0x03
|
||||
#define FCS_CRYPTO_GCM_GHASH_MODE 0x04
|
||||
|
||||
#define FCS_HKDF_REQUEST_DATA_SIZE 512U
|
||||
#define FCS_HKDF_KEY_OBJ_MAX_SIZE 352U
|
||||
#define FCS_HKDF_KEY_DATA_SIZE 168U
|
||||
#define FCS_HKDF_STEP0_1_KEY_OBJ_SIZE_BITS 384U
|
||||
#define FCS_HKDF_STEP2_KEY_OBJ_SIZE_BITS 256U
|
||||
#define FCS_HKDF_INPUT_BLOCK_SIZE 80U
|
||||
#define FCS_HKDF_SHA2_384_KEY_DATA_SIZE 48U
|
||||
|
||||
/* FCS Payload Structure */
|
||||
typedef struct fcs_rng_payload_t {
|
||||
|
@ -183,10 +194,12 @@ uint32_t intel_fcs_random_number_gen(uint64_t addr, uint64_t *ret_size,
|
|||
uint32_t *mbox_error);
|
||||
int intel_fcs_random_number_gen_ext(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t size, uint32_t *send_id);
|
||||
uint32_t intel_fcs_send_cert(uint64_t addr, uint64_t size,
|
||||
uint32_t intel_fcs_send_cert(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint64_t addr, uint64_t size,
|
||||
uint32_t *send_id);
|
||||
uint32_t intel_fcs_get_provision_data(uint32_t *send_id);
|
||||
uint32_t intel_fcs_cntr_set_preauth(uint8_t counter_type,
|
||||
uint32_t intel_fcs_cntr_set_preauth(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint8_t counter_type,
|
||||
int32_t counter_value,
|
||||
uint32_t test_bit,
|
||||
uint32_t *mbox_error);
|
||||
|
@ -198,14 +211,18 @@ uint32_t intel_fcs_decryption(uint32_t src_addr, uint32_t src_size,
|
|||
uint32_t dst_addr, uint32_t dst_size,
|
||||
uint32_t *send_id);
|
||||
|
||||
int intel_fcs_encryption_ext(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_encryption_ext(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint32_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t *mbox_error);
|
||||
int intel_fcs_decryption_ext(uint32_t sesion_id, uint32_t context_id,
|
||||
uint32_t *mbox_error, uint32_t smmu_src_addr,
|
||||
uint32_t smmu_dst_addr);
|
||||
int intel_fcs_decryption_ext(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t sesion_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint32_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t *mbox_error);
|
||||
uint32_t *mbox_error, uint64_t owner_id,
|
||||
uint32_t smmu_src_addr, uint32_t smmu_dst_addr);
|
||||
|
||||
int intel_fcs_sigma_teardown(uint32_t session_id, uint32_t *mbox_error);
|
||||
int intel_fcs_chip_id(uint32_t *id_low, uint32_t *id_high, uint32_t *mbox_error);
|
||||
|
@ -218,9 +235,10 @@ int intel_fcs_get_measurement(uint64_t src_addr, uint32_t src_size,
|
|||
uint32_t intel_fcs_get_rom_patch_sha384(uint64_t addr, uint64_t *ret_size,
|
||||
uint32_t *mbox_error);
|
||||
|
||||
int intel_fcs_create_cert_on_reload(uint32_t cert_request,
|
||||
uint32_t *mbox_error);
|
||||
int intel_fcs_get_attestation_cert(uint32_t cert_request, uint64_t dst_addr,
|
||||
int intel_fcs_create_cert_on_reload(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t cert_request, uint32_t *mbox_error);
|
||||
int intel_fcs_get_attestation_cert(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t cert_request, uint64_t dst_addr,
|
||||
uint32_t *dst_size, uint32_t *mbox_error);
|
||||
|
||||
int intel_fcs_open_crypto_service_session(uint32_t *session_id,
|
||||
|
@ -242,10 +260,12 @@ int intel_fcs_get_crypto_service_key_info(uint32_t session_id, uint32_t key_id,
|
|||
int intel_fcs_get_digest_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint32_t param_size,
|
||||
uint64_t param_data, uint32_t *mbox_error);
|
||||
int intel_fcs_get_digest_update_finalize(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_get_digest_update_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint8_t is_finalised, uint32_t *mbox_error);
|
||||
uint8_t is_finalised, uint32_t *mbox_error,
|
||||
uint32_t smmu_src_addr);
|
||||
int intel_fcs_get_digest_smmu_update_finalize(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
|
@ -255,11 +275,12 @@ int intel_fcs_get_digest_smmu_update_finalize(uint32_t session_id, uint32_t cont
|
|||
int intel_fcs_mac_verify_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint32_t param_size,
|
||||
uint64_t param_data, uint32_t *mbox_error);
|
||||
int intel_fcs_mac_verify_update_finalize(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_mac_verify_update_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t data_size, uint8_t is_finalised,
|
||||
uint32_t *mbox_error);
|
||||
uint32_t *mbox_error, uint64_t smmu_src_addr);
|
||||
int intel_fcs_mac_verify_smmu_update_finalize(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
|
@ -269,7 +290,8 @@ int intel_fcs_mac_verify_smmu_update_finalize(uint32_t session_id, uint32_t cont
|
|||
int intel_fcs_ecdsa_hash_sign_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint32_t param_size,
|
||||
uint64_t param_data, uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_hash_sign_finalize(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_ecdsa_hash_sign_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t *mbox_error);
|
||||
|
@ -277,7 +299,8 @@ int intel_fcs_ecdsa_hash_sign_finalize(uint32_t session_id, uint32_t context_id,
|
|||
int intel_fcs_ecdsa_hash_sig_verify_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint32_t param_size,
|
||||
uint64_t param_data, uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_hash_sig_verify_finalize(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_ecdsa_hash_sig_verify_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t *mbox_error);
|
||||
|
@ -286,11 +309,12 @@ int intel_fcs_ecdsa_sha2_data_sign_init(uint32_t session_id,
|
|||
uint32_t context_id, uint32_t key_id,
|
||||
uint32_t param_size, uint64_t param_data,
|
||||
uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_sha2_data_sign_update_finalize(uint32_t session_id,
|
||||
uint32_t context_id, uint32_t src_addr,
|
||||
uint32_t src_size, uint64_t dst_addr,
|
||||
uint32_t *dst_size, uint8_t is_finalised,
|
||||
uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_sha2_data_sign_update_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint8_t is_finalised, uint32_t *mbox_error,
|
||||
uint64_t smmu_src_addr);
|
||||
int intel_fcs_ecdsa_sha2_data_sign_smmu_update_finalize(uint32_t session_id,
|
||||
uint32_t context_id, uint32_t src_addr,
|
||||
uint32_t src_size, uint64_t dst_addr,
|
||||
|
@ -301,11 +325,12 @@ int intel_fcs_ecdsa_sha2_data_sig_verify_init(uint32_t session_id,
|
|||
uint32_t context_id, uint32_t key_id,
|
||||
uint32_t param_size, uint64_t param_data,
|
||||
uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_sha2_data_sig_verify_update_finalize(uint32_t session_id,
|
||||
uint32_t context_id, uint32_t src_addr,
|
||||
uint32_t src_size, uint64_t dst_addr,
|
||||
uint32_t *dst_size, uint32_t data_size,
|
||||
uint8_t is_finalised, uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_sha2_data_sig_verify_update_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t data_size, uint8_t is_finalised,
|
||||
uint32_t *mbox_error, uint64_t smmu_src_addr);
|
||||
int intel_fcs_ecdsa_sha2_data_sig_verify_smmu_update_finalize(uint32_t session_id,
|
||||
uint32_t context_id, uint32_t src_addr,
|
||||
uint32_t src_size, uint64_t dst_addr,
|
||||
|
@ -316,14 +341,16 @@ int intel_fcs_ecdsa_sha2_data_sig_verify_smmu_update_finalize(uint32_t session_i
|
|||
int intel_fcs_ecdsa_get_pubkey_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint32_t param_size,
|
||||
uint64_t param_data, uint32_t *mbox_error);
|
||||
int intel_fcs_ecdsa_get_pubkey_finalize(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_ecdsa_get_pubkey_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t *mbox_error);
|
||||
|
||||
int intel_fcs_ecdh_request_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint32_t param_size,
|
||||
uint64_t param_data, uint32_t *mbox_error);
|
||||
int intel_fcs_ecdh_request_finalize(uint32_t session_id, uint32_t context_id,
|
||||
int intel_fcs_ecdh_request_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint32_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t *dst_size,
|
||||
uint32_t *mbox_error);
|
||||
|
@ -331,10 +358,16 @@ int intel_fcs_ecdh_request_finalize(uint32_t session_id, uint32_t context_id,
|
|||
int intel_fcs_aes_crypt_init(uint32_t session_id, uint32_t context_id,
|
||||
uint32_t key_id, uint64_t param_addr,
|
||||
uint32_t param_size, uint32_t *mbox_error);
|
||||
int intel_fcs_aes_crypt_update_finalize(uint32_t session_id,
|
||||
uint32_t context_id, uint64_t src_addr,
|
||||
uint32_t src_size, uint64_t dst_addr,
|
||||
uint32_t dst_size, uint8_t is_finalised,
|
||||
uint32_t *send_id);
|
||||
int intel_fcs_aes_crypt_update_finalize(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t context_id,
|
||||
uint64_t src_addr, uint32_t src_size,
|
||||
uint64_t dst_addr, uint32_t dst_size,
|
||||
uint32_t aad_size, uint8_t is_finalised,
|
||||
uint32_t *send_id, uint64_t smmu_src_addr,
|
||||
uint64_t smmu_dst_addr);
|
||||
|
||||
int intel_fcs_hkdf_request(uint32_t smc_fid, uint32_t trans_id,
|
||||
uint32_t session_id, uint32_t step_type,
|
||||
uint32_t mac_mode, uint32_t src_addr,
|
||||
uint32_t key_uid, uint32_t op_key_size);
|
||||
#endif /* SOCFPGA_FCS_H */
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
* Copyright (c) 2019-2023, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2024, Altera Corporation. All rights reserved.
|
||||
* Copyright (c) 2024-2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -23,20 +23,22 @@
|
|||
#define MBOX_TEST_BIT BIT(31)
|
||||
|
||||
/* Mailbox Shared Memory Register Map */
|
||||
#define MBOX_CIN 0x00
|
||||
#define MBOX_ROUT 0x04
|
||||
#define MBOX_URG 0x08
|
||||
#define MBOX_INT 0x0C
|
||||
#define MBOX_COUT 0x20
|
||||
#define MBOX_RIN 0x24
|
||||
#define MBOX_STATUS 0x2C
|
||||
#define MBOX_CMD_BUFFER 0x40
|
||||
#define MBOX_RESP_BUFFER 0xC0
|
||||
#define MBOX_CIN 0x00 /* Command valid offset, to SDM */
|
||||
#define MBOX_ROUT 0x04 /* Response output offset, to SDM */
|
||||
#define MBOX_URG 0x08 /* Urgent command, to SDM */
|
||||
#define MBOX_INT 0x0C /* Interrupt enables, to SDM */
|
||||
/* 0x10 - 0x1F, Reserved */
|
||||
|
||||
/* Mailbox SDM doorbell */
|
||||
#define MBOX_DOORBELL_TO_SDM 0x400
|
||||
#define MBOX_DOORBELL_FROM_SDM 0x480
|
||||
#define MBOX_COUT 0x20 /* Command free offset, from SDM */
|
||||
#define MBOX_RIN 0x24 /* Response valid offset, from SDM */
|
||||
#define MBOX_STATUS 0x2C /* Mailbox status from SDM to client */
|
||||
/* 0x30 - 0x3F, Reserved */
|
||||
|
||||
#define MBOX_CMD_BUFFER 0x40 /* Circular buffer, cmds to SDM */
|
||||
#define MBOX_RESP_BUFFER 0xC0 /* Circular buffer, resp from SDM */
|
||||
|
||||
#define MBOX_DOORBELL_TO_SDM 0x400 /* Doorbell from HPS to SDM */
|
||||
#define MBOX_DOORBELL_FROM_SDM 0x480 /* Doorbell from SDM to HPS */
|
||||
|
||||
/* Mailbox commands */
|
||||
|
||||
|
@ -61,12 +63,15 @@
|
|||
#define MBOX_HWMON_READVOLT 0x18
|
||||
#define MBOX_HWMON_READTEMP 0x19
|
||||
|
||||
|
||||
/* QSPI Commands */
|
||||
#define MBOX_CMD_QSPI_OPEN 0x32
|
||||
#define MBOX_CMD_QSPI_CLOSE 0x33
|
||||
#define MBOX_CMD_QSPI_SET_CS 0x34
|
||||
#define MBOX_CMD_QSPI_ERASE 0x38
|
||||
#define MBOX_CMD_QSPI_WRITE 0x39
|
||||
#define MBOX_CMD_QSPI_READ 0x3A
|
||||
#define MBOX_CMD_QSPI_DIRECT 0x3B
|
||||
#define MBOX_CMD_QSPI_GET_DEV_INFO 0x74
|
||||
|
||||
/* SEU Commands */
|
||||
#define MBOX_CMD_SEU_ERR_READ 0x3C
|
||||
|
@ -94,12 +99,14 @@
|
|||
#define MBOX_FCS_ECDSA_SHA2_DATA_SIGN_VERIFY 0x87
|
||||
#define MBOX_FCS_ECDSA_GET_PUBKEY 0x88
|
||||
#define MBOX_FCS_ECDH_REQUEST 0x89
|
||||
#define MBOX_FCS_HKDF_REQUEST 0x8B
|
||||
#define MBOX_FCS_OPEN_CS_SESSION 0xA0
|
||||
#define MBOX_FCS_CLOSE_CS_SESSION 0xA1
|
||||
#define MBOX_FCS_IMPORT_CS_KEY 0xA5
|
||||
#define MBOX_FCS_EXPORT_CS_KEY 0xA6
|
||||
#define MBOX_FCS_REMOVE_CS_KEY 0xA7
|
||||
#define MBOX_FCS_GET_CS_KEY_INFO 0xA8
|
||||
#define MBOX_FCS_CREATE_CS_KEY 0xA9
|
||||
|
||||
/* PSG SIGMA Commands */
|
||||
#define MBOX_PSG_SIGMA_TEARDOWN 0xD5
|
||||
|
@ -111,7 +118,9 @@
|
|||
#define MBOX_GET_MEASUREMENT 0x183
|
||||
|
||||
/* Miscellaneous commands */
|
||||
#define MBOX_CMD_MCTP_MSG 0x194
|
||||
#define MBOX_GET_ROM_PATCH_SHA384 0x1B0
|
||||
#define MBOX_CMD_GET_DEVICEID 0x500
|
||||
|
||||
/* Mailbox Definitions */
|
||||
|
||||
|
@ -120,6 +129,18 @@
|
|||
#define CMD_CASUAL 0
|
||||
#define CMD_URGENT 1
|
||||
|
||||
/* Mailbox command flags and related macros */
|
||||
#define MBOX_CMD_FLAG_DIRECT BIT(0)
|
||||
#define MBOX_CMD_FLAG_INDIRECT BIT(1)
|
||||
#define MBOX_CMD_FLAG_CASUAL BIT(2)
|
||||
#define MBOX_CMD_FLAG_URGENT BIT(3)
|
||||
|
||||
#define MBOX_CMD_FLAG_CASUAL_INDIRECT (MBOX_CMD_FLAG_CASUAL | \
|
||||
MBOX_CMD_FLAG_INDIRECT)
|
||||
|
||||
#define IS_CMD_SET(cmd, _type) ((((cmd) & MBOX_CMD_FLAG_##_type) != 0) ? \
|
||||
1 : 0)
|
||||
|
||||
#define MBOX_WORD_BYTE 4U
|
||||
#define MBOX_RESP_BUFFER_SIZE 16
|
||||
#define MBOX_CMD_BUFFER_SIZE 32
|
||||
|
@ -171,22 +192,25 @@
|
|||
+ MBOX_WORD_BYTE * (ptr))
|
||||
|
||||
/* Mailbox interrupt flags and masks */
|
||||
#define MBOX_INT_FLAG_COE 0x1
|
||||
#define MBOX_INT_FLAG_RIE 0x2
|
||||
#define MBOX_INT_FLAG_UAE 0x100
|
||||
#define MBOX_COE_BIT(INTERRUPT) ((INTERRUPT) & 0x3)
|
||||
#define MBOX_UAE_BIT(INTERRUPT) (((INTERRUPT) & (1<<8)))
|
||||
#define MBOX_INT_FLAG_COE BIT(0) /* COUT update interrupt enable */
|
||||
#define MBOX_INT_FLAG_RIE BIT(1) /* RIN update interrupt enable */
|
||||
#define MBOX_INT_FLAG_UAE BIT(8) /* Urgent ACK interrupt enable */
|
||||
|
||||
#define MBOX_COE_BIT(INTERRUPT) ((INTERRUPT) & MBOX_INT_FLAG_COE)
|
||||
#define MBOX_RIE_BIT(INTERRUPT) ((INTERRUPT) & MBOX_INT_FLAG_RIE)
|
||||
#define MBOX_UAE_BIT(INTERRUPT) ((INTERRUPT) & MBOX_INT_FLAG_UAE)
|
||||
|
||||
/* Mailbox response and status */
|
||||
#define MBOX_RESP_ERR(BUFFER) ((BUFFER) & 0x000007ff)
|
||||
#define MBOX_RESP_LEN(BUFFER) (((BUFFER) & 0x007ff000) >> 12)
|
||||
#define MBOX_RESP_CLIENT_ID(BUFFER) (((BUFFER) & 0xf0000000) >> 28)
|
||||
#define MBOX_RESP_JOB_ID(BUFFER) (((BUFFER) & 0x0f000000) >> 24)
|
||||
#define MBOX_RESP_TRANSACTION_ID(BUFFER) (((BUFFER) & 0xff000000) >> 24)
|
||||
#define MBOX_STATUS_UA_MASK (1<<8)
|
||||
|
||||
/* Mailbox command and response */
|
||||
#define MBOX_CLIENT_ID_CMD(CLIENT_ID) ((CLIENT_ID) << 28)
|
||||
#define MBOX_JOB_ID_CMD(JOB_ID) (JOB_ID<<24)
|
||||
#define MBOX_JOB_ID_CMD(JOB_ID) (JOB_ID << 24)
|
||||
#define MBOX_CMD_LEN_CMD(CMD_LEN) ((CMD_LEN) << 12)
|
||||
#define MBOX_INDIRECT(val) ((val) << 11)
|
||||
#define MBOX_CMD_MASK(header) ((header) & 0x7ff)
|
||||
|
@ -204,6 +228,17 @@
|
|||
#define CONFIG_STATUS_FW_VER_OFFSET 1
|
||||
#define CONFIG_STATUS_FW_VER_MASK 0x00FFFFFF
|
||||
|
||||
/* QSPI mailbox command macros */
|
||||
#define MBOX_QSPI_SET_CS_OFFSET (28)
|
||||
#define MBOX_QSPI_SET_CS_MODE_OFFSET (27)
|
||||
#define MBOX_QSPI_SET_CS_CA_OFFSET (26)
|
||||
#define MBOX_QSPI_ERASE_SIZE_GRAN (0x400)
|
||||
|
||||
#define MBOX_4K_ALIGNED_MASK (0xFFF)
|
||||
#define MBOX_IS_4K_ALIGNED(x) ((x) & MBOX_4K_ALIGNED_MASK)
|
||||
#define MBOX_IS_WORD_ALIGNED(x) (!((x) & 0x3))
|
||||
#define MBOX_QSPI_RW_MAX_WORDS (0x1000)
|
||||
|
||||
/* Data structure */
|
||||
|
||||
typedef struct mailbox_payload {
|
||||
|
@ -264,4 +299,107 @@ int mailbox_safe_inject_seu_err(uint32_t *arg, unsigned int len);
|
|||
|
||||
int mailbox_send_fpga_config_comp(void);
|
||||
|
||||
#if SIP_SVC_V3
|
||||
#define MBOX_CLIENT_ID_SHIFT (28)
|
||||
#define MBOX_JOB_ID_SHIFT (24)
|
||||
#define MBOX_CMD_LEN_SHIFT (12)
|
||||
#define MBOX_INDIRECT_SHIFT (11)
|
||||
|
||||
#define MBOX_FRAME_CMD_HEADER(client_id, job_id, args_len, indirect, cmd)\
|
||||
((client_id << MBOX_CLIENT_ID_SHIFT) | \
|
||||
(job_id << MBOX_JOB_ID_SHIFT) | \
|
||||
(args_len << MBOX_CMD_LEN_SHIFT) | \
|
||||
(indirect << MBOX_CMD_LEN_SHIFT) | \
|
||||
cmd)
|
||||
|
||||
#define FLAG_SDM_RESPONSE_IS_VALID BIT(0)
|
||||
#define FLAG_SDM_RESPONSE_IS_USED BIT(1)
|
||||
#define FLAG_SDM_RESPONSE_IS_IN_PROGRESS BIT(2)
|
||||
#define FLAG_SDM_RESPONSE_IS_POLL_ON_INTR BIT(3)
|
||||
|
||||
/*
|
||||
* TODO: Re-visit this queue size based on the system load.
|
||||
* 4 bits for client ID and 4 bits for job ID, total 8 bits and we can have up to
|
||||
* 256 transactions. We can tune this based on our system load at any given time
|
||||
*/
|
||||
#define MBOX_SVC_CMD_QUEUE_SIZE (32)
|
||||
#define MBOX_SVC_RESP_QUEUE_SIZE (32)
|
||||
#define MBOX_SVC_MAX_JOB_ID (16)
|
||||
#define MBOX_SVC_CMD_ARG_SIZE (2)
|
||||
#define MBOX_SVC_CMD_IS_USED BIT(0)
|
||||
#define MBOX_SVC_CMD_CB_ARGS_SIZE (4)
|
||||
#define MBOX_SVC_MAX_CLIENTS (16)
|
||||
#define MBOX_SVC_MAX_RESP_DATA_SIZE (32)
|
||||
#define MBOX_SVC_SMC_RET_MAX_SIZE (8)
|
||||
|
||||
/* Client ID(4bits) + Job ID(4bits) = Transcation ID(TID - 8bits, 256 combinations) */
|
||||
#define MBOX_MAX_TIDS (256)
|
||||
/* Each transcation ID bitmap holds 64bits */
|
||||
#define MBOX_TID_BITMAP_SIZE (sizeof(uint64_t) * 8)
|
||||
/* Number of transcation ID bitmaps required to hold 256 combinations */
|
||||
#define MBOX_MAX_TIDS_BITMAP (MBOX_MAX_TIDS / MBOX_TID_BITMAP_SIZE)
|
||||
|
||||
/* SDM Response State (SRS) enums */
|
||||
typedef enum sdm_resp_state {
|
||||
SRS_WAIT_FOR_RESP = 0x00U,
|
||||
SRS_WAIT_FOR_HEADER,
|
||||
SRS_WAIT_FOR_ARGUMENTS,
|
||||
SRS_SYNC_ERROR
|
||||
} sdm_resp_state_t;
|
||||
|
||||
/* SDM response data structure */
|
||||
typedef struct sdm_response {
|
||||
bool is_poll_intr;
|
||||
uint8_t client_id;
|
||||
uint8_t job_id;
|
||||
uint16_t resp_len;
|
||||
uint16_t err_code;
|
||||
uint32_t flags;
|
||||
uint32_t header;
|
||||
uint16_t rcvd_resp_len;
|
||||
uint32_t resp_data[MBOX_SVC_MAX_RESP_DATA_SIZE];
|
||||
} sdm_response_t;
|
||||
|
||||
/* SDM client callback template */
|
||||
typedef uint8_t (*sdm_command_callback)(void *resp, void *cmd,
|
||||
uint32_t *ret_args);
|
||||
|
||||
/* SDM command data structure */
|
||||
typedef struct sdm_command {
|
||||
uint8_t client_id;
|
||||
uint8_t job_id;
|
||||
uint32_t flags;
|
||||
sdm_command_callback cb;
|
||||
uint32_t *cb_args;
|
||||
uint8_t cb_args_len;
|
||||
} sdm_command_t;
|
||||
|
||||
/* Get the transcation ID from client ID and job ID. */
|
||||
#define MBOX_GET_TRANS_ID(cid, jib) (((cid) << 4) | (jib))
|
||||
|
||||
/* Mailbox service data structure */
|
||||
typedef struct mailbox_service {
|
||||
sdm_resp_state_t resp_state;
|
||||
sdm_resp_state_t next_resp_state;
|
||||
uint32_t flags;
|
||||
int curr_di;
|
||||
uint64_t received_bitmap[MBOX_MAX_TIDS_BITMAP];
|
||||
uint64_t interrupt_bitmap[MBOX_MAX_TIDS_BITMAP];
|
||||
sdm_command_t cmd_queue[MBOX_SVC_CMD_QUEUE_SIZE];
|
||||
sdm_response_t resp_queue[MBOX_SVC_RESP_QUEUE_SIZE];
|
||||
} mailbox_service_t;
|
||||
|
||||
int mailbox_send_cmd_async_v3(uint8_t client_id, uint8_t job_id, uint32_t cmd,
|
||||
uint32_t *args, uint32_t args_len, uint8_t cmd_flag,
|
||||
sdm_command_callback cb, uint32_t *cb_args,
|
||||
uint32_t cb_args_len);
|
||||
|
||||
int mailbox_response_poll_v3(uint8_t client_id, uint8_t job_id, uint32_t *ret_args,
|
||||
uint32_t *ret_args_size);
|
||||
|
||||
int mailbox_response_poll_on_intr_v3(uint8_t *client_id, uint8_t *job_id,
|
||||
uint64_t *bitmap);
|
||||
|
||||
#endif /* #if SIP_SVC_V3 */
|
||||
|
||||
#endif /* SOCFPGA_MBOX_H */
|
||||
|
|
|
@ -26,6 +26,10 @@
|
|||
#define INTEL_SIP_SMC_CMD_V2_RANGE_BEGIN 0x400
|
||||
#define INTEL_SIP_SMC_CMD_V2_RANGE_END 0x4FF
|
||||
|
||||
/* SiP V3 command code range */
|
||||
#define INTEL_SIP_SMC_CMD_V3_RANGE_BEGIN 0x00C8
|
||||
#define INTEL_SIP_SMC_CMD_V3_RANGE_END 0x01F4
|
||||
|
||||
/* SiP V2 protocol header */
|
||||
#define INTEL_SIP_SMC_HEADER_JOB_ID_MASK 0xF
|
||||
#define INTEL_SIP_SMC_HEADER_JOB_ID_OFFSET 0U
|
||||
|
@ -189,11 +193,11 @@
|
|||
/*
|
||||
* Increase if there is any backward compatibility impact
|
||||
*/
|
||||
#define SIP_SVC_VERSION_MAJOR 2
|
||||
#define SIP_SVC_VERSION_MAJOR 3
|
||||
/*
|
||||
* Increase if there is new SMC function ID being added
|
||||
*/
|
||||
#define SIP_SVC_VERSION_MINOR 2
|
||||
#define SIP_SVC_VERSION_MINOR 1
|
||||
|
||||
|
||||
/* Structure Definitions */
|
||||
|
@ -243,4 +247,103 @@ uintptr_t sip_smc_handler_v2(uint32_t smc_fid,
|
|||
void *handle,
|
||||
u_register_t flags);
|
||||
|
||||
|
||||
#if SIP_SVC_V3
|
||||
#define SMC_RET_ARGS_ONE (1)
|
||||
#define SMC_RET_ARGS_TWO (2)
|
||||
#define SMC_RET_ARGS_THREE (3)
|
||||
#define SMC_RET_ARGS_FOUR (4)
|
||||
#define SMC_RET_ARGS_FIVE (5)
|
||||
#define SMC_RET_ARGS_SIX (6)
|
||||
|
||||
/*
|
||||
* SiP SVC Version3 SMC Functions IDs
|
||||
*/
|
||||
|
||||
/* Generic response POLL commands */
|
||||
#define ALTERA_SIP_SMC_ASYNC_RESP_POLL (0x420000C8)
|
||||
#define ALTERA_SIP_SMC_ASYNC_RESP_POLL_ON_INTR (0x420000C9)
|
||||
|
||||
/* QSPI related commands */
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_OPEN (0x420000CC)
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_CLOSE (0x420000CD)
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_SET_CS (0x420000CE)
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_ERASE (0x420000CF)
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_WRITE (0x420000D0)
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_READ (0x420000D1)
|
||||
#define ALTERA_SIP_SMC_ASYNC_GET_DEVICE_IDENTITY (0x420000D2)
|
||||
#define ALTERA_SIP_SMC_ASYNC_GET_IDCODE (0x420000D3)
|
||||
#define ALTERA_SIP_SMC_ASYNC_QSPI_GET_DEV_INFO (0x420000D4)
|
||||
|
||||
#define ALTERA_SIP_SMC_ASYNC_HWMON_READTEMP (0x420000E8)
|
||||
#define ALTERA_SIP_SMC_ASYNC_HWMON_READVOLT (0x420000E9)
|
||||
|
||||
/* FCS crypto service VAB/SDOS commands */
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_RANDOM_NUMBER (0x4200012C)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_RANDOM_NUMBER_EXT (0x4200012D)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CRYPTION (0x4200012E)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CRYPTION_EXT (0x4200012F)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_SERVICE_REQUEST (0x42000130)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_SEND_CERTIFICATE (0x42000131)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_PROVISION_DATA (0x42000132)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CNTR_SET_PREAUTH (0x42000133)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_PSGSIGMA_TEARDOWN (0x42000134)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CHIP_ID (0x42000135)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ATTESTATION_SUBKEY (0x42000136)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ATTESTATION_MEASUREMENTS (0x42000137)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_ATTESTATION_CERT (0x42000138)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CREATE_CERT_ON_RELOAD (0x42000139)
|
||||
|
||||
/* FCS crypto service session management commands */
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_OPEN_CS_SESSION (0x4200013A)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CLOSE_CS_SESSION (0x4200013B)
|
||||
|
||||
/* FCS crypto service key management commands */
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_IMPORT_CS_KEY (0x4200013C)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_EXPORT_CS_KEY (0x4200013D)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_REMOVE_CS_KEY (0x4200013E)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_CS_KEY_INFO (0x4200013F)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CREATE_CS_KEY (0x42000167)
|
||||
|
||||
/* FCS crypto service primitive commands */
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_AES_CRYPT_INIT (0x42000140)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_AES_CRYPT_UPDATE (0x42000141)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_AES_CRYPT_FINALIZE (0x42000142)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_DIGEST_INIT (0x42000143)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_DIGEST_UPDATE (0x42000144)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_DIGEST_FINALIZE (0x42000145)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_DIGEST_SMMU_UPDATE (0x42000146)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_GET_DIGEST_SMMU_FINALIZE (0x42000147)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_MAC_VERIFY_INIT (0x42000148)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_MAC_VERIFY_UPDATE (0x42000149)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_MAC_VERIFY_FINALIZE (0x4200014A)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_MAC_VERIFY_SMMU_UPDATE (0x4200014B)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_MAC_VERIFY_SMMU_FINALIZE (0x4200014C)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_HASH_SIGN_INIT (0x4200014D)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_HASH_SIGN_FINALIZE (0x4200014E)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIGN_INIT (0x4200014F)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIGN_UPDATE (0x42000150)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIGN_FINALIZE (0x42000151)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIGN_SMMU_UPDATE (0x42000152)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIGN_SMMU_FINALIZE (0x42000153)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_HASH_SIG_VERIFY_INIT (0x42000154)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_HASH_SIG_VERIFY_FINALIZE (0x42000155)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIG_VERIFY_INIT (0x42000156)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIG_VERIFY_UPDATE (0x42000157)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIG_VERIFY_FINALIZE (0x42000158)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIG_VERIFY_SMMU_UPDATE (0x42000159)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_SHA2_DATA_SIG_VERIFY_SMMU_FINALIZE (0x4200015A)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_GET_PUBKEY_INIT (0x42000160)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDSA_GET_PUBKEY_FINALIZE (0x42000161)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDH_REQUEST_INIT (0x42000162)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_ECDH_REQUEST_FINALIZE (0x42000163)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_SDM_REMAPPER_CONFIG (0x42000164)
|
||||
#define ALTERA_SIP_SMC_ASYNC_MCTP_MSG (0x42000165)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_HKDF_REQUEST (0x42000166)
|
||||
#define ALTERA_SIP_SMC_ASYNC_FCS_CREATE_CS_KEY (0x42000167)
|
||||
|
||||
#define GET_CLIENT_ID(x) (((x) & 0xF0) >> 4)
|
||||
#define GET_JOB_ID(x) ((x) & 0x0F)
|
||||
#endif /* SIP_SVC_V3 */
|
||||
|
||||
#endif /* SOCFPGA_SIP_SVC_H */
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,11 +1,12 @@
|
|||
/*
|
||||
* Copyright (c) 2020-2023, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2024, Altera Corporation. All rights reserved.
|
||||
* Copyright (c) 2024-2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
||||
#include <lib/mmio.h>
|
||||
#include <lib/spinlock.h>
|
||||
#include <common/debug.h>
|
||||
#include <drivers/delay_timer.h>
|
||||
#include <platform_def.h>
|
||||
|
@ -15,6 +16,34 @@
|
|||
#include "socfpga_sip_svc.h"
|
||||
#include "socfpga_system_manager.h"
|
||||
|
||||
#if SIP_SVC_V3
|
||||
/* Function prototypes */
|
||||
void mailbox_init_v3(void);
|
||||
static int mailbox_response_handler_fsm(void);
|
||||
static inline void mailbox_free_cmd_desc(sdm_command_t *cmd_desc);
|
||||
static sdm_response_t *mailbox_get_resp_desc(uint8_t client_id, uint8_t job_id,
|
||||
uint8_t *index);
|
||||
static sdm_command_t *mailbox_get_cmd_desc(uint8_t client_id, uint8_t job_id);
|
||||
static inline void mailbox_free_resp_desc(uint8_t index);
|
||||
static sdm_command_t *mailbox_get_free_cmd_desc(void);
|
||||
static sdm_response_t *mailbox_get_resp_desc_cid(uint8_t client_id,
|
||||
uint8_t *index);
|
||||
static int mailbox_read_response_v3(uint8_t client_id, uint8_t *job_id,
|
||||
uint32_t *header, uint32_t *resp,
|
||||
uint32_t *resp_len,
|
||||
uint8_t ignore_client_id);
|
||||
static int mailbox_poll_response_v3(uint8_t client_id, uint8_t job_id,
|
||||
uint32_t *resp, unsigned int *resp_len,
|
||||
uint32_t urgent);
|
||||
|
||||
static spinlock_t mbox_db_lock; /* Mailbox service data base lock */
|
||||
static spinlock_t mbox_write_lock; /* Hardware mailbox FIFO write lock */
|
||||
static spinlock_t mbox_read_lock; /* Hardware mailbox FIFO read lock */
|
||||
|
||||
static mailbox_service_t mbox_svc; /* Mailbox service data base */
|
||||
static uint8_t async_v1_job_id;
|
||||
#endif /* #if SIP_SVC_V3 */
|
||||
|
||||
static mailbox_payload_t mailbox_resp_payload;
|
||||
static mailbox_container_t mailbox_resp_ctr = {0, 0, &mailbox_resp_payload};
|
||||
|
||||
|
@ -34,13 +63,13 @@ static bool is_mailbox_cmdbuf_empty(uint32_t cin)
|
|||
|
||||
static int wait_for_mailbox_cmdbuf_empty(uint32_t cin)
|
||||
{
|
||||
unsigned int timeout = 200U;
|
||||
unsigned int timeout = 20000U;
|
||||
|
||||
do {
|
||||
if (is_mailbox_cmdbuf_empty(cin)) {
|
||||
break;
|
||||
}
|
||||
mdelay(10U);
|
||||
udelay(50U);
|
||||
} while (--timeout != 0U);
|
||||
|
||||
if (timeout == 0U) {
|
||||
|
@ -54,7 +83,9 @@ static int write_mailbox_cmd_buffer(uint32_t *cin, uint32_t cout,
|
|||
uint32_t data,
|
||||
bool *is_doorbell_triggered)
|
||||
{
|
||||
unsigned int timeout = 100U;
|
||||
unsigned int timeout = 20000U;
|
||||
|
||||
VERBOSE("MBOX: 0x%x\n", data);
|
||||
|
||||
do {
|
||||
if (is_mailbox_cmdbuf_full(*cin)) {
|
||||
|
@ -63,7 +94,7 @@ static int write_mailbox_cmd_buffer(uint32_t *cin, uint32_t cout,
|
|||
MBOX_DOORBELL_TO_SDM, 1U);
|
||||
*is_doorbell_triggered = true;
|
||||
}
|
||||
mdelay(10U);
|
||||
udelay(50U);
|
||||
} else {
|
||||
mmio_write_32(MBOX_ENTRY_TO_ADDR(CMD, (*cin)++), data);
|
||||
*cin %= MBOX_CMD_BUFFER_SIZE;
|
||||
|
@ -84,6 +115,11 @@ static int write_mailbox_cmd_buffer(uint32_t *cin, uint32_t cout,
|
|||
return MBOX_RET_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* Function description: Write the command header, and its payload one by one
|
||||
* into the mailbox command buffer. Along with this, check for mailbox buffer
|
||||
* full condition and trigger doorbell to SDM if the command buffer is full.
|
||||
*/
|
||||
static int fill_mailbox_circular_buffer(uint32_t header_cmd, uint32_t *args,
|
||||
unsigned int len)
|
||||
{
|
||||
|
@ -92,15 +128,21 @@ static int fill_mailbox_circular_buffer(uint32_t header_cmd, uint32_t *args,
|
|||
int ret;
|
||||
bool is_doorbell_triggered = false;
|
||||
|
||||
#if SIP_SVC_V3
|
||||
spin_lock(&mbox_write_lock);
|
||||
#endif
|
||||
|
||||
cmd_free_offset = mmio_read_32(MBOX_OFFSET + MBOX_CIN);
|
||||
sdm_read_offset = mmio_read_32(MBOX_OFFSET + MBOX_COUT);
|
||||
|
||||
/* Write the command header here */
|
||||
ret = write_mailbox_cmd_buffer(&cmd_free_offset, sdm_read_offset,
|
||||
header_cmd, &is_doorbell_triggered);
|
||||
if (ret != 0) {
|
||||
goto restart_mailbox;
|
||||
}
|
||||
|
||||
/* Write the payload here w.r.to args and its len - one by one. */
|
||||
for (i = 0U; i < len; i++) {
|
||||
is_doorbell_triggered = false;
|
||||
ret = write_mailbox_cmd_buffer(&cmd_free_offset,
|
||||
|
@ -113,6 +155,9 @@ static int fill_mailbox_circular_buffer(uint32_t header_cmd, uint32_t *args,
|
|||
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_TO_SDM, 1U);
|
||||
|
||||
#if SIP_SVC_V3
|
||||
spin_unlock(&mbox_write_lock);
|
||||
#endif
|
||||
return MBOX_RET_OK;
|
||||
|
||||
restart_mailbox:
|
||||
|
@ -129,12 +174,21 @@ restart_mailbox:
|
|||
}
|
||||
}
|
||||
|
||||
#if SIP_SVC_V3
|
||||
spin_unlock(&mbox_write_lock);
|
||||
#endif
|
||||
return MBOX_TIMEOUT;
|
||||
}
|
||||
|
||||
int mailbox_read_response(unsigned int *job_id, uint32_t *response,
|
||||
unsigned int *resp_len)
|
||||
{
|
||||
#if SIP_SVC_V3
|
||||
return mailbox_read_response_v3(MBOX_ATF_CLIENT_ID,
|
||||
(uint8_t *)job_id, NULL,
|
||||
response, resp_len,
|
||||
0);
|
||||
#else
|
||||
uint32_t rin;
|
||||
uint32_t rout;
|
||||
uint32_t resp_data;
|
||||
|
@ -174,13 +228,23 @@ int mailbox_read_response(unsigned int *job_id, uint32_t *response,
|
|||
|
||||
return MBOX_RET_OK;
|
||||
}
|
||||
|
||||
return MBOX_NO_RESPONSE;
|
||||
#endif
|
||||
}
|
||||
|
||||
int mailbox_read_response_async(unsigned int *job_id, uint32_t *header,
|
||||
uint32_t *response, unsigned int *resp_len,
|
||||
uint8_t ignore_client_id)
|
||||
{
|
||||
#if SIP_SVC_V3
|
||||
/* Just to avoid the build warning */
|
||||
(void)mailbox_resp_ctr;
|
||||
return mailbox_read_response_v3(MBOX_ATF_CLIENT_ID,
|
||||
(uint8_t *)job_id, header,
|
||||
response, resp_len,
|
||||
ignore_client_id);
|
||||
#else
|
||||
uint32_t rin;
|
||||
uint32_t rout;
|
||||
uint32_t resp_data;
|
||||
|
@ -220,7 +284,6 @@ int mailbox_read_response_async(unsigned int *job_id, uint32_t *header,
|
|||
return MBOX_WRONG_ID;
|
||||
}
|
||||
}
|
||||
|
||||
*job_id = MBOX_RESP_JOB_ID(resp_data);
|
||||
ret_resp_len = MBOX_RESP_LEN(resp_data);
|
||||
mailbox_resp_ctr.payload->header = resp_data;
|
||||
|
@ -272,11 +335,16 @@ int mailbox_read_response_async(unsigned int *job_id, uint32_t *header,
|
|||
|
||||
*resp_len = 0;
|
||||
return (mailbox_resp_ctr.flag & MBOX_PAYLOAD_FLAG_BUSY) ? MBOX_BUSY : MBOX_NO_RESPONSE;
|
||||
#endif
|
||||
}
|
||||
|
||||
int mailbox_poll_response(uint32_t job_id, uint32_t urgent, uint32_t *response,
|
||||
unsigned int *resp_len)
|
||||
unsigned int *resp_len)
|
||||
{
|
||||
#if SIP_SVC_V3
|
||||
return mailbox_poll_response_v3(MBOX_ATF_CLIENT_ID, (uint8_t)job_id,
|
||||
response, resp_len, urgent);
|
||||
#else
|
||||
unsigned int timeout = 40U;
|
||||
unsigned int sdm_loop = 255U;
|
||||
unsigned int ret_resp_len;
|
||||
|
@ -285,7 +353,6 @@ int mailbox_poll_response(uint32_t job_id, uint32_t urgent, uint32_t *response,
|
|||
uint32_t resp_data;
|
||||
|
||||
while (sdm_loop != 0U) {
|
||||
|
||||
do {
|
||||
if (mmio_read_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM)
|
||||
== 1U) {
|
||||
|
@ -310,7 +377,7 @@ int mailbox_poll_response(uint32_t job_id, uint32_t urgent, uint32_t *response,
|
|||
}
|
||||
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_URG, 0U);
|
||||
INFO("Error: Mailbox did not get UA");
|
||||
ERROR("MBOX: Mailbox did not get UA");
|
||||
return MBOX_RET_ERROR;
|
||||
}
|
||||
|
||||
|
@ -324,13 +391,21 @@ int mailbox_poll_response(uint32_t job_id, uint32_t urgent, uint32_t *response,
|
|||
rout %= MBOX_RESP_BUFFER_SIZE;
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_ROUT, rout);
|
||||
|
||||
if (MBOX_RESP_CLIENT_ID(resp_data) != MBOX_ATF_CLIENT_ID
|
||||
|| MBOX_RESP_JOB_ID(resp_data) != job_id) {
|
||||
if ((MBOX_RESP_CLIENT_ID(resp_data) != MBOX_ATF_CLIENT_ID) ||
|
||||
(MBOX_RESP_JOB_ID(resp_data) != job_id)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Get the return response len from the response header. */
|
||||
ret_resp_len = MBOX_RESP_LEN(resp_data);
|
||||
|
||||
/* Print the response header. */
|
||||
VERBOSE("MBOX: RespHdr: cid %d, jid %d, len %d, err_code 0x%x\n",
|
||||
MBOX_RESP_CLIENT_ID(resp_data),
|
||||
MBOX_RESP_JOB_ID(resp_data),
|
||||
MBOX_RESP_LEN(resp_data),
|
||||
MBOX_RESP_ERR(resp_data));
|
||||
|
||||
if (iterate_resp(ret_resp_len, response, resp_len)
|
||||
!= MBOX_RET_OK) {
|
||||
return MBOX_TIMEOUT;
|
||||
|
@ -349,6 +424,7 @@ int mailbox_poll_response(uint32_t job_id, uint32_t urgent, uint32_t *response,
|
|||
|
||||
INFO("Timed out waiting for SDM\n");
|
||||
return MBOX_TIMEOUT;
|
||||
#endif
|
||||
}
|
||||
|
||||
int iterate_resp(uint32_t mbox_resp_len, uint32_t *resp_buf,
|
||||
|
@ -366,8 +442,7 @@ int iterate_resp(uint32_t mbox_resp_len, uint32_t *resp_buf,
|
|||
|
||||
if ((resp_buf != NULL) && (resp_len != NULL)
|
||||
&& (*resp_len != 0U)) {
|
||||
*(resp_buf + total_resp_len)
|
||||
= resp_data;
|
||||
*(resp_buf + total_resp_len) = resp_data;
|
||||
*resp_len = *resp_len - 1;
|
||||
total_resp_len++;
|
||||
}
|
||||
|
@ -417,6 +492,9 @@ int mailbox_send_cmd_async(uint32_t *job_id, uint32_t cmd, uint32_t *args,
|
|||
return status;
|
||||
}
|
||||
|
||||
#if SIP_SVC_V3
|
||||
async_v1_job_id = (uint8_t)*job_id;
|
||||
#endif
|
||||
*job_id = (*job_id + 1U) % MBOX_MAX_IND_JOB_ID;
|
||||
|
||||
return MBOX_RET_OK;
|
||||
|
@ -433,9 +511,7 @@ int mailbox_send_cmd(uint32_t job_id, uint32_t cmd, uint32_t *args,
|
|||
MBOX_STATUS_UA_MASK;
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_URG, cmd);
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_TO_SDM, 1U);
|
||||
}
|
||||
|
||||
else {
|
||||
} else {
|
||||
status = fill_mailbox_circular_buffer(
|
||||
MBOX_CLIENT_ID_CMD(MBOX_ATF_CLIENT_ID) |
|
||||
MBOX_JOB_ID_CMD(job_id) |
|
||||
|
@ -460,12 +536,12 @@ void mailbox_clear_response(void)
|
|||
|
||||
void mailbox_set_int(uint32_t interrupt)
|
||||
{
|
||||
|
||||
mmio_write_32(MBOX_OFFSET+MBOX_INT, MBOX_COE_BIT(interrupt) |
|
||||
mmio_write_32(MBOX_OFFSET+MBOX_INT,
|
||||
MBOX_COE_BIT(interrupt) |
|
||||
MBOX_RIE_BIT(interrupt) |
|
||||
MBOX_UAE_BIT(interrupt));
|
||||
}
|
||||
|
||||
|
||||
void mailbox_set_qspi_open(void)
|
||||
{
|
||||
mailbox_set_int(MBOX_INT_FLAG_COE | MBOX_INT_FLAG_RIE);
|
||||
|
@ -606,6 +682,7 @@ int mailbox_init(void)
|
|||
|
||||
mailbox_set_int(MBOX_INT_FLAG_COE | MBOX_INT_FLAG_RIE |
|
||||
MBOX_INT_FLAG_UAE);
|
||||
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_URG, 0U);
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM, 0U);
|
||||
|
||||
|
@ -616,8 +693,16 @@ int mailbox_init(void)
|
|||
return status;
|
||||
}
|
||||
|
||||
#if SIP_SVC_V3
|
||||
/* Initialize the mailbox version3 implementation, and in V3 we
|
||||
* are interested in only RIE interrupt
|
||||
*/
|
||||
mailbox_init_v3();
|
||||
mailbox_set_int(MBOX_INT_FLAG_RIE);
|
||||
#else
|
||||
mailbox_set_int(MBOX_INT_FLAG_COE | MBOX_INT_FLAG_RIE |
|
||||
MBOX_INT_FLAG_UAE);
|
||||
#endif
|
||||
|
||||
return MBOX_RET_OK;
|
||||
}
|
||||
|
@ -730,3 +815,693 @@ int mailbox_safe_inject_seu_err(uint32_t *arg, unsigned int len)
|
|||
return mailbox_send_cmd(MBOX_JOB_ID, MBOX_CMD_SAFE_INJECT_SEU_ERR, arg, len,
|
||||
CMD_CASUAL, NULL, NULL);
|
||||
}
|
||||
|
||||
#if SIP_SVC_V3
|
||||
static int mailbox_fill_cmd_desc(uint8_t client_id, uint8_t job_id,
|
||||
uint32_t *resp_buff)
|
||||
{
|
||||
sdm_command_t *cmd_desc = NULL;
|
||||
|
||||
/* Get a free command descriptor */
|
||||
cmd_desc = mailbox_get_free_cmd_desc();
|
||||
if (cmd_desc == NULL) {
|
||||
return MBOX_BUFFER_FULL;
|
||||
}
|
||||
|
||||
/* Record all the given values for the command. */
|
||||
cmd_desc->client_id = client_id;
|
||||
cmd_desc->job_id = job_id;
|
||||
cmd_desc->cb = NULL;
|
||||
cmd_desc->cb_args = resp_buff;
|
||||
cmd_desc->cb_args_len = 0U;
|
||||
|
||||
return MBOX_RET_OK;
|
||||
}
|
||||
|
||||
/* Returns the command descriptor based on the client and job ID. */
|
||||
static sdm_command_t *mailbox_get_cmd_desc(uint8_t client_id, uint8_t job_id)
|
||||
{
|
||||
spin_lock(&mbox_db_lock);
|
||||
for (uint32_t count = 0; count < MBOX_SVC_CMD_QUEUE_SIZE; count++) {
|
||||
if ((mbox_svc.cmd_queue[count].client_id == client_id) &&
|
||||
(mbox_svc.cmd_queue[count].job_id == job_id) &&
|
||||
(mbox_svc.cmd_queue[count].flags & MBOX_SVC_CMD_IS_USED)) {
|
||||
spin_unlock(&mbox_db_lock);
|
||||
return &(mbox_svc.cmd_queue[count]);
|
||||
}
|
||||
}
|
||||
|
||||
spin_unlock(&mbox_db_lock);
|
||||
VERBOSE("MBOX: Command descriptor not found for cid %d, jid %d\n",
|
||||
client_id, job_id);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Returns the response descriptor based on only client ID. */
|
||||
static sdm_response_t *mailbox_get_resp_desc_cid(uint8_t client_id, uint8_t *index)
|
||||
{
|
||||
spin_lock(&mbox_db_lock);
|
||||
|
||||
for (uint32_t count = 0; count < MBOX_SVC_RESP_QUEUE_SIZE; count++) {
|
||||
if ((mbox_svc.resp_queue[count].client_id == client_id) &&
|
||||
(mbox_svc.resp_queue[count].flags & FLAG_SDM_RESPONSE_IS_VALID)) {
|
||||
*index = count;
|
||||
/*
|
||||
* Once we get the valid response descriptor, get the
|
||||
* job ID and mark up the bitmaps.
|
||||
*/
|
||||
uint8_t job_id = mbox_svc.resp_queue[count].job_id;
|
||||
uint8_t transaction_id = MBOX_GET_TRANS_ID(client_id, job_id);
|
||||
|
||||
mbox_svc.received_bitmap[transaction_id / MBOX_TID_BITMAP_SIZE] &=
|
||||
~(1ULL << (transaction_id % MBOX_TID_BITMAP_SIZE));
|
||||
mbox_svc.interrupt_bitmap[transaction_id / MBOX_TID_BITMAP_SIZE] &=
|
||||
~(1ULL << (transaction_id % MBOX_TID_BITMAP_SIZE));
|
||||
spin_unlock(&mbox_db_lock);
|
||||
return &(mbox_svc.resp_queue[count]);
|
||||
}
|
||||
}
|
||||
|
||||
spin_unlock(&mbox_db_lock);
|
||||
VERBOSE("MBOX: Response descriptor not found for cid %d\n", client_id);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Returns the response descriptor based on the client and job ID. */
|
||||
static sdm_response_t *mailbox_get_resp_desc(uint8_t client_id, uint8_t job_id, uint8_t *index)
|
||||
{
|
||||
spin_lock(&mbox_db_lock);
|
||||
/*
|
||||
* Let's first check whether we have a response bitmap set for the given
|
||||
* client ID and job ID.
|
||||
*/
|
||||
uint8_t transaction_id = MBOX_GET_TRANS_ID(client_id, job_id);
|
||||
|
||||
if ((mbox_svc.received_bitmap[transaction_id / MBOX_TID_BITMAP_SIZE] &
|
||||
(1ULL << (transaction_id % MBOX_TID_BITMAP_SIZE))) == 0) {
|
||||
spin_unlock(&mbox_db_lock);
|
||||
VERBOSE("MBOX: Response bitmap not set for cid %d, jid %d, bitmap 0x%16lx\n",
|
||||
client_id, job_id, mbox_svc.received_bitmap[transaction_id / 64]);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
for (uint32_t count = 0; count < MBOX_SVC_RESP_QUEUE_SIZE; count++) {
|
||||
if (mbox_svc.resp_queue[count].flags & FLAG_SDM_RESPONSE_IS_VALID) {
|
||||
if ((mbox_svc.resp_queue[count].client_id == client_id) &&
|
||||
(mbox_svc.resp_queue[count].job_id == job_id)) {
|
||||
*index = count;
|
||||
mbox_svc.received_bitmap[transaction_id / MBOX_TID_BITMAP_SIZE] &=
|
||||
~(1ULL << (transaction_id % MBOX_TID_BITMAP_SIZE));
|
||||
mbox_svc.interrupt_bitmap[transaction_id / MBOX_TID_BITMAP_SIZE] &=
|
||||
~(1ULL << (transaction_id % MBOX_TID_BITMAP_SIZE));
|
||||
spin_unlock(&mbox_db_lock);
|
||||
return &(mbox_svc.resp_queue[count]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
spin_unlock(&mbox_db_lock);
|
||||
VERBOSE("MBOX: Response descriptor not found for cid %d, jid %d\n",
|
||||
client_id, job_id);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static int32_t mailbox_get_free_resp_desc(void)
|
||||
{
|
||||
spin_lock(&mbox_db_lock);
|
||||
static uint32_t free_index = MBOX_SVC_RESP_QUEUE_SIZE - 1;
|
||||
uint32_t count = 0U, try = 0U;
|
||||
|
||||
for (try = 0; try < MBOX_SVC_RESP_QUEUE_SIZE; try++) {
|
||||
free_index = (free_index + 1) % MBOX_SVC_RESP_QUEUE_SIZE;
|
||||
if ((mbox_svc.resp_queue[free_index].flags &
|
||||
FLAG_SDM_RESPONSE_IS_USED) != 0U) {
|
||||
count = free_index;
|
||||
spin_unlock(&mbox_db_lock);
|
||||
return count;
|
||||
}
|
||||
}
|
||||
|
||||
/* No free descriptors are available */
|
||||
spin_unlock(&mbox_db_lock);
|
||||
VERBOSE("MBOX: No free response descriptors are available\n");
|
||||
|
||||
return MBOX_BUFFER_FULL;
|
||||
}
|
||||
|
||||
static sdm_command_t *mailbox_get_free_cmd_desc(void)
|
||||
{
|
||||
spin_lock(&mbox_db_lock);
|
||||
static uint32_t free_index;
|
||||
|
||||
/* Rollover the command queue free index */
|
||||
if (free_index == (MBOX_SVC_CMD_QUEUE_SIZE - 1)) {
|
||||
free_index = 0U;
|
||||
}
|
||||
|
||||
for (; free_index < MBOX_SVC_CMD_QUEUE_SIZE; free_index++) {
|
||||
if ((mbox_svc.cmd_queue[free_index].flags &
|
||||
MBOX_SVC_CMD_IS_USED) != 0U) {
|
||||
mbox_svc.cmd_queue[free_index].flags |= MBOX_SVC_CMD_IS_USED;
|
||||
spin_unlock(&mbox_db_lock);
|
||||
return &(mbox_svc.cmd_queue[free_index]);
|
||||
}
|
||||
}
|
||||
|
||||
/* No free command descriptors are available */
|
||||
spin_unlock(&mbox_db_lock);
|
||||
VERBOSE("MBOX: No free command descriptors available\n");
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static inline void mailbox_free_cmd_desc(sdm_command_t *cmd_desc)
|
||||
{
|
||||
if (cmd_desc == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
spin_lock(&mbox_db_lock);
|
||||
memset((void *)cmd_desc, 0, sizeof(sdm_command_t));
|
||||
spin_unlock(&mbox_db_lock);
|
||||
}
|
||||
|
||||
static inline void mailbox_free_resp_desc(uint8_t index)
|
||||
{
|
||||
if (index >= MBOX_SVC_RESP_QUEUE_SIZE) {
|
||||
return;
|
||||
}
|
||||
|
||||
spin_lock(&mbox_db_lock);
|
||||
memset((void *)&mbox_svc.resp_queue[index], 0, sizeof(sdm_response_t));
|
||||
spin_unlock(&mbox_db_lock);
|
||||
}
|
||||
|
||||
/*
|
||||
* This function serves the V1 _sync_read and _async_read functionality, and it
|
||||
* is introduced as part of V3 framework to keep backward compatible with V1
|
||||
* clients.
|
||||
*/
|
||||
static int mailbox_read_response_v3(uint8_t client_id, uint8_t *job_id,
|
||||
uint32_t *header, uint32_t *resp,
|
||||
uint32_t *resp_len,
|
||||
uint8_t ignore_client_id)
|
||||
{
|
||||
uint8_t di = 0U;
|
||||
int status = MBOX_RET_OK;
|
||||
sdm_response_t *resp_desc = NULL;
|
||||
sdm_command_t *cmd_desc = NULL;
|
||||
|
||||
/*
|
||||
* In the V1, the client ID is always MBOX_ATF_CLIENT_ID and in this
|
||||
* routine we will collect the response which only belongs to this
|
||||
* client ID. So safe to ignore this input.
|
||||
*/
|
||||
(void)ignore_client_id;
|
||||
|
||||
/* Clear the SDM doorbell interrupt */
|
||||
if (mmio_read_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM) == 1U)
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM, 0U);
|
||||
|
||||
/* Fill the command descriptor index and get the same */
|
||||
status = mailbox_fill_cmd_desc(client_id, async_v1_job_id, resp);
|
||||
if (status != MBOX_RET_OK) {
|
||||
return status;
|
||||
}
|
||||
|
||||
cmd_desc = mailbox_get_cmd_desc(client_id, async_v1_job_id);
|
||||
|
||||
/* Get the response from SDM, just go through one cycle */
|
||||
status = mailbox_response_handler_fsm();
|
||||
if (status != MBOX_RET_OK) {
|
||||
mailbox_free_cmd_desc(cmd_desc);
|
||||
*resp_len = 0U;
|
||||
return status;
|
||||
}
|
||||
|
||||
/* Check the local response queue with the given client ID */
|
||||
resp_desc = mailbox_get_resp_desc_cid(client_id, &di);
|
||||
if (resp_desc == NULL) {
|
||||
mailbox_free_cmd_desc(cmd_desc);
|
||||
*resp_len = 0U;
|
||||
return MBOX_NO_RESPONSE;
|
||||
}
|
||||
|
||||
/* Update the received mailbox response length, job ID and header */
|
||||
*job_id = resp_desc->job_id;
|
||||
*resp_len = resp_desc->rcvd_resp_len;
|
||||
if (header != NULL) {
|
||||
*header = resp_desc->header;
|
||||
}
|
||||
|
||||
/* Check the mailbox response error code */
|
||||
if (MBOX_RESP_ERR(resp_desc->header) > 0U) {
|
||||
INFO("MBOX: Error in async response: %x\n", resp_desc->header);
|
||||
status = -MBOX_RESP_ERR(resp_desc->header);
|
||||
}
|
||||
|
||||
/* Free up the response and command descriptors */
|
||||
mailbox_free_resp_desc(di);
|
||||
mailbox_free_cmd_desc(cmd_desc);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
int mailbox_send_cmd_async_v3(uint8_t client_id, uint8_t job_id, uint32_t cmd,
|
||||
uint32_t *args, uint32_t args_len, uint8_t cmd_flag,
|
||||
sdm_command_callback cb, uint32_t *cb_args,
|
||||
uint32_t cb_args_len)
|
||||
{
|
||||
int status = 0;
|
||||
sdm_command_t *cmd_desc = NULL;
|
||||
|
||||
VERBOSE("MBOX: cid: %d, jid: %d, cmd: %d, cmd_flag: %d\n",
|
||||
client_id, job_id, cmd, cmd_flag);
|
||||
|
||||
if (IS_CMD_SET(cmd_flag, URGENT)) {
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_URG, cmd);
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_TO_SDM, 1U);
|
||||
} else {
|
||||
/* Get a free command descriptor */
|
||||
cmd_desc = mailbox_get_free_cmd_desc();
|
||||
if (cmd_desc == NULL) {
|
||||
return MBOX_BUFFER_FULL;
|
||||
}
|
||||
|
||||
/* Record all the given values for the command. */
|
||||
cmd_desc->client_id = client_id;
|
||||
cmd_desc->job_id = job_id;
|
||||
cmd_desc->cb = cb;
|
||||
cmd_desc->cb_args = cb_args;
|
||||
cmd_desc->cb_args_len = cb_args_len;
|
||||
|
||||
/* Push the command to mailbox FIFO */
|
||||
status = fill_mailbox_circular_buffer(
|
||||
MBOX_FRAME_CMD_HEADER(client_id, job_id,
|
||||
args_len, IS_CMD_SET(cmd_flag, INDIRECT), cmd),
|
||||
args,
|
||||
args_len);
|
||||
|
||||
if (status != MBOX_RET_OK) {
|
||||
INFO("MBOX: Failed to push the command to mailbox FIFO\n");
|
||||
/* Free the command descriptor. */
|
||||
mailbox_free_cmd_desc(cmd_desc);
|
||||
}
|
||||
}
|
||||
|
||||
INFO("MBOX: %s: status: %d\n", __func__, status);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
static int mailbox_poll_response_v3(uint8_t client_id, uint8_t job_id,
|
||||
uint32_t *resp, unsigned int *resp_len,
|
||||
uint32_t urgent)
|
||||
{
|
||||
unsigned int timeout = 40U;
|
||||
unsigned int sdm_loop = 255U;
|
||||
bool is_cmd_desc_fill = false;
|
||||
uint8_t di = 0U;
|
||||
sdm_response_t *resp_desc = NULL;
|
||||
sdm_command_t *cmd_desc = NULL;
|
||||
|
||||
while (sdm_loop != 0U) {
|
||||
do {
|
||||
if (mmio_read_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM)
|
||||
== 1U) {
|
||||
break;
|
||||
}
|
||||
mdelay(10U);
|
||||
} while (--timeout != 0U);
|
||||
|
||||
if (timeout == 0U) {
|
||||
INFO("%s: Timed out waiting for SDM intr\n", __func__);
|
||||
break;
|
||||
}
|
||||
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM, 0U);
|
||||
|
||||
if ((urgent & 1U) != 0U) {
|
||||
mdelay(5U);
|
||||
if ((mmio_read_32(MBOX_OFFSET + MBOX_STATUS) &
|
||||
MBOX_STATUS_UA_MASK) ^
|
||||
(urgent & MBOX_STATUS_UA_MASK)) {
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_URG, 0U);
|
||||
return MBOX_RET_OK;
|
||||
}
|
||||
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_URG, 0U);
|
||||
ERROR("MBOX: Mailbox did not get UA");
|
||||
return MBOX_RET_ERROR;
|
||||
}
|
||||
|
||||
/* Fill the command descriptor index and get the same. */
|
||||
if (!is_cmd_desc_fill) {
|
||||
if (mailbox_fill_cmd_desc(client_id, job_id, resp) !=
|
||||
MBOX_RET_OK) {
|
||||
return MBOX_BUFFER_FULL;
|
||||
}
|
||||
|
||||
cmd_desc = mailbox_get_cmd_desc(client_id, job_id);
|
||||
is_cmd_desc_fill = true;
|
||||
}
|
||||
|
||||
/* Since it is sync call, will try to read till it time out */
|
||||
(void)mailbox_response_handler_fsm();
|
||||
|
||||
/* Check the response queue with the given client ID and job ID */
|
||||
resp_desc = mailbox_get_resp_desc(client_id, job_id, &di);
|
||||
if (resp_desc != NULL) {
|
||||
VERBOSE("%s: Resp received for cid %d, jid %d\n",
|
||||
__func__, resp_desc->client_id, resp_desc->job_id);
|
||||
|
||||
uint16_t header = resp_desc->header;
|
||||
|
||||
/* Update the return response length */
|
||||
if (resp_len != NULL) {
|
||||
*resp_len = resp_desc->rcvd_resp_len;
|
||||
}
|
||||
|
||||
/* Free the response and command descriptor */
|
||||
mailbox_free_resp_desc(di);
|
||||
mailbox_free_cmd_desc(cmd_desc);
|
||||
|
||||
if (MBOX_RESP_ERR(header) > 0U) {
|
||||
INFO("%s: SDM err code: 0x%x\n", __func__,
|
||||
MBOX_RESP_ERR(header));
|
||||
return -MBOX_RESP_ERR(header);
|
||||
}
|
||||
|
||||
VERBOSE("%s: MBOX_RET_OK\n", __func__);
|
||||
return MBOX_RET_OK;
|
||||
}
|
||||
sdm_loop--;
|
||||
}
|
||||
|
||||
INFO("%s: Timed out waiting for SDM\n", __func__);
|
||||
return MBOX_TIMEOUT;
|
||||
}
|
||||
|
||||
/* SDM response parser handler state machine. */
|
||||
static void mailbox_response_parser(void)
|
||||
{
|
||||
int di = -1; /* Descriptor index */
|
||||
uint32_t rin;
|
||||
uint32_t rout;
|
||||
|
||||
switch (mbox_svc.next_resp_state) {
|
||||
case SRS_WAIT_FOR_RESP:
|
||||
{
|
||||
mbox_svc.resp_state = SRS_WAIT_FOR_RESP;
|
||||
|
||||
rin = mmio_read_32(MBOX_OFFSET + MBOX_RIN);
|
||||
rout = mmio_read_32(MBOX_OFFSET + MBOX_ROUT);
|
||||
if (rin != rout) {
|
||||
mbox_svc.next_resp_state = SRS_WAIT_FOR_HEADER;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case SRS_WAIT_FOR_HEADER:
|
||||
{
|
||||
mbox_svc.resp_state = SRS_WAIT_FOR_HEADER;
|
||||
uint32_t resp_hdr;
|
||||
uint8_t trans_id = 0U;
|
||||
|
||||
rin = mmio_read_32(MBOX_OFFSET + MBOX_RIN);
|
||||
rout = mmio_read_32(MBOX_OFFSET + MBOX_ROUT);
|
||||
if (rin != rout) {
|
||||
/* Read the header and dequeue from the queue. */
|
||||
resp_hdr = mmio_read_32(MBOX_ENTRY_TO_ADDR(RESP, (rout)++));
|
||||
rout %= MBOX_RESP_BUFFER_SIZE;
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_ROUT, rout);
|
||||
|
||||
/* Allocate a new response descriptor */
|
||||
di = mailbox_get_free_resp_desc();
|
||||
if (di != -1) {
|
||||
mbox_svc.curr_di = di;
|
||||
mbox_svc.resp_queue[di].header = resp_hdr;
|
||||
mbox_svc.resp_queue[di].client_id = MBOX_RESP_CLIENT_ID(resp_hdr);
|
||||
mbox_svc.resp_queue[di].job_id = MBOX_RESP_JOB_ID(resp_hdr);
|
||||
mbox_svc.resp_queue[di].resp_len = MBOX_RESP_LEN(resp_hdr);
|
||||
mbox_svc.resp_queue[di].flags |= (FLAG_SDM_RESPONSE_IS_USED |
|
||||
FLAG_SDM_RESPONSE_IS_IN_PROGRESS);
|
||||
mbox_svc.resp_queue[di].err_code = MBOX_RESP_ERR(resp_hdr);
|
||||
trans_id = MBOX_RESP_TRANSACTION_ID(resp_hdr);
|
||||
|
||||
VERBOSE("MBOX: Resp Hdr: cid %d, jid %d, len %d, err_code 0x%x\n",
|
||||
mbox_svc.resp_queue[di].client_id,
|
||||
mbox_svc.resp_queue[di].job_id,
|
||||
mbox_svc.resp_queue[di].resp_len,
|
||||
mbox_svc.resp_queue[di].err_code);
|
||||
|
||||
/* Check if the response is an argument response */
|
||||
if (mbox_svc.resp_queue[di].resp_len > 0) {
|
||||
mbox_svc.next_resp_state = SRS_WAIT_FOR_ARGUMENTS;
|
||||
} else {
|
||||
VERBOSE("MBOX: Received complete response with no args\n");
|
||||
/* Non argument response, done */
|
||||
mbox_svc.resp_queue[mbox_svc.curr_di].flags |=
|
||||
FLAG_SDM_RESPONSE_IS_VALID;
|
||||
|
||||
/* Go back to waiting for new response */
|
||||
mbox_svc.next_resp_state = SRS_WAIT_FOR_RESP;
|
||||
mbox_svc.curr_di = -1;
|
||||
|
||||
/* Mark the transaction ID as received */
|
||||
spin_lock(&mbox_db_lock);
|
||||
mbox_svc.received_bitmap[trans_id / MBOX_TID_BITMAP_SIZE] |=
|
||||
(1ULL << (trans_id % MBOX_TID_BITMAP_SIZE));
|
||||
spin_unlock(&mbox_db_lock);
|
||||
}
|
||||
} else {
|
||||
mbox_svc.next_resp_state = SRS_SYNC_ERROR;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case SRS_WAIT_FOR_ARGUMENTS:
|
||||
{
|
||||
mbox_svc.resp_state = SRS_WAIT_FOR_ARGUMENTS;
|
||||
uint16_t mbox_resp_len = mbox_svc.resp_queue[mbox_svc.curr_di].resp_len;
|
||||
uint32_t *read_buff = NULL;
|
||||
uint16_t read_len = 0U;
|
||||
uint16_t read_max_len = 0U;
|
||||
uint32_t timeout = 0U;
|
||||
|
||||
/* Determine where to copy the buffer. */
|
||||
sdm_command_t *cmd_desc = mailbox_get_cmd_desc(
|
||||
mbox_svc.resp_queue[mbox_svc.curr_di].client_id,
|
||||
mbox_svc.resp_queue[mbox_svc.curr_di].job_id);
|
||||
if (cmd_desc != NULL && cmd_desc->cb_args != NULL) {
|
||||
read_buff = cmd_desc->cb_args;
|
||||
read_max_len = mbox_resp_len;
|
||||
} else {
|
||||
read_buff = (uint32_t *)mbox_svc.resp_queue[mbox_svc.curr_di].resp_data;
|
||||
read_max_len = MBOX_SVC_MAX_RESP_DATA_SIZE;
|
||||
}
|
||||
|
||||
rin = mmio_read_32(MBOX_OFFSET + MBOX_RIN);
|
||||
rout = mmio_read_32(MBOX_OFFSET + MBOX_ROUT);
|
||||
|
||||
while ((read_len < mbox_resp_len) && (rin != rout) && (read_len < read_max_len)) {
|
||||
timeout = 10000U;
|
||||
|
||||
/* Copy the response data to the buffer */
|
||||
read_buff[read_len++] = mmio_read_32(MBOX_ENTRY_TO_ADDR(RESP, (rout)++));
|
||||
|
||||
VERBOSE("MBOX: 0x%x\n", read_buff[read_len - 1]);
|
||||
|
||||
/* Update the read out buffer index */
|
||||
rout %= MBOX_RESP_BUFFER_SIZE;
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_ROUT, rout);
|
||||
|
||||
/*
|
||||
* The response buffer is of 16 words size, this loop checks
|
||||
* if the response buffer is empty and if empty trigger an
|
||||
* interrupt to SDM and wait for the response buffer to fill
|
||||
*/
|
||||
do {
|
||||
if (read_len == mbox_resp_len)
|
||||
break;
|
||||
|
||||
rin = mmio_read_32(MBOX_OFFSET + MBOX_RIN);
|
||||
if (rout == rin) {
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_TO_SDM, 1U);
|
||||
udelay(100);
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
timeout--;
|
||||
} while ((read_len < mbox_resp_len) && (timeout != 0U));
|
||||
|
||||
if (timeout == 0U) {
|
||||
INFO("MBOX: Timeout waiting for response data\n");
|
||||
mbox_svc.next_resp_state = SRS_SYNC_ERROR;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Check if we have received all the arguments */
|
||||
mbox_svc.resp_queue[mbox_svc.curr_di].rcvd_resp_len = read_len;
|
||||
if (mbox_resp_len == read_len) {
|
||||
uint8_t transaction_id =
|
||||
((mbox_svc.resp_queue[mbox_svc.curr_di].client_id << 4) |
|
||||
(mbox_svc.resp_queue[mbox_svc.curr_di].job_id));
|
||||
VERBOSE("MBOX: Received all the response data len %d, transaction_id %d\n",
|
||||
read_len, transaction_id);
|
||||
|
||||
spin_lock(&mbox_db_lock);
|
||||
mbox_svc.received_bitmap[transaction_id / MBOX_TID_BITMAP_SIZE] |=
|
||||
(1ULL << (transaction_id % MBOX_TID_BITMAP_SIZE));
|
||||
spin_unlock(&mbox_db_lock);
|
||||
|
||||
mbox_svc.resp_queue[mbox_svc.curr_di].flags |= FLAG_SDM_RESPONSE_IS_VALID;
|
||||
mbox_svc.next_resp_state = SRS_WAIT_FOR_RESP;
|
||||
mbox_svc.curr_di = -1;
|
||||
} else {
|
||||
mbox_svc.next_resp_state = SRS_SYNC_ERROR;
|
||||
VERBOSE("MBOX: Received partial response data len %d, max len %d\n",
|
||||
read_len, read_max_len);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case SRS_SYNC_ERROR:
|
||||
{
|
||||
mbox_svc.resp_state = SRS_SYNC_ERROR;
|
||||
INFO("MBOX: Error in response handling\n");
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
break;
|
||||
} /* switch */
|
||||
}
|
||||
|
||||
static int mailbox_response_handler_fsm(void)
|
||||
{
|
||||
int status = MBOX_RET_OK;
|
||||
|
||||
spin_lock(&mbox_read_lock);
|
||||
/* Mailbox peripheral response parser */
|
||||
do {
|
||||
/* Iterate till the state machine transition ends */
|
||||
mailbox_response_parser();
|
||||
|
||||
/* Note down if there is any error in the response parsing */
|
||||
if (mbox_svc.next_resp_state == SRS_SYNC_ERROR) {
|
||||
status = MBOX_RET_ERROR;
|
||||
}
|
||||
|
||||
} while (mbox_svc.resp_state != mbox_svc.next_resp_state);
|
||||
spin_unlock(&mbox_read_lock);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
int mailbox_response_poll_on_intr_v3(uint8_t *client_id, uint8_t *job_id,
|
||||
uint64_t *bitmap)
|
||||
{
|
||||
uint32_t i = 0U;
|
||||
int status = MBOX_RET_OK;
|
||||
|
||||
/* Clear the SDM doorbell interrupt immediately */
|
||||
if (mmio_read_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM) == 1U) {
|
||||
mmio_write_32(MBOX_OFFSET + MBOX_DOORBELL_FROM_SDM, 0U);
|
||||
}
|
||||
|
||||
/* Check mailbox FIFO for any pending responses available to read. */
|
||||
status = mailbox_response_handler_fsm();
|
||||
if (status != MBOX_RET_OK) {
|
||||
return status;
|
||||
}
|
||||
|
||||
/*
|
||||
* Once we read the complete mailbox FIFO, let's mark up the bitmap for
|
||||
* available responses with respect to each transcation IDs.
|
||||
*/
|
||||
status = MBOX_NO_RESPONSE;
|
||||
spin_lock(&mbox_db_lock);
|
||||
for (i = 0; i < MBOX_MAX_TIDS_BITMAP; i++) {
|
||||
bitmap[i] = mbox_svc.interrupt_bitmap[i] ^ mbox_svc.received_bitmap[i];
|
||||
if (bitmap[i] != 0 && status == MBOX_NO_RESPONSE) {
|
||||
status = MBOX_RET_OK;
|
||||
}
|
||||
|
||||
mbox_svc.interrupt_bitmap[i] = mbox_svc.received_bitmap[i];
|
||||
}
|
||||
spin_unlock(&mbox_db_lock);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
int mailbox_response_poll_v3(uint8_t client_id, uint8_t job_id,
|
||||
uint32_t *ret_args, uint32_t *ret_args_len)
|
||||
{
|
||||
sdm_command_t *cmd_desc = NULL;
|
||||
sdm_response_t *resp_desc = NULL;
|
||||
uint8_t di = 0U;
|
||||
int status = MBOX_RET_OK;
|
||||
|
||||
/*
|
||||
* Let's first check the local response queue with the given
|
||||
* client ID and job ID
|
||||
*/
|
||||
resp_desc = mailbox_get_resp_desc(client_id, job_id, &di);
|
||||
if (resp_desc == NULL) {
|
||||
/* Not available in the local queue, let's read mailbox FIFO */
|
||||
status = mailbox_response_handler_fsm();
|
||||
if (status != MBOX_RET_OK) {
|
||||
return status;
|
||||
}
|
||||
|
||||
resp_desc = mailbox_get_resp_desc(client_id, job_id, &di);
|
||||
}
|
||||
cmd_desc = mailbox_get_cmd_desc(client_id, job_id);
|
||||
|
||||
if (cmd_desc != NULL && resp_desc != NULL) {
|
||||
VERBOSE("MBOX: Resp found for cid %d, jid %d\n", client_id, job_id);
|
||||
|
||||
/* Command callback function */
|
||||
*ret_args_len = cmd_desc->cb(resp_desc, cmd_desc, ret_args);
|
||||
|
||||
/* Free the command and response descriptors. */
|
||||
mailbox_free_cmd_desc(cmd_desc);
|
||||
mailbox_free_resp_desc(di);
|
||||
|
||||
return MBOX_RET_OK;
|
||||
}
|
||||
|
||||
INFO("MBOX: No resp found for cid: %d, jid: %d\n", client_id, job_id);
|
||||
|
||||
return MBOX_NO_RESPONSE;
|
||||
}
|
||||
|
||||
void mailbox_init_v3(void)
|
||||
{
|
||||
uint32_t count;
|
||||
|
||||
memset((void *)&mbox_svc, 0, sizeof(mbox_svc));
|
||||
|
||||
mbox_svc.next_resp_state = SRS_WAIT_FOR_RESP;
|
||||
mbox_svc.resp_state = SRS_WAIT_FOR_RESP;
|
||||
|
||||
/* Free all entries from the response queue. */
|
||||
for (count = 0; count < MBOX_SVC_RESP_QUEUE_SIZE; count++) {
|
||||
mbox_svc.resp_queue[count].flags = 0;
|
||||
}
|
||||
|
||||
/* Free all entries from the command queue. */
|
||||
for (count = 0; count < MBOX_SVC_CMD_QUEUE_SIZE; count++) {
|
||||
mbox_svc.cmd_queue[count].flags = 0;
|
||||
}
|
||||
|
||||
mbox_svc.curr_di = -1;
|
||||
}
|
||||
#endif /* #if SIP_SVC_V3 */
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -1,5 +1,6 @@
|
|||
/*
|
||||
* Copyright (c) 2020-2022, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -115,6 +116,16 @@ void bl31_platform_setup(void)
|
|||
mmio_write_64(PLAT_CPU_RELEASE_ADDR,
|
||||
(uint64_t)plat_secondary_cpus_bl31_entry);
|
||||
|
||||
#if SIP_SVC_V3
|
||||
/*
|
||||
* Re-initialize the mailbox to include V3 specific routines.
|
||||
* In V3, this re-initialize is required because prior to BL31, U-Boot
|
||||
* SPL has its own mailbox settings and this initialization will
|
||||
* override to those settings as required by the V3 framework.
|
||||
*/
|
||||
mailbox_init();
|
||||
#endif
|
||||
|
||||
mailbox_hps_stage_notify(HPS_EXECUTION_STATE_SSBL);
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
/*
|
||||
* Copyright (c) 2019-2020, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2019-2022, Intel Corporation. All rights reserved.
|
||||
* Copyright (c) 2025, Altera Corporation. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -122,6 +123,16 @@ void bl31_platform_setup(void)
|
|||
mmio_write_64(PLAT_CPU_RELEASE_ADDR,
|
||||
(uint64_t)plat_secondary_cpus_bl31_entry);
|
||||
|
||||
#if SIP_SVC_V3
|
||||
/*
|
||||
* Re-initialize the mailbox to include V3 specific routines.
|
||||
* In V3, this re-initialize is required because prior to BL31, U-Boot
|
||||
* SPL has its own mailbox settings and this initialization will
|
||||
* override to those settings as required by the V3 framework.
|
||||
*/
|
||||
mailbox_init();
|
||||
#endif
|
||||
|
||||
mailbox_hps_stage_notify(HPS_EXECUTION_STATE_SSBL);
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue