SPM: Separate interrupt codes to new interrupt.[h/c]
Change-Id: I67442ff712b92ec9404ed473975feec46f66ea06
Signed-off-by: Kevin Peng <kevin.peng@arm.com>
diff --git a/platform/CMakeLists.txt b/platform/CMakeLists.txt
index f6a9754..03b7a25 100755
--- a/platform/CMakeLists.txt
+++ b/platform/CMakeLists.txt
@@ -73,6 +73,7 @@
tfm_secure_api
tfm_arch
tfm_partition_defs
+ tfm_spm
$<$<BOOL:${PLATFORM_DEFAULT_ATTEST_HAL}>:tfm_sprt>
$<$<AND:$<BOOL:${TFM_PARTITION_CRYPTO}>,$<BOOL:${PLATFORM_DEFAULT_CRYPTO_KEYS}>>:crypto_service_mbedtls>
)
diff --git a/platform/ext/target/arm/corstone1000/CMakeLists.txt b/platform/ext/target/arm/corstone1000/CMakeLists.txt
index c0389cb..1fe0fe8 100644
--- a/platform/ext/target/arm/corstone1000/CMakeLists.txt
+++ b/platform/ext/target/arm/corstone1000/CMakeLists.txt
@@ -89,11 +89,6 @@
)
endif()
-target_link_libraries(platform_s
- PUBLIC
- tfm_spm
-)
-
target_compile_definitions(platform_s
PRIVATE
$<$<BOOL:${PLATFORM_IS_FVP}>:PLATFORM_IS_FVP>
diff --git a/platform/ext/target/arm/mps2/an519/tfm_interrupts.c b/platform/ext/target/arm/mps2/an519/tfm_interrupts.c
index 3a50303..83caa02 100644
--- a/platform/ext/target/arm/mps2/an519/tfm_interrupts.c
+++ b/platform/ext/target/arm/mps2/an519/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_load_info_t *p_tfm_timer0_irq_ldinf = NULL;
diff --git a/platform/ext/target/arm/mps2/an521/tfm_interrupts.c b/platform/ext/target/arm/mps2/an521/tfm_interrupts.c
index 5bdfd84..ea299db 100644
--- a/platform/ext/target/arm/mps2/an521/tfm_interrupts.c
+++ b/platform/ext/target/arm/mps2/an521/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/arm/mps3/an524/tfm_interrupts.c b/platform/ext/target/arm/mps3/an524/tfm_interrupts.c
index 5bdfd84..ea299db 100644
--- a/platform/ext/target/arm/mps3/an524/tfm_interrupts.c
+++ b/platform/ext/target/arm/mps3/an524/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/arm/mps3/an547/tfm_interrupts.c b/platform/ext/target/arm/mps3/an547/tfm_interrupts.c
index 3ca0aac..aadb040 100644
--- a/platform/ext/target/arm/mps3/an547/tfm_interrupts.c
+++ b/platform/ext/target/arm/mps3/an547/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/arm/mps3/an552/tfm_interrupts.c b/platform/ext/target/arm/mps3/an552/tfm_interrupts.c
index 3ca0aac..aadb040 100644
--- a/platform/ext/target/arm/mps3/an552/tfm_interrupts.c
+++ b/platform/ext/target/arm/mps3/an552/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/arm/mps3/corstone_polaris/tfm_interrupts.c b/platform/ext/target/arm/mps3/corstone_polaris/tfm_interrupts.c
index 3ca0aac..aadb040 100644
--- a/platform/ext/target/arm/mps3/corstone_polaris/tfm_interrupts.c
+++ b/platform/ext/target/arm/mps3/corstone_polaris/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/arm/musca_b1/secure_enclave/CMakeLists.txt b/platform/ext/target/arm/musca_b1/secure_enclave/CMakeLists.txt
index a70d90e..19db9a7 100644
--- a/platform/ext/target/arm/musca_b1/secure_enclave/CMakeLists.txt
+++ b/platform/ext/target/arm/musca_b1/secure_enclave/CMakeLists.txt
@@ -86,10 +86,6 @@
$<$<BOOL:${TFM_PARTITION_PLATFORM}>:${CMAKE_CURRENT_SOURCE_DIR}/services/src/tfm_platform_system.c>
)
-target_link_libraries(platform_s
- PUBLIC
- tfm_spm
-)
#========================= Platform Non-Secure ================================#
# FIXME: platform_ns must have at least 1 source, even if it is not used
diff --git a/platform/ext/target/arm/musca_b1/sse_200/tfm_interrupts.c b/platform/ext/target/arm/musca_b1/sse_200/tfm_interrupts.c
index 5bdfd84..ea299db 100644
--- a/platform/ext/target/arm/musca_b1/sse_200/tfm_interrupts.c
+++ b/platform/ext/target/arm/musca_b1/sse_200/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/arm/musca_s1/tfm_interrupts.c b/platform/ext/target/arm/musca_s1/tfm_interrupts.c
index 5bdfd84..ea299db 100644
--- a/platform/ext/target/arm/musca_s1/tfm_interrupts.c
+++ b/platform/ext/target/arm/musca_s1/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/cypress/psoc64/CMakeLists.txt b/platform/ext/target/cypress/psoc64/CMakeLists.txt
index 950ebb3..4779e3e 100644
--- a/platform/ext/target/cypress/psoc64/CMakeLists.txt
+++ b/platform/ext/target/cypress/psoc64/CMakeLists.txt
@@ -141,7 +141,6 @@
target_link_libraries(platform_s
PRIVATE
- tfm_spm
${P64_UTILS_LIB_TARGET}
)
diff --git a/platform/ext/target/cypress/psoc64/tfm_interrupts.c b/platform/ext/target/cypress/psoc64/tfm_interrupts.c
index 4591ced..24f58ab 100644
--- a/platform/ext/target/cypress/psoc64/tfm_interrupts.c
+++ b/platform/ext/target/cypress/psoc64/tfm_interrupts.c
@@ -11,6 +11,7 @@
#include "spm_ipc.h"
#include "tfm_hal_interrupt.h"
#include "tfm_peripherals_def.h"
+#include "ffm/interrupt.h"
#include "load/interrupt_defs.h"
static struct irq_t timer0_irq = {0};
diff --git a/platform/ext/target/nordic_nrf/common/nrf5340/tfm_interrupts.c b/platform/ext/target/nordic_nrf/common/nrf5340/tfm_interrupts.c
index d80bf20..4e2db5a 100644
--- a/platform/ext/target/nordic_nrf/common/nrf5340/tfm_interrupts.c
+++ b/platform/ext/target/nordic_nrf/common/nrf5340/tfm_interrupts.c
@@ -13,6 +13,7 @@
#include "tfm_peripherals_def.h"
#include "tfm_peripherals_config.h"
#include "load/interrupt_defs.h"
+#include "ffm/interrupt.h"
#include "tfm_spm_hal.h"
diff --git a/platform/ext/target/nordic_nrf/common/nrf9160/tfm_interrupts.c b/platform/ext/target/nordic_nrf/common/nrf9160/tfm_interrupts.c
index cb414f7..5982340 100644
--- a/platform/ext/target/nordic_nrf/common/nrf9160/tfm_interrupts.c
+++ b/platform/ext/target/nordic_nrf/common/nrf9160/tfm_interrupts.c
@@ -13,6 +13,7 @@
#include "tfm_peripherals_def.h"
#include "tfm_peripherals_config.h"
#include "load/interrupt_defs.h"
+#include "ffm/interrupt.h"
#include "tfm_spm_hal.h"
diff --git a/secure_fw/spm/CMakeLists.txt b/secure_fw/spm/CMakeLists.txt
index 3686ad1..f6e71db 100755
--- a/secure_fw/spm/CMakeLists.txt
+++ b/secure_fw/spm/CMakeLists.txt
@@ -54,6 +54,7 @@
$<$<BOOL:${TFM_PSA_API}>:cmsis_psa/static_load.c>
$<$<BOOL:${TFM_PSA_API}>:ffm/psa_api.c>
$<$<BOOL:${TFM_PSA_API}>:ffm/backend.c>
+ $<$<BOOL:${TFM_PSA_API}>:ffm/interrupt.c>
$<$<BOOL:${TFM_PSA_API}>:cmsis_psa/tfm_core_svcalls_ipc.c>
$<$<AND:$<BOOL:${TFM_PSA_API}>,$<NOT:$<BOOL:${TFM_MULTI_CORE_TOPOLOGY}>>>:cmsis_psa/tfm_nspm_ipc.c>
$<$<BOOL:${TFM_PSA_API}>:cmsis_psa/tfm_pools.c>
diff --git a/secure_fw/spm/cmsis_psa/spm_ipc.c b/secure_fw/spm/cmsis_psa/spm_ipc.c
index b539d98..5c7a35e 100755
--- a/secure_fw/spm/cmsis_psa/spm_ipc.c
+++ b/secure_fw/spm/cmsis_psa/spm_ipc.c
@@ -774,71 +774,3 @@
CRITICAL_SECTION_LEAVE(cs_assert);
}
-
-__attribute__((naked))
-static psa_flih_result_t tfm_flih_deprivileged_handling(void *p_pt,
- uintptr_t fn_flih,
- void *p_context_ctrl)
-{
- __ASM volatile("SVC %0 \n"
- "BX LR \n"
- : : "I" (TFM_SVC_PREPARE_DEPRIV_FLIH));
-}
-
-void spm_handle_interrupt(void *p_pt, struct irq_load_info_t *p_ildi)
-{
- psa_flih_result_t flih_result;
- struct partition_t *p_part;
-
- if (!p_pt || !p_ildi) {
- tfm_core_panic();
- }
-
- p_part = (struct partition_t *)p_pt;
-
- if (p_ildi->pid != p_part->p_ldinf->pid) {
- tfm_core_panic();
- }
-
- if (p_ildi->flih_func == NULL) {
- /* SLIH Model Handling */
- tfm_hal_irq_disable(p_ildi->source);
- flih_result = PSA_FLIH_SIGNAL;
- } else {
- /* FLIH Model Handling */
- if (tfm_spm_partition_get_privileged_mode(p_part->p_ldinf->flags) ==
- TFM_PARTITION_PRIVILEGED_MODE) {
- flih_result = p_ildi->flih_func();
- } else {
- flih_result = tfm_flih_deprivileged_handling(
- p_part,
- (uintptr_t)p_ildi->flih_func,
- CURRENT_THREAD->p_context_ctrl);
- }
- }
-
- if (flih_result == PSA_FLIH_SIGNAL) {
- spm_assert_signal(p_pt, p_ildi->signal);
- }
-}
-
-struct irq_load_info_t *get_irq_info_for_signal(
- const struct partition_load_info_t *p_ldinf,
- psa_signal_t signal)
-{
- size_t i;
- struct irq_load_info_t *irq_info;
-
- if (!IS_ONLY_ONE_BIT_IN_UINT32(signal)) {
- return NULL;
- }
-
- irq_info = (struct irq_load_info_t *)LOAD_INFO_IRQ(p_ldinf);
- for (i = 0; i < p_ldinf->nirqs; i++) {
- if (irq_info[i].signal == signal) {
- return &irq_info[i];
- }
- }
-
- return NULL;
-}
diff --git a/secure_fw/spm/cmsis_psa/spm_ipc.h b/secure_fw/spm/cmsis_psa/spm_ipc.h
index 3e8e4a5..2d4fe98 100644
--- a/secure_fw/spm/cmsis_psa/spm_ipc.h
+++ b/secure_fw/spm/cmsis_psa/spm_ipc.h
@@ -446,36 +446,6 @@
*/
void spm_assert_signal(void *p_pt, psa_signal_t signal);
-/**
- * \brief Return the IRQ load info context pointer associated with a signal
- *
- * \param[in] p_ldinf The load info of the partition in which we look
- * for the signal.
- * \param[in] signal The signal to query for.
- *
- * \retval NULL if one of more the following are true:
- * - the \ref signal indicates more than one signal
- * - the \ref signal does not belong to the
- * partition.
- * \retval Any other value The load info pointer associated with the signal
- */
-struct irq_load_info_t *get_irq_info_for_signal(
- const struct partition_load_info_t *p_ldinf,
- psa_signal_t signal);
-
-/**
- * \brief Entry of Secure interrupt handler. Platforms can call this function to
- * handle individual interrupts.
- *
- * \param[in] p_pt The owner Partition of the interrupt to handle
- * \param[in] p_ildi The irq_load_info_t struct of the interrupt to handle
- *
- * Note:
- * The input parameters are maintained by platforms and they must be init-ed
- * in the interrupt init functions.
- */
-void spm_handle_interrupt(void *p_pt, struct irq_load_info_t *p_ildi);
-
#ifdef CONFIG_TFM_PSA_API_THREAD_CALL
/*
diff --git a/secure_fw/spm/cmsis_psa/tfm_core_svcalls_ipc.c b/secure_fw/spm/cmsis_psa/tfm_core_svcalls_ipc.c
index 64a941c..83fc619 100644
--- a/secure_fw/spm/cmsis_psa/tfm_core_svcalls_ipc.c
+++ b/secure_fw/spm/cmsis_psa/tfm_core_svcalls_ipc.c
@@ -16,6 +16,7 @@
#include "tfm_svcalls.h"
#include "utilities.h"
#include "load/spm_load_api.h"
+#include "ffm/interrupt.h"
#include "ffm/tfm_boot_data.h"
#include "ffm/psa_api.h"
#include "tfm_hal_isolation.h"
@@ -112,84 +113,6 @@
return status;
}
-extern void tfm_flih_func_return(psa_flih_result_t result);
-
-/*
- * Prepare execution context for deprivileged FLIH functions
- * svc_args: IRQ owner partition_t pointer, flih_func, current thread data
- */
-uint32_t tfm_flih_prepare_depriv_flih(uint32_t *svc_args)
-{
- struct partition_t *p_curr_sp;
- struct partition_t *p_owner_sp = (struct partition_t *)svc_args[0];
- uintptr_t sp_limit, stack;
- struct context_ctrl_t flih_ctx_ctrl;
-
- /* Come too early before runtime setup, should not happen. */
- if (!CURRENT_THREAD) {
- tfm_core_panic();
- }
-
- p_curr_sp = GET_CTX_OWNER(CURRENT_THREAD->p_context_ctrl);
- sp_limit =
- ((struct context_ctrl_t *)p_owner_sp->thrd.p_context_ctrl)->sp_limit;
-
- if (p_owner_sp == p_curr_sp) {
- stack = (uintptr_t)__get_PSP();
- } else {
- stack = ((struct context_ctrl_t *)p_owner_sp->thrd.p_context_ctrl)->sp;
-
- if (p_owner_sp->p_boundaries != p_curr_sp->p_boundaries) {
- tfm_hal_update_boundaries(p_owner_sp->p_ldinf,
- p_owner_sp->p_boundaries);
- }
-
- /*
- * CURRENT_THREAD->p_context_ctrl is the svc_args[2] on MSP, safe to
- * update it. It is only used to track the owner of the thread data,
- * i.e. the partition that has been interrupted.
- */
- THRD_UPDATE_CUR_CTXCTRL(&(p_owner_sp->ctx_ctrl));
- }
-
- tfm_arch_init_context(&flih_ctx_ctrl,
- (uintptr_t)svc_args[1], NULL,
- (uintptr_t)tfm_flih_func_return,
- sp_limit, stack);
-
- (void)tfm_arch_refresh_hardware_context(&flih_ctx_ctrl);
-
- return flih_ctx_ctrl.exc_ret;
-}
-
-/* Go back to ISR from FLIH functions */
-uint32_t tfm_flih_return_to_isr(psa_flih_result_t result, uint32_t *msp)
-{
- struct partition_t *p_prev_sp, *p_owner_sp;
- struct context_flih_ret_t *p_ctx_flih_ret =
- (struct context_flih_ret_t *)msp;
-
- p_prev_sp = GET_CTX_OWNER(p_ctx_flih_ret->state_ctx.r2);
- p_owner_sp = GET_CTX_OWNER(CURRENT_THREAD->p_context_ctrl);
-
- if (p_owner_sp->p_boundaries != p_prev_sp->p_boundaries) {
- tfm_hal_update_boundaries(p_prev_sp->p_ldinf,
- p_prev_sp->p_boundaries);
- }
-
- /* Restore context pointer */
- THRD_UPDATE_CUR_CTXCTRL(p_ctx_flih_ret->state_ctx.r2);
-
- tfm_arch_set_psplim(
- ((struct context_ctrl_t *)CURRENT_THREAD->p_context_ctrl)->sp_limit);
- __set_PSP(p_ctx_flih_ret->psp);
-
- /* Set FLIH result to the ISR */
- p_ctx_flih_ret->state_ctx.r0 = (uint32_t)result;
-
- return p_ctx_flih_ret->exc_ret;
-}
-
uint32_t tfm_core_svc_handler(uint32_t *msp, uint32_t exc_return,
uint32_t *psp)
{
diff --git a/secure_fw/spm/ffm/interrupt.c b/secure_fw/spm/ffm/interrupt.c
new file mode 100644
index 0000000..a9419cb
--- /dev/null
+++ b/secure_fw/spm/ffm/interrupt.c
@@ -0,0 +1,160 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include "interrupt.h"
+
+#include "bitops.h"
+#include "spm_ipc.h"
+#include "tfm_arch.h"
+#include "tfm_hal_interrupt.h"
+#include "tfm_hal_isolation.h"
+#include "thread.h"
+#include "utilities.h"
+
+#include "load/spm_load_api.h"
+
+__attribute__((naked))
+static psa_flih_result_t tfm_flih_deprivileged_handling(void *p_pt,
+ uintptr_t fn_flih,
+ void *p_context_ctrl)
+{
+ __ASM volatile("SVC %0 \n"
+ "BX LR \n"
+ : : "I" (TFM_SVC_PREPARE_DEPRIV_FLIH));
+}
+
+struct irq_load_info_t *get_irq_info_for_signal(
+ const struct partition_load_info_t *p_ldinf,
+ psa_signal_t signal)
+{
+ size_t i;
+ struct irq_load_info_t *irq_info;
+
+ if (!IS_ONLY_ONE_BIT_IN_UINT32(signal)) {
+ return NULL;
+ }
+
+ irq_info = (struct irq_load_info_t *)LOAD_INFO_IRQ(p_ldinf);
+ for (i = 0; i < p_ldinf->nirqs; i++) {
+ if (irq_info[i].signal == signal) {
+ return &irq_info[i];
+ }
+ }
+
+ return NULL;
+}
+
+extern void tfm_flih_func_return(psa_flih_result_t result);
+
+uint32_t tfm_flih_prepare_depriv_flih(uint32_t *svc_args)
+{
+ struct partition_t *p_curr_sp;
+ struct partition_t *p_owner_sp = (struct partition_t *)svc_args[0];
+ uintptr_t sp_limit, stack;
+ struct context_ctrl_t flih_ctx_ctrl;
+
+ /* Come too early before runtime setup, should not happen. */
+ if (!CURRENT_THREAD) {
+ tfm_core_panic();
+ }
+
+ p_curr_sp = GET_CTX_OWNER(CURRENT_THREAD->p_context_ctrl);
+ sp_limit =
+ ((struct context_ctrl_t *)p_owner_sp->thrd.p_context_ctrl)->sp_limit;
+
+ if (p_owner_sp == p_curr_sp) {
+ stack = (uintptr_t)__get_PSP();
+ } else {
+ stack = ((struct context_ctrl_t *)p_owner_sp->thrd.p_context_ctrl)->sp;
+
+ if (p_owner_sp->p_boundaries != p_curr_sp->p_boundaries) {
+ tfm_hal_update_boundaries(p_owner_sp->p_ldinf,
+ p_owner_sp->p_boundaries);
+ }
+
+ /*
+ * CURRENT_THREAD->p_context_ctrl is the svc_args[2] on MSP, safe to
+ * update it. It is only used to track the owner of the thread data,
+ * i.e. the partition that has been interrupted.
+ */
+ THRD_UPDATE_CUR_CTXCTRL(&(p_owner_sp->ctx_ctrl));
+ }
+
+ tfm_arch_init_context(&flih_ctx_ctrl,
+ (uintptr_t)svc_args[1], NULL,
+ (uintptr_t)tfm_flih_func_return,
+ sp_limit, stack);
+
+ (void)tfm_arch_refresh_hardware_context(&flih_ctx_ctrl);
+
+ return flih_ctx_ctrl.exc_ret;
+}
+
+/* Go back to ISR from FLIH functions */
+uint32_t tfm_flih_return_to_isr(psa_flih_result_t result, uint32_t *msp)
+{
+ struct partition_t *p_prev_sp, *p_owner_sp;
+ struct context_flih_ret_t *p_ctx_flih_ret =
+ (struct context_flih_ret_t *)msp;
+
+ p_prev_sp = GET_CTX_OWNER(p_ctx_flih_ret->state_ctx.r2);
+ p_owner_sp = GET_CTX_OWNER(CURRENT_THREAD->p_context_ctrl);
+
+ if (p_owner_sp->p_boundaries != p_prev_sp->p_boundaries) {
+ tfm_hal_update_boundaries(p_prev_sp->p_ldinf,
+ p_prev_sp->p_boundaries);
+ }
+
+ /* Restore context pointer */
+ THRD_UPDATE_CUR_CTXCTRL(p_ctx_flih_ret->state_ctx.r2);
+
+ tfm_arch_set_psplim(
+ ((struct context_ctrl_t *)CURRENT_THREAD->p_context_ctrl)->sp_limit);
+ __set_PSP(p_ctx_flih_ret->psp);
+
+ /* Set FLIH result to the ISR */
+ p_ctx_flih_ret->state_ctx.r0 = (uint32_t)result;
+
+ return p_ctx_flih_ret->exc_ret;
+}
+
+void spm_handle_interrupt(void *p_pt, struct irq_load_info_t *p_ildi)
+{
+ psa_flih_result_t flih_result;
+ struct partition_t *p_part;
+
+ if (!p_pt || !p_ildi) {
+ tfm_core_panic();
+ }
+
+ p_part = (struct partition_t *)p_pt;
+
+ if (p_ildi->pid != p_part->p_ldinf->pid) {
+ tfm_core_panic();
+ }
+
+ if (p_ildi->flih_func == NULL) {
+ /* SLIH Model Handling */
+ tfm_hal_irq_disable(p_ildi->source);
+ flih_result = PSA_FLIH_SIGNAL;
+ } else {
+ /* FLIH Model Handling */
+ if (tfm_spm_partition_get_privileged_mode(p_part->p_ldinf->flags) ==
+ TFM_PARTITION_PRIVILEGED_MODE) {
+ flih_result = p_ildi->flih_func();
+ } else {
+ flih_result = tfm_flih_deprivileged_handling(
+ p_part,
+ (uintptr_t)p_ildi->flih_func,
+ CURRENT_THREAD->p_context_ctrl);
+ }
+ }
+
+ if (flih_result == PSA_FLIH_SIGNAL) {
+ spm_assert_signal(p_pt, p_ildi->signal);
+ }
+}
diff --git a/secure_fw/spm/ffm/interrupt.h b/secure_fw/spm/ffm/interrupt.h
new file mode 100644
index 0000000..1cdf1b4
--- /dev/null
+++ b/secure_fw/spm/ffm/interrupt.h
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2021, Arm Limited. All rights reserved.
+ *
+ * SPDX-License-Identifier: BSD-3-Clause
+ *
+ */
+
+#include "load/interrupt_defs.h"
+#include "load/partition_defs.h"
+#include "psa/service.h"
+
+/**
+ * \brief Return the IRQ load info context pointer associated with a signal
+ *
+ * \param[in] p_ldinf The load info of the partition in which we look
+ * for the signal.
+ * \param[in] signal The signal to query for.
+ *
+ * \retval NULL if one of more the following are true:
+ * - the \ref signal indicates more than one signal
+ * - the \ref signal does not belong to the
+ * partition.
+ * \retval Any other value The load info pointer associated with the signal
+ */
+struct irq_load_info_t *get_irq_info_for_signal(
+ const struct partition_load_info_t *p_ldinf,
+ psa_signal_t signal);
+
+/**
+ * \brief Entry of Secure interrupt handler. Platforms can call this function to
+ * handle individual interrupts.
+ *
+ * \param[in] p_pt The owner Partition of the interrupt to handle
+ * \param[in] p_ildi The irq_load_info_t struct of the interrupt to handle
+ *
+ * Note:
+ * The input parameters are maintained by platforms and they must be init-ed
+ * in the interrupt init functions.
+ */
+void spm_handle_interrupt(void *p_pt, struct irq_load_info_t *p_ildi);
+
+/*
+ * Prepare execution context for deprivileged FLIH functions
+ * svc_args: IRQ owner partition_t pointer, flih_func, current thread data
+ */
+uint32_t tfm_flih_prepare_depriv_flih(uint32_t *svc_args);
+
+/* Go back to ISR from FLIH functions */
+uint32_t tfm_flih_return_to_isr(psa_flih_result_t result, uint32_t *msp);
diff --git a/secure_fw/spm/ffm/psa_api.c b/secure_fw/spm/ffm/psa_api.c
index 9d3e6e1..ec5580d 100644
--- a/secure_fw/spm/ffm/psa_api.c
+++ b/secure_fw/spm/ffm/psa_api.c
@@ -10,6 +10,7 @@
#include "critical_section.h"
#include "psa/lifecycle.h"
#include "psa/service.h"
+#include "interrupt.h"
#include "spm_ipc.h"
#include "tfm_arch.h"
#include "tfm_core_utils.h"