aboutsummaryrefslogtreecommitdiffstats
path: root/os/hal/ports/STM32
diff options
context:
space:
mode:
Diffstat (limited to 'os/hal/ports/STM32')
-rw-r--r--os/hal/ports/STM32/LLD/SPIv2/spi_lld.c153
-rw-r--r--os/hal/ports/STM32/LLD/SPIv2/spi_lld.h180
2 files changed, 332 insertions, 1 deletions
diff --git a/os/hal/ports/STM32/LLD/SPIv2/spi_lld.c b/os/hal/ports/STM32/LLD/SPIv2/spi_lld.c
index fec4b2fba..cc4635122 100644
--- a/os/hal/ports/STM32/LLD/SPIv2/spi_lld.c
+++ b/os/hal/ports/STM32/LLD/SPIv2/spi_lld.c
@@ -54,6 +54,30 @@
STM32_DMA_GETCHANNEL(STM32_SPI_SPI3_TX_DMA_STREAM, \
STM32_SPI3_TX_DMA_CHN)
+#define SPI4_RX_DMA_CHANNEL \
+ STM32_DMA_GETCHANNEL(STM32_SPI_SPI4_RX_DMA_STREAM, \
+ STM32_SPI4_RX_DMA_CHN)
+
+#define SPI4_TX_DMA_CHANNEL \
+ STM32_DMA_GETCHANNEL(STM32_SPI_SPI4_TX_DMA_STREAM, \
+ STM32_SPI4_TX_DMA_CHN)
+
+#define SPI5_RX_DMA_CHANNEL \
+ STM32_DMA_GETCHANNEL(STM32_SPI_SPI5_RX_DMA_STREAM, \
+ STM32_SPI5_RX_DMA_CHN)
+
+#define SPI5_TX_DMA_CHANNEL \
+ STM32_DMA_GETCHANNEL(STM32_SPI_SPI5_TX_DMA_STREAM, \
+ STM32_SPI5_TX_DMA_CHN)
+
+#define SPI6_RX_DMA_CHANNEL \
+ STM32_DMA_GETCHANNEL(STM32_SPI_SPI6_RX_DMA_STREAM, \
+ STM32_SPI6_RX_DMA_CHN)
+
+#define SPI6_TX_DMA_CHANNEL \
+ STM32_DMA_GETCHANNEL(STM32_SPI_SPI6_TX_DMA_STREAM, \
+ STM32_SPI6_TX_DMA_CHN)
+
/*===========================================================================*/
/* Driver exported variables. */
/*===========================================================================*/
@@ -73,6 +97,21 @@ SPIDriver SPID2;
SPIDriver SPID3;
#endif
+/** @brief SPI4 driver identifier.*/
+#if STM32_SPI_USE_SPI4 || defined(__DOXYGEN__)
+SPIDriver SPID4;
+#endif
+
+/** @brief SPI5 driver identifier.*/
+#if STM32_SPI_USE_SPI5 || defined(__DOXYGEN__)
+SPIDriver SPID5;
+#endif
+
+/** @brief SPI6 driver identifier.*/
+#if STM32_SPI_USE_SPI6 || defined(__DOXYGEN__)
+SPIDriver SPID6;
+#endif
+
/*===========================================================================*/
/* Driver local variables and types. */
/*===========================================================================*/
@@ -200,6 +239,60 @@ void spi_lld_init(void) {
STM32_DMA_CR_DMEIE |
STM32_DMA_CR_TEIE;
#endif
+
+#if STM32_SPI_USE_SPI4
+ spiObjectInit(&SPID4);
+ SPID4.spi = SPI4;
+ SPID4.dmarx = STM32_DMA_STREAM(STM32_SPI_SPI4_RX_DMA_STREAM);
+ SPID4.dmatx = STM32_DMA_STREAM(STM32_SPI_SPI4_TX_DMA_STREAM);
+ SPID4.rxdmamode = STM32_DMA_CR_CHSEL(SPI4_RX_DMA_CHANNEL) |
+ STM32_DMA_CR_PL(STM32_SPI_SPI4_DMA_PRIORITY) |
+ STM32_DMA_CR_DIR_P2M |
+ STM32_DMA_CR_TCIE |
+ STM32_DMA_CR_DMEIE |
+ STM32_DMA_CR_TEIE;
+ SPID4.txdmamode = STM32_DMA_CR_CHSEL(SPI4_TX_DMA_CHANNEL) |
+ STM32_DMA_CR_PL(STM32_SPI_SPI4_DMA_PRIORITY) |
+ STM32_DMA_CR_DIR_M2P |
+ STM32_DMA_CR_DMEIE |
+ STM32_DMA_CR_TEIE;
+#endif
+
+#if STM32_SPI_USE_SPI5
+ spiObjectInit(&SPID3);
+ SPID5.spi = SPI5;
+ SPID5.dmarx = STM32_DMA_STREAM(STM32_SPI_SPI5_RX_DMA_STREAM);
+ SPID5.dmatx = STM32_DMA_STREAM(STM32_SPI_SPI5_TX_DMA_STREAM);
+ SPID5.rxdmamode = STM32_DMA_CR_CHSEL(SPI5_RX_DMA_CHANNEL) |
+ STM32_DMA_CR_PL(STM32_SPI_SPI5_DMA_PRIORITY) |
+ STM32_DMA_CR_DIR_P2M |
+ STM32_DMA_CR_TCIE |
+ STM32_DMA_CR_DMEIE |
+ STM32_DMA_CR_TEIE;
+ SPID5.txdmamode = STM32_DMA_CR_CHSEL(SPI5_TX_DMA_CHANNEL) |
+ STM32_DMA_CR_PL(STM32_SPI_SPI5_DMA_PRIORITY) |
+ STM32_DMA_CR_DIR_M2P |
+ STM32_DMA_CR_DMEIE |
+ STM32_DMA_CR_TEIE;
+#endif
+
+#if STM32_SPI_USE_SPI6
+ spiObjectInit(&SPID6);
+ SPID6.spi = SPI6;
+ SPID6.dmarx = STM32_DMA_STREAM(STM32_SPI_SPI6_RX_DMA_STREAM);
+ SPID6.dmatx = STM32_DMA_STREAM(STM32_SPI_SPI6_TX_DMA_STREAM);
+ SPID6.rxdmamode = STM32_DMA_CR_CHSEL(SPI6_RX_DMA_CHANNEL) |
+ STM32_DMA_CR_PL(STM32_SPI_SPI6_DMA_PRIORITY) |
+ STM32_DMA_CR_DIR_P2M |
+ STM32_DMA_CR_TCIE |
+ STM32_DMA_CR_DMEIE |
+ STM32_DMA_CR_TEIE;
+ SPID6.txdmamode = STM32_DMA_CR_CHSEL(SPI6_TX_DMA_CHANNEL) |
+ STM32_DMA_CR_PL(STM32_SPI_SPI6_DMA_PRIORITY) |
+ STM32_DMA_CR_DIR_M2P |
+ STM32_DMA_CR_DMEIE |
+ STM32_DMA_CR_TEIE;
+#endif
}
/**
@@ -262,6 +355,54 @@ void spi_lld_start(SPIDriver *spip) {
rccEnableSPI3(FALSE);
}
#endif
+#if STM32_SPI_USE_SPI4
+ if (&SPID4 == spip) {
+ bool b;
+ b = dmaStreamAllocate(spip->dmarx,
+ STM32_SPI_SPI4_IRQ_PRIORITY,
+ (stm32_dmaisr_t)spi_lld_serve_rx_interrupt,
+ (void *)spip);
+ osalDbgAssert(!b, "stream already allocated");
+ b = dmaStreamAllocate(spip->dmatx,
+ STM32_SPI_SPI4_IRQ_PRIORITY,
+ (stm32_dmaisr_t)spi_lld_serve_tx_interrupt,
+ (void *)spip);
+ osalDbgAssert(!b, "stream already allocated");
+ rccEnableSPI4(FALSE);
+ }
+#endif
+#if STM32_SPI_USE_SPI5
+ if (&SPID5 == spip) {
+ bool b;
+ b = dmaStreamAllocate(spip->dmarx,
+ STM32_SPI_SPI5_IRQ_PRIORITY,
+ (stm32_dmaisr_t)spi_lld_serve_rx_interrupt,
+ (void *)spip);
+ osalDbgAssert(!b, "stream already allocated");
+ b = dmaStreamAllocate(spip->dmatx,
+ STM32_SPI_SPI5_IRQ_PRIORITY,
+ (stm32_dmaisr_t)spi_lld_serve_tx_interrupt,
+ (void *)spip);
+ osalDbgAssert(!b, "stream already allocated");
+ rccEnableSPI5(FALSE);
+ }
+#endif
+#if STM32_SPI_USE_SPI6
+ if (&SPID6 == spip) {
+ bool b;
+ b = dmaStreamAllocate(spip->dmarx,
+ STM32_SPI_SPI6_IRQ_PRIORITY,
+ (stm32_dmaisr_t)spi_lld_serve_rx_interrupt,
+ (void *)spip);
+ osalDbgAssert(!b, "stream already allocated");
+ b = dmaStreamAllocate(spip->dmatx,
+ STM32_SPI_SPI6_IRQ_PRIORITY,
+ (stm32_dmaisr_t)spi_lld_serve_tx_interrupt,
+ (void *)spip);
+ osalDbgAssert(!b, "stream already allocated");
+ rccEnableSPI6(FALSE);
+ }
+#endif
/* DMA setup.*/
dmaStreamSetPeripheral(spip->dmarx, &spip->spi->DR);
@@ -323,6 +464,18 @@ void spi_lld_stop(SPIDriver *spip) {
if (&SPID3 == spip)
rccDisableSPI3(FALSE);
#endif
+#if STM32_SPI_USE_SPI4
+ if (&SPID4 == spip)
+ rccDisableSPI4(FALSE);
+#endif
+#if STM32_SPI_USE_SPI5
+ if (&SPID5 == spip)
+ rccDisableSPI5(FALSE);
+#endif
+#if STM32_SPI_USE_SPI6
+ if (&SPID6 == spip)
+ rccDisableSPI6(FALSE);
+#endif
}
}
diff --git a/os/hal/ports/STM32/LLD/SPIv2/spi_lld.h b/os/hal/ports/STM32/LLD/SPIv2/spi_lld.h
index bf7ddf700..235341e35 100644
--- a/os/hal/ports/STM32/LLD/SPIv2/spi_lld.h
+++ b/os/hal/ports/STM32/LLD/SPIv2/spi_lld.h
@@ -67,6 +67,33 @@
#endif
/**
+ * @brief SPI4 driver enable switch.
+ * @details If set to @p TRUE the support for SPI4 is included.
+ * @note The default is @p FALSE.
+ */
+#if !defined(STM32_SPI_USE_SPI4) || defined(__DOXYGEN__)
+#define STM32_SPI_USE_SPI4 FALSE
+#endif
+
+/**
+ * @brief SPI5 driver enable switch.
+ * @details If set to @p TRUE the support for SPI5 is included.
+ * @note The default is @p FALSE.
+ */
+#if !defined(STM32_SPI_USE_SPI5) || defined(__DOXYGEN__)
+#define STM32_SPI_USE_SPI5 FALSE
+#endif
+
+/**
+ * @brief SPI6 driver enable switch.
+ * @details If set to @p TRUE the support for SPI6 is included.
+ * @note The default is @p FALSE.
+ */
+#if !defined(STM32_SPI_USE_SPI6) || defined(__DOXYGEN__)
+#define STM32_SPI_USE_SPI6 FALSE
+#endif
+
+/**
* @brief SPI1 interrupt priority level setting.
*/
#if !defined(STM32_SPI_SPI1_IRQ_PRIORITY) || defined(__DOXYGEN__)
@@ -88,6 +115,27 @@
#endif
/**
+ * @brief SPI4 interrupt priority level setting.
+ */
+#if !defined(STM32_SPI_SPI4_IRQ_PRIORITY) || defined(__DOXYGEN__)
+#define STM32_SPI_SPI4_IRQ_PRIORITY 10
+#endif
+
+/**
+ * @brief SPI5 interrupt priority level setting.
+ */
+#if !defined(STM32_SPI_SPI5_IRQ_PRIORITY) || defined(__DOXYGEN__)
+#define STM32_SPI_SPI5_IRQ_PRIORITY 10
+#endif
+
+/**
+ * @brief SPI6 interrupt priority level setting.
+ */
+#if !defined(STM32_SPI_SPI6_IRQ_PRIORITY) || defined(__DOXYGEN__)
+#define STM32_SPI_SPI6_IRQ_PRIORITY 10
+#endif
+
+/**
* @brief SPI1 DMA priority (0..3|lowest..highest).
* @note The priority level is used for both the TX and RX DMA streams but
* because of the streams ordering the RX stream has always priority
@@ -118,6 +166,36 @@
#endif
/**
+ * @brief SPI4 DMA priority (0..3|lowest..highest).
+ * @note The priority level is used for both the TX and RX DMA streams but
+ * because of the streams ordering the RX stream has always priority
+ * over the TX stream.
+ */
+#if !defined(STM32_SPI_SPI4_DMA_PRIORITY) || defined(__DOXYGEN__)
+#define STM32_SPI_SPI4_DMA_PRIORITY 1
+#endif
+
+/**
+ * @brief SPI5 DMA priority (0..3|lowest..highest).
+ * @note The priority level is used for both the TX and RX DMA streams but
+ * because of the streams ordering the RX stream has always priority
+ * over the TX stream.
+ */
+#if !defined(STM32_SPI_SPI5_DMA_PRIORITY) || defined(__DOXYGEN__)
+#define STM32_SPI_SPI5_DMA_PRIORITY 1
+#endif
+
+/**
+ * @brief SPI6 DMA priority (0..3|lowest..highest).
+ * @note The priority level is used for both the TX and RX DMA streams but
+ * because of the streams ordering the RX stream has always priority
+ * over the TX stream.
+ */
+#if !defined(STM32_SPI_SPI6_DMA_PRIORITY) || defined(__DOXYGEN__)
+#define STM32_SPI_SPI6_DMA_PRIORITY 1
+#endif
+
+/**
* @brief SPI DMA error hook.
*/
#if !defined(STM32_SPI_DMA_ERROR_HOOK) || defined(__DOXYGEN__)
@@ -141,7 +219,20 @@
#error "SPI3 not present in the selected device"
#endif
-#if !STM32_SPI_USE_SPI1 && !STM32_SPI_USE_SPI2 && !STM32_SPI_USE_SPI3
+#if STM32_SPI_USE_SPI4 && !STM32_HAS_SPI4
+#error "SPI4 not present in the selected device"
+#endif
+
+#if STM32_SPI_USE_SPI5 && !STM32_HAS_SPI5
+#error "SPI5 not present in the selected device"
+#endif
+
+#if STM32_SPI_USE_SPI6 && !STM32_HAS_SPI6
+#error "SPI6 not present in the selected device"
+#endif
+
+#if !STM32_SPI_USE_SPI1 && !STM32_SPI_USE_SPI2 && !STM32_SPI_USE_SPI3 && \
+ !STM32_SPI_USE_SPI4 && !STM32_SPI_USE_SPI5 && !STM32_SPI_USE_SPI6
#error "SPI driver activated but no SPI peripheral assigned"
#endif
@@ -160,6 +251,21 @@
#error "Invalid IRQ priority assigned to SPI3"
#endif
+#if STM32_SPI_USE_SPI4 && \
+ !OSAL_IRQ_IS_VALID_PRIORITY(STM32_SPI_SPI4_IRQ_PRIORITY)
+#error "Invalid IRQ priority assigned to SPI4"
+#endif
+
+#if STM32_SPI_USE_SPI5 && \
+ !OSAL_IRQ_IS_VALID_PRIORITY(STM32_SPI_SPI5_IRQ_PRIORITY)
+#error "Invalid IRQ priority assigned to SPI5"
+#endif
+
+#if STM32_SPI_USE_SPI6 && \
+ !OSAL_IRQ_IS_VALID_PRIORITY(STM32_SPI_SPI6_IRQ_PRIORITY)
+#error "Invalid IRQ priority assigned to SPI6"
+#endif
+
#if STM32_SPI_USE_SPI1 && \
!STM32_DMA_IS_VALID_PRIORITY(STM32_SPI_SPI1_DMA_PRIORITY)
#error "Invalid DMA priority assigned to SPI1"
@@ -175,6 +281,21 @@
#error "Invalid DMA priority assigned to SPI3"
#endif
+#if STM32_SPI_USE_SPI4 && \
+ !STM32_DMA_IS_VALID_PRIORITY(STM32_SPI_SPI4_DMA_PRIORITY)
+#error "Invalid DMA priority assigned to SPI4"
+#endif
+
+#if STM32_SPI_USE_SPI5 && \
+ !STM32_DMA_IS_VALID_PRIORITY(STM32_SPI_SPI5_DMA_PRIORITY)
+#error "Invalid DMA priority assigned to SPI5"
+#endif
+
+#if STM32_SPI_USE_SPI6 && \
+ !STM32_DMA_IS_VALID_PRIORITY(STM32_SPI_SPI6_DMA_PRIORITY)
+#error "Invalid DMA priority assigned to SPI6"
+#endif
+
/* The following checks are only required when there is a DMA able to
reassign streams to different channels.*/
#if STM32_ADVANCED_DMA
@@ -194,6 +315,21 @@
#error "SPI3 DMA streams not defined"
#endif
+#if STM32_SPI_USE_SPI4 && (!defined(STM32_SPI_SPI4_RX_DMA_STREAM) || \
+ !defined(STM32_SPI_SPI4_TX_DMA_STREAM))
+#error "SPI4 DMA streams not defined"
+#endif
+
+#if STM32_SPI_USE_SPI5 && (!defined(STM32_SPI_SPI5_RX_DMA_STREAM) || \
+ !defined(STM32_SPI_SPI5_TX_DMA_STREAM))
+#error "SPI5 DMA streams not defined"
+#endif
+
+#if STM32_SPI_USE_SPI6 && (!defined(STM32_SPI_SPI6_RX_DMA_STREAM) || \
+ !defined(STM32_SPI_SPI6_TX_DMA_STREAM))
+#error "SPI6 DMA streams not defined"
+#endif
+
/* Check on the validity of the assigned DMA channels.*/
#if STM32_SPI_USE_SPI1 && \
!STM32_DMA_IS_VALID_ID(STM32_SPI_SPI1_RX_DMA_STREAM, STM32_SPI1_RX_DMA_MSK)
@@ -224,6 +360,36 @@
!STM32_DMA_IS_VALID_ID(STM32_SPI_SPI3_TX_DMA_STREAM, STM32_SPI3_TX_DMA_MSK)
#error "invalid DMA stream associated to SPI3 TX"
#endif
+
+#if STM32_SPI_USE_SPI4 && \
+ !STM32_DMA_IS_VALID_ID(STM32_SPI_SPI4_RX_DMA_STREAM, STM32_SPI4_RX_DMA_MSK)
+#error "invalid DMA stream associated to SPI4 RX"
+#endif
+
+#if STM32_SPI_USE_SPI4 && \
+ !STM32_DMA_IS_VALID_ID(STM32_SPI_SPI4_TX_DMA_STREAM, STM32_SPI4_TX_DMA_MSK)
+#error "invalid DMA stream associated to SPI4 TX"
+#endif
+
+#if STM32_SPI_USE_SPI5 && \
+ !STM32_DMA_IS_VALID_ID(STM32_SPI_SPI5_RX_DMA_STREAM, STM32_SPI5_RX_DMA_MSK)
+#error "invalid DMA stream associated to SPI5 RX"
+#endif
+
+#if STM32_SPI_USE_SPI5 && \
+ !STM32_DMA_IS_VALID_ID(STM32_SPI_SPI5_TX_DMA_STREAM, STM32_SPI5_TX_DMA_MSK)
+#error "invalid DMA stream associated to SPI5 TX"
+#endif
+
+#if STM32_SPI_USE_SPI6 && \
+ !STM32_DMA_IS_VALID_ID(STM32_SPI_SPI6_RX_DMA_STREAM, STM32_SPI6_RX_DMA_MSK)
+#error "invalid DMA stream associated to SPI6 RX"
+#endif
+
+#if STM32_SPI_USE_SPI6 && \
+ !STM32_DMA_IS_VALID_ID(STM32_SPI_SPI6_TX_DMA_STREAM, STM32_SPI6_TX_DMA_MSK)
+#error "invalid DMA stream associated to SPI6 TX"
+#endif
#endif /* STM32_ADVANCED_DMA */
#if !defined(STM32_DMA_REQUIRED)
@@ -344,6 +510,18 @@ extern SPIDriver SPID2;
extern SPIDriver SPID3;
#endif
+#if STM32_SPI_USE_SPI4 && !defined(__DOXYGEN__)
+extern SPIDriver SPID4;
+#endif
+
+#if STM32_SPI_USE_SPI5 && !defined(__DOXYGEN__)
+extern SPIDriver SPID5;
+#endif
+
+#if STM32_SPI_USE_SPI6 && !defined(__DOXYGEN__)
+extern SPIDriver SPID6;
+#endif
+
#ifdef __cplusplus
extern "C" {
#endif