summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGregory Nutt <gnutt@nuttx.org>2014-06-20 15:22:00 -0600
committerGregory Nutt <gnutt@nuttx.org>2014-06-20 15:22:00 -0600
commit73c397380330baf18ba899930e76cd8a6e9516d0 (patch)
tree8e531e6994e79efec7dbb733443f0e17a1d3bf6f
parent302fc87b5fdab3e0cf001be9a610d6655607e9a7 (diff)
downloadnuttx-73c397380330baf18ba899930e76cd8a6e9516d0.tar.gz
nuttx-73c397380330baf18ba899930e76cd8a6e9516d0.tar.bz2
nuttx-73c397380330baf18ba899930e76cd8a6e9516d0.zip
SAMA5D4: Add partial support for secure interrupt controller (SAIC)
-rw-r--r--nuttx/arch/arm/src/armv7-a/Kconfig11
-rw-r--r--nuttx/arch/arm/src/armv7-a/arm_vectors.S9
-rw-r--r--nuttx/arch/arm/src/sama5/Kconfig11
-rw-r--r--nuttx/arch/arm/src/sama5/chip/sam_aic.h2
-rw-r--r--nuttx/arch/arm/src/sama5/chip/sam_matrix.h8
-rw-r--r--nuttx/arch/arm/src/sama5/sam_irq.c347
-rw-r--r--nuttx/configs/sama5d4-ek/ramtest/defconfig3
7 files changed, 303 insertions, 88 deletions
diff --git a/nuttx/arch/arm/src/armv7-a/Kconfig b/nuttx/arch/arm/src/armv7-a/Kconfig
index 5636a1533..ba56052f4 100644
--- a/nuttx/arch/arm/src/armv7-a/Kconfig
+++ b/nuttx/arch/arm/src/armv7-a/Kconfig
@@ -55,4 +55,13 @@ config ARMV7A_OABI_TOOLCHAIN
default n
depends on ARMV7A_TOOLCHAIN_BUILDROOT
---help---
- Most of the older buildroot toolchains are OABI and are named arm-nuttx-elf- vs. arm-nuttx-eabi-
+ Most of the older buildroot toolchains are OABI and are named
+ arm-nuttx-elf- vs. arm-nuttx-eabi-
+
+config ARMV7A_DECODEFIQ
+ bool "FIQ Handler"
+ default n
+ ---help---
+ Select this option if your platform supports the function
+ arm_decodefiq(). This is used primarily to support secure TrustZone
+ interrupts received on the FIQ vector.
diff --git a/nuttx/arch/arm/src/armv7-a/arm_vectors.S b/nuttx/arch/arm/src/armv7-a/arm_vectors.S
index ecd21b9cc..c3ea3063f 100644
--- a/nuttx/arch/arm/src/armv7-a/arm_vectors.S
+++ b/nuttx/arch/arm/src/armv7-a/arm_vectors.S
@@ -1,7 +1,7 @@
/************************************************************************************
* arch/arm/src/armv7-a/arm_vectors.S
*
- * Copyright (C) 2013 Gregory Nutt. All rights reserved.
+ * Copyright (C) 2013-2014 Gregory Nutt. All rights reserved.
* Author: Gregory Nutt <gnutt@nuttx.org>
*
* Redistribution and use in source and binary forms, with or without
@@ -469,7 +469,8 @@ arm_vectorundefinsn:
* Name: arm_vectorfiq
*
* Description:
- * Shouldn't happen
+ * Shouldn't happen unless a arm_decodefiq() is provided. FIQ is primarily used
+ * with the TrustZone feature in order to handler secure interrupts.
*
************************************************************************************/
@@ -477,7 +478,11 @@ arm_vectorundefinsn:
.type arm_vectorfiq, %function
arm_vectorfiq:
+#ifdef CONFIG_ARMV7A_DECODEFIQ
+# error Missing logic
+#else
subs pc, lr, #4
+#endif
.size arm_vectorfiq, . - arm_vectorfiq
/************************************************************************************
diff --git a/nuttx/arch/arm/src/sama5/Kconfig b/nuttx/arch/arm/src/sama5/Kconfig
index c4a04e993..c1e8d10e5 100644
--- a/nuttx/arch/arm/src/sama5/Kconfig
+++ b/nuttx/arch/arm/src/sama5/Kconfig
@@ -101,6 +101,10 @@ config SAMA5_HAVE_TC2
bool
default n
+config SAMA5_HAVE_TRUSTZONE
+ bool
+ default n
+
config SAMA5_HAVE_TWI3
bool
default n
@@ -135,6 +139,7 @@ config ARCH_CHIP_SAMA5D4
select SAMA5_HAVE_SPI2
select SAMA5_HAVE_TC1
select SAMA5_HAVE_TC2
+ select SAMA5_HAVE_TRUSTZONE
select SAMA5_HAVE_TWI3
select ARCH_NAND_HWECC
@@ -522,6 +527,12 @@ config SAMA5_VDEC
endmenu # SAMA5 Peripheral Support
+config SAMA5_SECURE
+ bool "Enable secure features"
+ default n
+ depends on SAMA5_HAVE_TRUSTZONE && EXPERIMENTAL
+ select ARMV7A_DECODEFIQ if SAMA5_HAVE_SAIC
+
config SAMA5_PIO_IRQ
bool "PIO pin interrupts"
---help---
diff --git a/nuttx/arch/arm/src/sama5/chip/sam_aic.h b/nuttx/arch/arm/src/sama5/chip/sam_aic.h
index 4da2cabb1..8f909fd18 100644
--- a/nuttx/arch/arm/src/sama5/chip/sam_aic.h
+++ b/nuttx/arch/arm/src/sama5/chip/sam_aic.h
@@ -108,7 +108,7 @@
#define SAM_AIC_WPMR (SAM_AIC_VBASE+SAM_AIC_WPMR_OFFSET)
#define SAM_AIC_WPSR (SAM_AIC_VBASE+SAM_AIC_WPSR_OFFSET)
-#ifdef SAMA5_HAVE_SAIC
+#ifdef CONFIG_SAMA5_HAVE_SAIC
# define SAM_SAIC_SSR (SAM_SAIC_VBASE+SAM_AIC_SSR_OFFSET)
# define SAM_SAIC_SMR (SAM_SAIC_VBASE+SAM_AIC_SMR_OFFSET)
# define SAM_SAIC_SVR (SAM_SAIC_VBASE+SAM_AIC_SVR_OFFSET)
diff --git a/nuttx/arch/arm/src/sama5/chip/sam_matrix.h b/nuttx/arch/arm/src/sama5/chip/sam_matrix.h
index 751dcb5f5..d75118b8c 100644
--- a/nuttx/arch/arm/src/sama5/chip/sam_matrix.h
+++ b/nuttx/arch/arm/src/sama5/chip/sam_matrix.h
@@ -203,6 +203,7 @@
# define SAM_MATRIX_SRTSR11_OFFSET 0x02ac /* Security Region Top Slave 11 Register */
# define SAM_MATRIX_SRTSR12_OFFSET 0x02b0 /* Security Region Top Slave 12 Register */
+# define SAM_MATRIX_SPSELR_OFFSET(n) (0x02c0 + ((n) << 2))
# define SAM_MATRIX_SPSELR1_OFFSET 0x02c0 /* Security Peripheral Select 1 Register */
# define SAM_MATRIX_SPSELR2_OFFSET 0x02c4 /* Security Peripheral Select 2 Register */
# define SAM_MATRIX_SPSELR3_OFFSET 0x02c8 /* Security Peripheral Select 3 Register */
@@ -290,10 +291,7 @@
#endif /* ATSAMA5D3 */
#ifdef ATSAMA5D4
-/* HMATRIX0 (H64MX)
- *
- *
- */
+/* HMATRIX0 (H64MX) */
# define SAM_MATRIX0_MCFG(n)) (SAM_MATRIX64_VBASE+SAM_MATRIX_MCFG_OFFSET(n))
# define SAM_MATRIX0_MCFG0 (SAM_MATRIX64_VBASE+SAM_MATRIX_MCFG0_OFFSET)
@@ -414,6 +412,7 @@
# define SAM_MATRIX0_SRTSR11 (SAM_MATRIX64_VBASE+SAM_MATRIX_SRTSR11_OFFSET)
# define SAM_MATRIX0_SRTSR12 (SAM_MATRIX64_VBASE+SAM_MATRIX_SRTSR12_OFFSET)
+# define SAM_MATRIX0_SPSELR(n) (SAM_MATRIX64_VBASE+SAM_MATRIX_SPSELR_OFFSET(n))
# define SAM_MATRIX0_SPSELR1 (SAM_MATRIX64_VBASE+SAM_MATRIX_SPSELR1_OFFSET)
# define SAM_MATRIX0_SPSELR2 (SAM_MATRIX64_VBASE+SAM_MATRIX_SPSELR2_OFFSET)
# define SAM_MATRIX0_SPSELR3 (SAM_MATRIX64_VBASE+SAM_MATRIX_SPSELR3_OFFSET)
@@ -539,6 +538,7 @@
# define SAM_MATRIX1_SRTSR11 (SAM_MATRIX32_VBASE+SAM_MATRIX_SRTSR11_OFFSET)
# define SAM_MATRIX1_SRTSR12 (SAM_MATRIX32_VBASE+SAM_MATRIX_SRTSR12_OFFSET)
+# define SAM_MATRIX1_SPSELR(n) (SAM_MATRIX32_VBASE+SAM_MATRIX_SPSELR_OFFSET(n))
# define SAM_MATRIX1_SPSELR1 (SAM_MATRIX32_VBASE+SAM_MATRIX_SPSELR1_OFFSET)
# define SAM_MATRIX1_SPSELR2 (SAM_MATRIX32_VBASE+SAM_MATRIX_SPSELR2_OFFSET)
# define SAM_MATRIX1_SPSELR3 (SAM_MATRIX32_VBASE+SAM_MATRIX_SPSELR3_OFFSET)
diff --git a/nuttx/arch/arm/src/sama5/sam_irq.c b/nuttx/arch/arm/src/sama5/sam_irq.c
index ca7d63987..d8cfdfd8a 100644
--- a/nuttx/arch/arm/src/sama5/sam_irq.c
+++ b/nuttx/arch/arm/src/sama5/sam_irq.c
@@ -107,47 +107,57 @@ static const uint8_t g_srctype[SCRTYPE_NTYPES] =
****************************************************************************/
#if defined(CONFIG_DEBUG_IRQ)
-static void sam_dumpaic(const char *msg, int irq)
+static void sam_dumpaic(const char *msg, uintptr_t base, int irq)
{
irqstate_t flags;
flags = irqsave();
- lldbg("AIC (%s, irq=%d):\n", msg, irq);
+ lldbg("AIC (%s, base=%08x irq=%d):\n", msg, base, irq);
/* Select the register set associated with this irq */
- putreg32(irq, SAM_AIC_SSR);
+ putreg32(irq, base + SAM_AIC_SSR_OFFSET);
/* Then dump all of the (readable) register contents */
lldbg(" SSR: %08x SMR: %08x SVR: %08x IVR: %08x\n",
- getreg32(SAM_AIC_SSR), getreg32(SAM_AIC_SMR),
- getreg32(SAM_AIC_SVR), getreg32(SAM_AIC_IVR));
+ getreg32(base + SAM_AIC_SSR_OFFSET),
+ getreg32(base + SAM_AIC_SMR_OFFSET),
+ getreg32(base + SAM_AIC_SVR_OFFSET),
+ getreg32(base + SAM_AIC_IVR_OFFSET));
lldbg(" FVR: %08x ISR: %08x\n",
- getreg32(SAM_AIC_FVR), getreg32(SAM_AIC_ISR));
+ getreg32(base + SAM_AIC_FVR_OFFSET),
+ getreg32(base + SAM_AIC_ISR_OFFSET));
lldbg(" IPR: %08x %08x %08x %08x\n",
- getreg32(SAM_AIC_IPR0), getreg32(SAM_AIC_IPR1),
- getreg32(SAM_AIC_IPR2), getreg32(SAM_AIC_IPR3));
+ getreg32(base + SAM_AIC_IPR0_OFFSET),
+ getreg32(base + SAM_AIC_IPR1_OFFSET),
+ getreg32(base + SAM_AIC_IPR2_OFFSET),
+ getreg32(base + SAM_AIC_IPR3_OFFSET));
/* SAMA5D4 does not have the FFSR register */
#ifdef SAM_AIC_FFSR
lldbg(" IMR: %08x CISR: %08x SPU: %08x FFSR: %08x\n",
- getreg32(SAM_AIC_IMR), getreg32(SAM_AIC_CISR),
- getreg32(SAM_AIC_SPU), getreg32(SAM_AIC_FFSR));
+ getreg32(base + SAM_AIC_IMR_OFFSET),
+ getreg32(base + SAM_AIC_CISR_OFFSET),
+ getreg32(base + SAM_AIC_SPU_OFFSET),
+ getreg32(base + SAM_AIC_FFSR_OFFSET));
#else
lldbg(" IMR: %08x CISR: %08x SPU: %08x\n",
- getreg32(SAM_AIC_IMR), getreg32(SAM_AIC_CISR),
- getreg32(SAM_AIC_SPU));
+ getreg32(base + SAM_AIC_IMR_OFFSET),
+ getreg32(base + SAM_AIC_CISR_OFFSET),
+ getreg32(base + SAM_AIC_SPU_OFFSET));
#endif
lldbg(" DCR: %08x WPMR: %08x WPSR: %08x\n",
- getreg32(SAM_AIC_DCR), getreg32(SAM_AIC_WPMR),
- getreg32(SAM_AIC_WPSR));
+ getreg32(base + SAM_AIC_DCR_OFFSET),
+ getreg32(base + SAM_AIC_WPMR_OFFSET),
+ getreg32(base + SAM_AIC_WPSR_OFFSET));
+
irqrestore(flags);
}
#else
-# define sam_dumpaic(msg, irq)
+# define sam_dumpaic(msg, base, irq)
#endif
/****************************************************************************
@@ -233,44 +243,91 @@ static uint32_t *sam_fiqhandler(int irq, uint32_t *regs)
}
/****************************************************************************
- * Public Functions
+ * Name: sam_aic_ish64mx
+ *
+ * Description:
+ * Return true if the peripheral is H64 Matrix.
+ *
+ * Input Parameter:
+ * PID = IRQ number
+ *
****************************************************************************/
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+static inline bool sam_aic_ish64mx(uint32_t irq)
+{
+ return (irq == SAM_IRQ_ARM ||
+ irq == SAM_IRQ_XDMAC0 ||
+ /* irq == SAM_IRQ_CPKCC || */
+ irq == SAM_IRQ_AESB ||
+ irq == SAM_IRQ_MPDDRC ||
+ irq == SAM_IRQ_VDEC ||
+ irq == SAM_IRQ_XDMAC1 ||
+ irq == SAM_IRQ_LCDC ||
+ irq == SAM_IRQ_ISI ||
+ irq == SAM_IRQ_L2CC);
+}
+#endif
+
/****************************************************************************
- * Name: up_irqinitialize
+ * Name: sam_aic_issecure
*
* Description:
- * This function is called by up_initialize() during the bring-up of the
- * system. It is the responsibility of this function to but the interrupt
- * subsystem into the working and ready state.
+ * Return true if the peripheral secure.
+ *
+ * Input Parameter:
+ * PID = IRQ number
*
****************************************************************************/
-void up_irqinitialize(void)
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+static bool sam_aic_issecure(uint32_t irq)
{
-#if defined(CONFIG_SAMA5_BOOT_ISRAM) || defined(CONFIG_SAMA5_BOOT_CS0FLASH)
- size_t vectorsize;
-#endif
- int i;
+ uintptr_t regaddr;
+ uint32_t bit;
+ int regndx;
- /* The following operations need to be atomic, but since this function is
- * called early in the initialization sequence, we expect to have exclusive
- * access to the AIC.
- */
+ /* Get the register index and bit mask */
- /* Colorize the interrupt stack for debug purposes */
+ regndx = (irq >> 5);
+ bit = ((uint32_t)1 << (irq & 0x1f));
-#if defined(CONFIG_DEBUG_STACK) && CONFIG_ARCH_INTERRUPTSTACK > 3
- {
- size_t intstack_size = (CONFIG_ARCH_INTERRUPTSTACK & ~3);
- up_stack_color((FAR void *)((uintptr_t)&g_intstackbase - intstack_size),
- intstack_size);
- }
+ /* Get the SPSELR register address */
+
+ if (sam_aic_ish64mx(irq))
+ {
+ /* H64MX. Use Matrix 0 */
+
+ regaddr = SAM_MATRIX0_SPSELR(regndx);
+ }
+ else
+ {
+ /* H32MX. Use Matrix 1 */
+
+ regaddr = SAM_MATRIX1_SPSELR(regndx);
+ }
+
+ /* Return true if the bit corresponding to this IRQ is zero */
+
+ return (getreg32(regaddr) & bit) == 0;
+}
#endif
+/****************************************************************************
+ * Name: sam_aic_initialize
+ *
+ * Description:
+ * Initialize the AIC or the SAIC.
+ *
+ ****************************************************************************/
+
+static void sam_aic_initialize(uintptr_t base)
+{
+ int i;
+
/* Unprotect SMR, SVR, SPU and DCR register */
- putreg32(AIC_WPMR_WPKEY, SAM_AIC_WPMR);
+ putreg32(AIC_WPMR_WPKEY, base + SAM_AIC_WPMR_OFFSET);
/* Configure the FIQ and the IRQs. */
@@ -278,35 +335,35 @@ void up_irqinitialize(void)
{
/* Select the interrupt registers */
- putreg32(i, SAM_AIC_SSR);
+ putreg32(i, base + SAM_AIC_SSR_OFFSET);
/* Disable the interrupt */
- putreg32(AIC_IDCR_INTD, SAM_AIC_IDCR);
+ putreg32(AIC_IDCR_INTD, base + SAM_AIC_IDCR_OFFSET);
/* Set the (unused) FIQ/IRQ handler */
if (i == SAM_PID_FIQ)
{
- putreg32((uint32_t)sam_fiqhandler, SAM_AIC_SVR);
+ putreg32((uint32_t)sam_fiqhandler, base + SAM_AIC_SVR_OFFSET);
}
else
{
- putreg32((uint32_t)arm_doirq, SAM_AIC_SVR);
+ putreg32((uint32_t)arm_doirq, base + SAM_AIC_SVR_OFFSET);
}
/* Set the default interrupt priority */
- putreg32(SAM_DEFAULT_PRIOR, SAM_AIC_SMR);
+ putreg32(SAM_DEFAULT_PRIOR, base + SAM_AIC_SMR_OFFSET);
/* Clear any pending interrupt */
- putreg32(AIC_ICCR_INTCLR, SAM_AIC_ICCR);
+ putreg32(AIC_ICCR_INTCLR, base + SAM_AIC_ICCR_OFFSET);
}
/* Set the (unused) spurious interrupt handler */
- putreg32((uint32_t)sam_spurious, SAM_AIC_SPU);
+ putreg32((uint32_t)sam_spurious, base + SAM_AIC_SPU_OFFSET);
/* Perform 8 interrupt acknowledgements by writing any value to the
* EOICR register.
@@ -314,12 +371,59 @@ void up_irqinitialize(void)
for (i = 0; i < 8 ; i++)
{
- putreg32(AIC_EOICR_ENDIT, SAM_AIC_EOICR);
+ putreg32(AIC_EOICR_ENDIT, base + SAM_AIC_EOICR_OFFSET);
}
/* Restore protection and the interrupt state */
- putreg32(AIC_WPMR_WPKEY | AIC_WPMR_WPEN, SAM_AIC_WPMR);
+ putreg32(AIC_WPMR_WPKEY | AIC_WPMR_WPEN, base + SAM_AIC_WPMR_OFFSET);
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: up_irqinitialize
+ *
+ * Description:
+ * This function is called by up_initialize() during the bring-up of the
+ * system. It is the responsibility of this function to but the interrupt
+ * subsystem into the working and ready state.
+ *
+ ****************************************************************************/
+
+void up_irqinitialize(void)
+{
+#if defined(CONFIG_SAMA5_BOOT_ISRAM) || defined(CONFIG_SAMA5_BOOT_CS0FLASH)
+ size_t vectorsize;
+#endif
+
+ /* The following operations need to be atomic, but since this function is
+ * called early in the initialization sequence, we expect to have exclusive
+ * access to the AIC.
+ */
+
+ /* Colorize the interrupt stack for debug purposes */
+
+#if defined(CONFIG_DEBUG_STACK) && CONFIG_ARCH_INTERRUPTSTACK > 3
+ {
+ size_t intstack_size = (CONFIG_ARCH_INTERRUPTSTACK & ~3);
+ up_stack_color((FAR void *)((uintptr_t)&g_intstackbase - intstack_size),
+ intstack_size);
+ }
+#endif
+
+ /* Initialize the Advanced Interrupt Controller (AIC) */
+
+ sam_aic_initialize(SAM_AIC_VBASE);
+
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+ /* Initialize the Secure Advanced Interrupt Controller (SAIC) */
+
+ sam_aic_initialize(SAM_SAIC_VBASE);
+
+#endif
#if defined(CONFIG_ARCH_LOWVECTORS)
/* If CONFIG_ARCH_LOWVECTORS is defined, then the vectors located at the
@@ -337,7 +441,7 @@ void up_irqinitialize(void)
* 0x0000:00000. VBAR == 0x0000:0000.
*
* This method is used when booting from ISRAM or NOR FLASH. In
- & that case, vectors must lie at the beginning of NOFR FLASH.
+ * that case, vectors must lie at the beginning of NOFR FLASH.
*
* 3. Set the Cortex-A5 VBAR register so that the vector table address
* is moved to a location other than 0x0000:0000.
@@ -440,7 +544,7 @@ void up_irqinitialize(void)
}
/****************************************************************************
- * Name: arm_decodeirq
+ * Name: arm_decodeirq, arm_decodefiq (and sam_decodeirq helper).
*
* Description:
* This function is called from the IRQ vector handler in arm_vectors.S.
@@ -454,7 +558,7 @@ void up_irqinitialize(void)
*
****************************************************************************/
-uint32_t *arm_decodeirq(uint32_t *regs)
+static uint32_t *sam_decodeirq(uintptr_t base, uint32_t *regs)
{
uint32_t irqid;
uint32_t ivr;
@@ -491,14 +595,14 @@ uint32_t *arm_decodeirq(uint32_t *regs)
/* Write in the IVR to support Protect Mode */
- ivr = getreg32(SAM_AIC_IVR);
- putreg32(ivr, SAM_AIC_IVR);
+ ivr = getreg32(base + SAM_AIC_IVR_OFFSET);
+ putreg32(ivr, base + SAM_AIC_IVR_OFFSET);
/* Get the IRQ number from the interrupt status register. NOTE that the
* IRQ number is the same is the peripheral ID (PID).
*/
- irqid = getreg32(SAM_AIC_ISR) & AIC_ISR_MASK;
+ irqid = getreg32(base + SAM_AIC_ISR_OFFSET) & AIC_ISR_MASK;
/* Dispatch the interrupt */
@@ -506,19 +610,46 @@ uint32_t *arm_decodeirq(uint32_t *regs)
/* Acknowledge interrupt */
- putreg32(AIC_EOICR_ENDIT, SAM_AIC_EOICR);
+ putreg32(AIC_EOICR_ENDIT, base + SAM_AIC_EOICR_OFFSET);
return regs;
}
+/* This is the entry point from the ARM IRQ vector handler */
+
+uint32_t *arm_decodeirq(uint32_t *regs)
+{
+ return sam_decodeirq(SAM_AIC_VBASE, regs);
+}
+
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+/* This is the entry point from the ARM FIQ vector handler */
+
+uint32_t *arm_decodefiq(uint32_t *regs)
+{
+ /* In order to distinguish a FIQ from a true secure interrupt we need to
+ * check the state of the FIQ line in the SAIC_CISR register.
+ */
+
+ if ((getreg32(SAM_SAIC_CISR) & AIC_CISR_NFIQ) != 0)
+ {
+ return sam_fiqhandler(SAM_IRQ_FIQ, regs);
+ }
+ else
+ {
+ return sam_decodeirq(SAM_SAIC_VBASE, regs);
+ }
+}
+#endif
+
/****************************************************************************
- * Name: up_disable_irq
+ * Name: up_disable_irq (and sam_disable_irq helper)
*
* Description:
* Disable the IRQ specified by 'irq'
*
****************************************************************************/
-void up_disable_irq(int irq)
+static void sam_disable_irq(uintptr_t base, int irq)
{
irqstate_t flags;
@@ -530,12 +661,12 @@ void up_disable_irq(int irq)
/* Select the register set associated with this irq */
- putreg32(irq, SAM_AIC_SSR);
+ putreg32(irq, base + SAM_AIC_SSR_OFFSET);
/* Disable the interrupt */
- putreg32(AIC_IDCR_INTD, SAM_AIC_IDCR);
- sam_dumpaic("disable", irq);
+ putreg32(AIC_IDCR_INTD, base + SAM_AIC_IDCR_OFFSET);
+ sam_dumpaic("disable", base, irq);
irqrestore(flags);
}
#ifdef CONFIG_SAMA5_PIO_IRQ
@@ -546,18 +677,31 @@ void up_disable_irq(int irq)
sam_pioirqdisable(irq);
}
#endif
- sam_dumpaic("disable", irq);
+}
+
+void up_disable_irq(int irq)
+{
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+ if (sam_aic_issecure(irq))
+ {
+ sam_disable_irq(SAM_SAIC_VBASE, irq);
+ }
+ else
+#endif
+ {
+ sam_disable_irq(SAM_AIC_VBASE, irq);
+ }
}
/****************************************************************************
- * Name: up_enable_irq
+ * Name: up_enable_irq (and sam_enable_irq helper)
*
* Description:
* Enable the IRQ specified by 'irq'
*
****************************************************************************/
-void up_enable_irq(int irq)
+static void sam_enable_irq(uintptr_t base, int irq)
{
irqstate_t flags;
@@ -569,12 +713,12 @@ void up_enable_irq(int irq)
/* Select the register set associated with this irq */
- putreg32(irq, SAM_AIC_SSR);
+ putreg32(irq, base + SAM_AIC_SSR_OFFSET);
/* Enable the interrupt */
- putreg32(AIC_IECR_INTEN, SAM_AIC_IECR);
- sam_dumpaic("enable", irq);
+ putreg32(AIC_IECR_INTEN, base + SAM_AIC_IECR_OFFSET);
+ sam_dumpaic("enable", base, irq);
irqrestore(flags);
}
#ifdef CONFIG_SAMA5_PIO_IRQ
@@ -587,6 +731,20 @@ void up_enable_irq(int irq)
#endif
}
+void up_enable_irq(int irq)
+{
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+ if (sam_aic_issecure(irq))
+ {
+ sam_enable_irq(SAM_SAIC_VBASE, irq);
+ }
+ else
+#endif
+ {
+ sam_enable_irq(SAM_AIC_VBASE, irq);
+ }
+}
+
/****************************************************************************
* Name: up_maskack_irq
*
@@ -601,7 +759,7 @@ void up_maskack_irq(int irq)
}
/****************************************************************************
- * Name: up_prioritize_irq
+ * Name: up_prioritize_irq (and sam_prioritize_irq helper)
*
* Description:
* Set the priority of an IRQ.
@@ -612,7 +770,7 @@ void up_maskack_irq(int irq)
****************************************************************************/
#ifdef CONFIG_ARCH_IRQPRIO
-int up_prioritize_irq(int irq, int priority)
+static int sam_prioritize_irq(uint32_t base, int irq, int priority)
{
irqstate_t flags;
uint32_t regval;
@@ -626,32 +784,46 @@ int up_prioritize_irq(int irq, int priority)
/* Select the register set associated with this irq */
- putreg32(irq, SAM_AIC_SSR);
+ putreg32(irq, base + SAM_AIC_SSR_OFFSET);
/* Unprotect and write the SMR register */
- putreg32(AIC_WPMR_WPKEY, SAM_AIC_WPMR);
+ putreg32(AIC_WPMR_WPKEY, base + SAM_AIC_WPMR_OFFSET);
/* Set the new priority, preserving the current srctype */
- regval = getreg32(SAM_AIC_SMR);
+ regval = getreg32(base + SAM_AIC_SMR_OFFSET);
regval &= ~AIC_SMR_PRIOR_MASK;
regval |= (uint32_t)priority << AIC_SMR_PRIOR_SHIFT;
- putreg32(regval, SAM_AIC_SMR);
+ putreg32(regval, base + SAM_AIC_SMR_OFFSET);
/* Restore protection and the interrupt state */
- putreg32(AIC_WPMR_WPKEY | AIC_WPMR_WPEN, SAM_AIC_WPMR);
- sam_dumpaic("prioritize", irq);
+ putreg32(AIC_WPMR_WPKEY | AIC_WPMR_WPEN, base + SAM_AIC_WPMR_OFFSET);
+ sam_dumpaic("prioritize", base, irq);
irqrestore(flags);
}
return OK;
}
+
+int up_prioritize_irq(int irq, int priority)
+{
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+ if (sam_aic_issecure(irq))
+ {
+ sam_prioritize_irq(SAM_SAIC_VBASE, irq, priority);
+ }
+ else
+#endif
+ {
+ sam_prioritize_irq(SAM_AIC_VBASE, irq, priority);
+ }
+}
#endif
/****************************************************************************
- * Name: sam_irq_srctype
+ * Name: sam_irq_srctype (and _sam_irq_srctype helper)
*
* Description:
* irq - Identifies the IRQ source to be configured
@@ -659,7 +831,8 @@ int up_prioritize_irq(int irq, int priority)
*
****************************************************************************/
-void sam_irq_srctype(int irq, enum sam_srctype_e srctype)
+static void _sam_irq_srctype(uintptr_t base, int irq,
+ enum sam_srctype_e srctype)
{
irqstate_t flags;
uint32_t regval;
@@ -672,22 +845,36 @@ void sam_irq_srctype(int irq, enum sam_srctype_e srctype)
/* Select the register set associated with this irq */
- putreg32(irq, SAM_AIC_SSR);
+ putreg32(irq, base + SAM_AIC_SSR_OFFSET);
/* Unprotect and write the SMR register */
- putreg32(AIC_WPMR_WPKEY, SAM_AIC_WPMR);
+ putreg32(AIC_WPMR_WPKEY, base + SAM_AIC_WPMR_OFFSET);
/* Set the new srctype, preserving the current priority */
- regval = getreg32(SAM_AIC_SMR);
+ regval = getreg32(base + SAM_AIC_SMR_OFFSET);
regval &= ~AIC_SMR_SRCTYPE_MASK;
regval |= (uint32_t)g_srctype[srctype] << AIC_SMR_SRCTYPE_SHIFT;
- putreg32(regval, SAM_AIC_SMR);
+ putreg32(regval, base + SAM_AIC_SMR_OFFSET);
/* Restore protection and the interrupt state */
- putreg32(AIC_WPMR_WPKEY | AIC_WPMR_WPEN, SAM_AIC_WPMR);
- sam_dumpaic("srctype", irq);
+ putreg32(AIC_WPMR_WPKEY | AIC_WPMR_WPEN, base + SAM_AIC_WPMR_OFFSET);
+ sam_dumpaic("srctype", base, irq);
irqrestore(flags);
}
+
+void sam_irq_srctype(int irq, enum sam_srctype_e srctype)
+{
+#if defined(CONFIG_SAMA5_SECURE) && defined(CONFIG_SAMA5_HAVE_SAIC)
+ if (sam_aic_issecure(irq))
+ {
+ _sam_irq_srctype(SAM_SAIC_VBASE, irq, srctype);
+ }
+ else
+#endif
+ {
+ _sam_irq_srctype(SAM_AIC_VBASE, irq, srctype);
+ }
+}
diff --git a/nuttx/configs/sama5d4-ek/ramtest/defconfig b/nuttx/configs/sama5d4-ek/ramtest/defconfig
index 99e53ac0f..02b909b98 100644
--- a/nuttx/configs/sama5d4-ek/ramtest/defconfig
+++ b/nuttx/configs/sama5d4-ek/ramtest/defconfig
@@ -118,6 +118,7 @@ CONFIG_ARMV7A_TOOLCHAIN_CODESOURCERYW=y
# CONFIG_ARMV7A_TOOLCHAIN_GNU_EABIL is not set
# CONFIG_ARMV7A_TOOLCHAIN_GNU_EABIW is not set
# CONFIG_ARMV7A_TOOLCHAIN_GNU_OABI is not set
+# CONFIG_ARMV7A_DECODEFIQ is not set
#
# SAMA5 Configuration Options
@@ -145,6 +146,7 @@ CONFIG_SAMA5_HAVE_SFC=y
CONFIG_SAMA5_HAVE_SPI2=y
CONFIG_SAMA5_HAVE_TC1=y
CONFIG_SAMA5_HAVE_TC2=y
+CONFIG_SAMA5_HAVE_TRUSTZONE=y
CONFIG_SAMA5_HAVE_TWI3=y
CONFIG_SAMA5_HAVE_VDEC=y
# CONFIG_ARCH_CHIP_SAMA5D3 is not set
@@ -211,6 +213,7 @@ CONFIG_SAMA5_USART3=y
# CONFIG_SAMA5_FUSE is not set
CONFIG_SAMA5_MPDDRC=y
# CONFIG_SAMA5_VDEC is not set
+# CONFIG_SAMA5_SECURE is not set
# CONFIG_SAMA5_PIO_IRQ is not set
#