Merged in antmerlino/nuttx/spi-initialize (pull request #746)

This change is needed specifically for the case where a bootloader sets the SPE bit before starting NuttX.  In that case, the test in the SPI driver is bogus.  This change fixes that by assuring that NuttX has booted and initialized at least once (whether or not SPE is set) before the driver starts refusing to initialize.

arch/arm/stm32*: Don't rely on SPI_CR1_SPE to determine if peripheral has been initialized yet.

Approved-by: GregoryN <gnutt@nuttx.org>
This commit is contained in:
Anthony Merlino 2018-11-01 16:00:27 +00:00 committed by GregoryN
parent 933d38a209
commit 7f10234468
5 changed files with 156 additions and 126 deletions

View File

@ -284,26 +284,27 @@ struct stm32_transport_s
struct stm32_i2s_s struct stm32_i2s_s
{ {
struct i2s_dev_s dev; /* Externally visible I2S interface */ struct i2s_dev_s dev; /* Externally visible I2S interface */
uintptr_t base; /* I2S controller register base address */ uintptr_t base; /* I2S controller register base address */
sem_t exclsem; /* Assures mutually exclusive acess to I2S */ sem_t exclsem; /* Assures mutually exclusive acess to I2S */
uint8_t datalen; /* Data width (8 or 16) */ bool initialized; /* Has I2S interface been initialized */
uint8_t datalen; /* Data width (8 or 16) */
#ifdef CONFIG_DEBUG_FEATURES #ifdef CONFIG_DEBUG_FEATURES
uint8_t align; /* Log2 of data width (0 or 1) */ uint8_t align; /* Log2 of data width (0 or 1) */
#endif #endif
uint8_t rxenab:1; /* True: RX transfers enabled */ uint8_t rxenab:1; /* True: RX transfers enabled */
uint8_t txenab:1; /* True: TX transfers enabled */ uint8_t txenab:1; /* True: TX transfers enabled */
uint8_t i2sno:6; /* I2S controller number (0 or 1) */ uint8_t i2sno:6; /* I2S controller number (0 or 1) */
#ifdef I2S_HAVE_MCK #ifdef I2S_HAVE_MCK
uint32_t samplerate; /* Data sample rate (determines only MCK divider) */ uint32_t samplerate; /* Data sample rate (determines only MCK divider) */
#endif #endif
uint32_t rxccr; /* DMA control register for RX transfers */ uint32_t rxccr; /* DMA control register for RX transfers */
uint32_t txccr; /* DMA control register for TX transfers */ uint32_t txccr; /* DMA control register for TX transfers */
#ifdef I2S_HAVE_RX #ifdef I2S_HAVE_RX
struct stm32_transport_s rx; /* RX transport state */ struct stm32_transport_s rx; /* RX transport state */
#endif #endif
#ifdef I2S_HAVE_TX #ifdef I2S_HAVE_TX
struct stm32_transport_s tx; /* TX transport state */ struct stm32_transport_s tx; /* TX transport state */
#endif #endif
/* Pre-allocated pool of buffer containers */ /* Pre-allocated pool of buffer containers */
@ -2457,15 +2458,16 @@ static void i2s2_configure(struct stm32_i2s_s *priv)
#ifdef CONFIG_STM32_I2S2_RX #ifdef CONFIG_STM32_I2S2_RX
priv->rxenab = true; priv->rxenab = true;
if ((i2s_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure I2S2 pins: MCK, SD, CK, WS */ /* Configure I2S2 pins: MCK, SD, CK, WS */
stm32_configgpio(GPIO_I2S2_MCK); stm32_configgpio(GPIO_I2S2_MCK);
stm32_configgpio(GPIO_I2S2_SD); stm32_configgpio(GPIO_I2S2_SD);
stm32_configgpio(GPIO_I2S2_CK); stm32_configgpio(GPIO_I2S2_CK);
stm32_configgpio(GPIO_I2S2_WS); stm32_configgpio(GPIO_I2S2_WS);
} priv->initialized = true;
}
#endif /* CONFIG_STM32_I2S2_RX */ #endif /* CONFIG_STM32_I2S2_RX */
#ifdef CONFIG_STM32_I2S2_TX #ifdef CONFIG_STM32_I2S2_TX
@ -2473,15 +2475,16 @@ static void i2s2_configure(struct stm32_i2s_s *priv)
/* Only configure if the port is not already configured */ /* Only configure if the port is not already configured */
if ((i2s_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure I2S2 pins: MCK, SD, CK, WS */ /* Configure I2S2 pins: MCK, SD, CK, WS */
stm32_configgpio(GPIO_I2S2_MCK); stm32_configgpio(GPIO_I2S2_MCK);
stm32_configgpio(GPIO_I2S2_SD); stm32_configgpio(GPIO_I2S2_SD);
stm32_configgpio(GPIO_I2S2_CK); stm32_configgpio(GPIO_I2S2_CK);
stm32_configgpio(GPIO_I2S2_WS); stm32_configgpio(GPIO_I2S2_WS);
} priv->initialized = true;
}
#endif /* CONFIG_STM32_I2S2_TX */ #endif /* CONFIG_STM32_I2S2_TX */
/* Configure driver state specific to this I2S peripheral */ /* Configure driver state specific to this I2S peripheral */
@ -2520,7 +2523,7 @@ static void i2s3_configure(struct stm32_i2s_s *priv)
#ifdef CONFIG_STM32_I2S3_RX #ifdef CONFIG_STM32_I2S3_RX
priv->rxenab = true; priv->rxenab = true;
if ((i2s_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure I2S3 pins: MCK, SD, CK, WS */ /* Configure I2S3 pins: MCK, SD, CK, WS */
@ -2528,6 +2531,7 @@ static void i2s3_configure(struct stm32_i2s_s *priv)
stm32_configgpio(GPIO_I2S3_SD); stm32_configgpio(GPIO_I2S3_SD);
stm32_configgpio(GPIO_I2S3_CK); stm32_configgpio(GPIO_I2S3_CK);
stm32_configgpio(GPIO_I2S3_WS); stm32_configgpio(GPIO_I2S3_WS);
priv->initialized = true;
} }
#endif /* CONFIG_STM32_I2S3_RX */ #endif /* CONFIG_STM32_I2S3_RX */
@ -2536,7 +2540,7 @@ static void i2s3_configure(struct stm32_i2s_s *priv)
/* Only configure if the port is not already configured */ /* Only configure if the port is not already configured */
if ((i2s_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure I2S3 pins: MCK, SD, CK, WS */ /* Configure I2S3 pins: MCK, SD, CK, WS */
@ -2544,6 +2548,7 @@ static void i2s3_configure(struct stm32_i2s_s *priv)
stm32_configgpio(GPIO_I2S3_SD); stm32_configgpio(GPIO_I2S3_SD);
stm32_configgpio(GPIO_I2S3_CK); stm32_configgpio(GPIO_I2S3_CK);
stm32_configgpio(GPIO_I2S3_WS); stm32_configgpio(GPIO_I2S3_WS);
priv->initialized = true;
} }
#endif /* CONFIG_STM32_I2S3_TX */ #endif /* CONFIG_STM32_I2S3_TX */

View File

@ -164,29 +164,30 @@
struct stm32_spidev_s struct stm32_spidev_s
{ {
struct spi_dev_s spidev; /* Externally visible part of the SPI interface */ struct spi_dev_s spidev; /* Externally visible part of the SPI interface */
uint32_t spibase; /* SPIn base address */ uint32_t spibase; /* SPIn base address */
uint32_t spiclock; /* Clocking for the SPI module */ uint32_t spiclock; /* Clocking for the SPI module */
#ifdef CONFIG_STM32_SPI_INTERRUPTS #ifdef CONFIG_STM32_SPI_INTERRUPTS
uint8_t spiirq; /* SPI IRQ number */ uint8_t spiirq; /* SPI IRQ number */
#endif #endif
#ifdef CONFIG_STM32_SPI_DMA #ifdef CONFIG_STM32_SPI_DMA
volatile uint8_t rxresult; /* Result of the RX DMA */ volatile uint8_t rxresult; /* Result of the RX DMA */
volatile uint8_t txresult; /* Result of the RX DMA */ volatile uint8_t txresult; /* Result of the RX DMA */
uint8_t rxch; /* The RX DMA channel number */ uint8_t rxch; /* The RX DMA channel number */
uint8_t txch; /* The TX DMA channel number */ uint8_t txch; /* The TX DMA channel number */
DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */ DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */
DMA_HANDLE txdma; /* DMA channel handle for TX transfers */ DMA_HANDLE txdma; /* DMA channel handle for TX transfers */
sem_t rxsem; /* Wait for RX DMA to complete */ sem_t rxsem; /* Wait for RX DMA to complete */
sem_t txsem; /* Wait for TX DMA to complete */ sem_t txsem; /* Wait for TX DMA to complete */
uint32_t txccr; /* DMA control register for TX transfers */ uint32_t txccr; /* DMA control register for TX transfers */
uint32_t rxccr; /* DMA control register for RX transfers */ uint32_t rxccr; /* DMA control register for RX transfers */
#endif #endif
sem_t exclsem; /* Held while chip is selected for mutual exclusion */ bool initialized; /* Has SPI interface been initialized */
uint32_t frequency; /* Requested clock frequency */ sem_t exclsem; /* Held while chip is selected for mutual exclusion */
uint32_t actual; /* Actual clock frequency */ uint32_t frequency; /* Requested clock frequency */
uint8_t nbits; /* Width of word in bits (4 through 16) */ uint32_t actual; /* Actual clock frequency */
uint8_t mode; /* Mode 0,1,2,3 */ uint8_t nbits; /* Width of word in bits (4 through 16) */
uint8_t mode; /* Mode 0,1,2,3 */
}; };
/************************************************************************************ /************************************************************************************
@ -1842,7 +1843,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI1 pins: SCK, MISO, and MOSI */ /* Configure SPI1 pins: SCK, MISO, and MOSI */
@ -1853,6 +1854,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1866,7 +1868,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI2 pins: SCK, MISO, and MOSI */ /* Configure SPI2 pins: SCK, MISO, and MOSI */
@ -1877,6 +1879,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1890,7 +1893,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI3 pins: SCK, MISO, and MOSI */ /* Configure SPI3 pins: SCK, MISO, and MOSI */
@ -1901,6 +1904,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1914,7 +1918,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI4 pins: SCK, MISO, and MOSI */ /* Configure SPI4 pins: SCK, MISO, and MOSI */
@ -1925,6 +1929,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1938,7 +1943,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI5 pins: SCK, MISO, and MOSI */ /* Configure SPI5 pins: SCK, MISO, and MOSI */
@ -1949,6 +1954,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1962,7 +1968,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI6 pins: SCK, MISO, and MOSI */ /* Configure SPI6 pins: SCK, MISO, and MOSI */
@ -1973,6 +1979,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else

View File

@ -144,31 +144,32 @@
struct stm32_spidev_s struct stm32_spidev_s
{ {
struct spi_dev_s spidev; /* Externally visible part of the SPI interface */ struct spi_dev_s spidev; /* Externally visible part of the SPI interface */
uint32_t spibase; /* SPIn base address */ uint32_t spibase; /* SPIn base address */
uint32_t spiclock; /* Clocking for the SPI module */ uint32_t spiclock; /* Clocking for the SPI module */
#ifdef CONFIG_STM32F7_SPI_INTERRUPTS #ifdef CONFIG_STM32F7_SPI_INTERRUPTS
uint8_t spiirq; /* SPI IRQ number */ uint8_t spiirq; /* SPI IRQ number */
#endif #endif
#ifdef CONFIG_STM32F7_SPI_DMA #ifdef CONFIG_STM32F7_SPI_DMA
volatile uint8_t rxresult; /* Result of the RX DMA */ volatile uint8_t rxresult; /* Result of the RX DMA */
volatile uint8_t txresult; /* Result of the RX DMA */ volatile uint8_t txresult; /* Result of the RX DMA */
uint8_t rxch; /* The RX DMA channel number */ uint8_t rxch; /* The RX DMA channel number */
uint8_t txch; /* The TX DMA channel number */ uint8_t txch; /* The TX DMA channel number */
DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */ DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */
DMA_HANDLE txdma; /* DMA channel handle for TX transfers */ DMA_HANDLE txdma; /* DMA channel handle for TX transfers */
sem_t rxsem; /* Wait for RX DMA to complete */ sem_t rxsem; /* Wait for RX DMA to complete */
sem_t txsem; /* Wait for TX DMA to complete */ sem_t txsem; /* Wait for TX DMA to complete */
uint32_t txccr; /* DMA control register for TX transfers */ uint32_t txccr; /* DMA control register for TX transfers */
uint32_t rxccr; /* DMA control register for RX transfers */ uint32_t rxccr; /* DMA control register for RX transfers */
#endif #endif
sem_t exclsem; /* Held while chip is selected for mutual exclusion */ bool initialized; /* Has SPI interface been initialized */
uint32_t frequency; /* Requested clock frequency */ sem_t exclsem; /* Held while chip is selected for mutual exclusion */
uint32_t actual; /* Actual clock frequency */ uint32_t frequency; /* Requested clock frequency */
int8_t nbits; /* Width of word in bits */ uint32_t actual; /* Actual clock frequency */
uint8_t mode; /* Mode 0,1,2,3 */ int8_t nbits; /* Width of word in bits */
uint8_t mode; /* Mode 0,1,2,3 */
#ifdef CONFIG_PM #ifdef CONFIG_PM
struct pm_callback_s pm_cb; /* PM callbacks */ struct pm_callback_s pm_cb; /* PM callbacks */
#endif #endif
}; };
@ -1927,7 +1928,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI1 pins: SCK, MISO, and MOSI */ /* Configure SPI1 pins: SCK, MISO, and MOSI */
@ -1938,6 +1939,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1951,7 +1953,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI2 pins: SCK, MISO, and MOSI */ /* Configure SPI2 pins: SCK, MISO, and MOSI */
@ -1962,6 +1964,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1975,7 +1978,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI3 pins: SCK, MISO, and MOSI */ /* Configure SPI3 pins: SCK, MISO, and MOSI */
@ -1986,6 +1989,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1999,7 +2003,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI4 pins: SCK, MISO, and MOSI */ /* Configure SPI4 pins: SCK, MISO, and MOSI */
@ -2010,6 +2014,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2023,7 +2028,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI5 pins: SCK, MISO, and MOSI */ /* Configure SPI5 pins: SCK, MISO, and MOSI */
@ -2034,6 +2039,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2047,7 +2053,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI6 pins: SCK, MISO, and MOSI */ /* Configure SPI6 pins: SCK, MISO, and MOSI */
@ -2058,6 +2064,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else

View File

@ -187,31 +187,32 @@
struct stm32_spidev_s struct stm32_spidev_s
{ {
struct spi_dev_s spidev; /* Externally visible part of the SPI interface */ struct spi_dev_s spidev; /* Externally visible part of the SPI interface */
uint32_t spibase; /* SPIn base address */ uint32_t spibase; /* SPIn base address */
uint32_t spiclock; /* Clocking for the SPI module */ uint32_t spiclock; /* Clocking for the SPI module */
#ifdef CONFIG_STM32H7_SPI_INTERRUPTS #ifdef CONFIG_STM32H7_SPI_INTERRUPTS
uint8_t spiirq; /* SPI IRQ number */ uint8_t spiirq; /* SPI IRQ number */
#endif #endif
#ifdef CONFIG_STM32H7_SPI_DMA #ifdef CONFIG_STM32H7_SPI_DMA
volatile uint8_t rxresult; /* Result of the RX DMA */ volatile uint8_t rxresult; /* Result of the RX DMA */
volatile uint8_t txresult; /* Result of the RX DMA */ volatile uint8_t txresult; /* Result of the RX DMA */
uint8_t rxch; /* The RX DMA channel number */ uint8_t rxch; /* The RX DMA channel number */
uint8_t txch; /* The TX DMA channel number */ uint8_t txch; /* The TX DMA channel number */
DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */ DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */
DMA_HANDLE txdma; /* DMA channel handle for TX transfers */ DMA_HANDLE txdma; /* DMA channel handle for TX transfers */
sem_t rxsem; /* Wait for RX DMA to complete */ sem_t rxsem; /* Wait for RX DMA to complete */
sem_t txsem; /* Wait for TX DMA to complete */ sem_t txsem; /* Wait for TX DMA to complete */
uint32_t txccr; /* DMA control register for TX transfers */ uint32_t txccr; /* DMA control register for TX transfers */
uint32_t rxccr; /* DMA control register for RX transfers */ uint32_t rxccr; /* DMA control register for RX transfers */
#endif #endif
sem_t exclsem; /* Held while chip is selected for mutual exclusion */ bool initialized; /* Has SPI interface been initialized */
uint32_t frequency; /* Requested clock frequency */ sem_t exclsem; /* Held while chip is selected for mutual exclusion */
uint32_t actual; /* Actual clock frequency */ uint32_t frequency; /* Requested clock frequency */
int8_t nbits; /* Width of word in bits */ uint32_t actual; /* Actual clock frequency */
uint8_t mode; /* Mode 0,1,2,3 */ int8_t nbits; /* Width of word in bits */
uint8_t mode; /* Mode 0,1,2,3 */
#ifdef CONFIG_PM #ifdef CONFIG_PM
struct pm_callback_s pm_cb; /* PM callbacks */ struct pm_callback_s pm_cb; /* PM callbacks */
#endif #endif
}; };
@ -1998,7 +1999,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI1 pins: SCK, MISO, and MOSI */ /* Configure SPI1 pins: SCK, MISO, and MOSI */
@ -2009,6 +2010,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2022,7 +2024,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI2 pins: SCK, MISO, and MOSI */ /* Configure SPI2 pins: SCK, MISO, and MOSI */
@ -2033,6 +2035,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2046,7 +2049,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI3 pins: SCK, MISO, and MOSI */ /* Configure SPI3 pins: SCK, MISO, and MOSI */
@ -2057,6 +2060,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2070,7 +2074,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI4 pins: SCK, MISO, and MOSI */ /* Configure SPI4 pins: SCK, MISO, and MOSI */
@ -2081,6 +2085,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2094,7 +2099,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI5 pins: SCK, MISO, and MOSI */ /* Configure SPI5 pins: SCK, MISO, and MOSI */
@ -2105,6 +2110,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -2118,7 +2124,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI6 pins: SCK, MISO, and MOSI */ /* Configure SPI6 pins: SCK, MISO, and MOSI */
@ -2129,6 +2135,7 @@ FAR struct spi_dev_s *stm32_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else

View File

@ -145,31 +145,32 @@
struct stm32l4_spidev_s struct stm32l4_spidev_s
{ {
struct spi_dev_s spidev; /* Externally visible part of the SPI interface */ struct spi_dev_s spidev; /* Externally visible part of the SPI interface */
uint32_t spibase; /* SPIn base address */ uint32_t spibase; /* SPIn base address */
uint32_t spiclock; /* Clocking for the SPI module */ uint32_t spiclock; /* Clocking for the SPI module */
#ifdef CONFIG_STM32L4_SPI_INTERRUPTS #ifdef CONFIG_STM32L4_SPI_INTERRUPTS
uint8_t spiirq; /* SPI IRQ number */ uint8_t spiirq; /* SPI IRQ number */
#endif #endif
#ifdef CONFIG_STM32L4_SPI_DMA #ifdef CONFIG_STM32L4_SPI_DMA
volatile uint8_t rxresult; /* Result of the RX DMA */ volatile uint8_t rxresult; /* Result of the RX DMA */
volatile uint8_t txresult; /* Result of the RX DMA */ volatile uint8_t txresult; /* Result of the RX DMA */
uint16_t rxch; /* The RX DMA channel number */ uint16_t rxch; /* The RX DMA channel number */
uint16_t txch; /* The TX DMA channel number */ uint16_t txch; /* The TX DMA channel number */
DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */ DMA_HANDLE rxdma; /* DMA channel handle for RX transfers */
DMA_HANDLE txdma; /* DMA channel handle for TX transfers */ DMA_HANDLE txdma; /* DMA channel handle for TX transfers */
sem_t rxsem; /* Wait for RX DMA to complete */ sem_t rxsem; /* Wait for RX DMA to complete */
sem_t txsem; /* Wait for TX DMA to complete */ sem_t txsem; /* Wait for TX DMA to complete */
uint32_t txccr; /* DMA control register for TX transfers */ uint32_t txccr; /* DMA control register for TX transfers */
uint32_t rxccr; /* DMA control register for RX transfers */ uint32_t rxccr; /* DMA control register for RX transfers */
#endif #endif
sem_t exclsem; /* Held while chip is selected for mutual exclusion */ bool initialized; /* Has SPI interface been initialized */
uint32_t frequency; /* Requested clock frequency */ sem_t exclsem; /* Held while chip is selected for mutual exclusion */
uint32_t actual; /* Actual clock frequency */ uint32_t frequency; /* Requested clock frequency */
uint8_t nbits; /* Width of word in bits (4 through 16) */ uint32_t actual; /* Actual clock frequency */
uint8_t mode; /* Mode 0,1,2,3 */ uint8_t nbits; /* Width of word in bits (4 through 16) */
uint8_t mode; /* Mode 0,1,2,3 */
#ifdef CONFIG_PM #ifdef CONFIG_PM
struct pm_callback_s pm_cb; /* PM callbacks */ struct pm_callback_s pm_cb; /* PM callbacks */
#endif #endif
}; };
@ -1701,7 +1702,7 @@ FAR struct spi_dev_s *stm32l4_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32L4_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI1 pins: SCK, MISO, and MOSI */ /* Configure SPI1 pins: SCK, MISO, and MOSI */
@ -1712,6 +1713,7 @@ FAR struct spi_dev_s *stm32l4_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1725,7 +1727,7 @@ FAR struct spi_dev_s *stm32l4_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32L4_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI2 pins: SCK, MISO, and MOSI */ /* Configure SPI2 pins: SCK, MISO, and MOSI */
@ -1736,6 +1738,7 @@ FAR struct spi_dev_s *stm32l4_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else
@ -1749,7 +1752,7 @@ FAR struct spi_dev_s *stm32l4_spibus_initialize(int bus)
/* Only configure if the bus is not already configured */ /* Only configure if the bus is not already configured */
if ((spi_getreg(priv, STM32L4_SPI_CR1_OFFSET) & SPI_CR1_SPE) == 0) if (!priv->initialized)
{ {
/* Configure SPI3 pins: SCK, MISO, and MOSI */ /* Configure SPI3 pins: SCK, MISO, and MOSI */
@ -1760,6 +1763,7 @@ FAR struct spi_dev_s *stm32l4_spibus_initialize(int bus)
/* Set up default configuration: Master, 8-bit, etc. */ /* Set up default configuration: Master, 8-bit, etc. */
spi_bus_initialize(priv); spi_bus_initialize(priv);
priv->initialized = true;
} }
} }
else else