Backport SPI driver enhancements from SAMA5 to SAM3/4

This commit is contained in:
Gregory Nutt
2014-03-13 10:34:35 -06:00
parent a300a46c8d
commit c0c2fc4afe
7 changed files with 1206 additions and 228 deletions
+43
View File
@@ -454,11 +454,13 @@ config SAM34_SMC
config SAM34_SPI0 config SAM34_SPI0
bool "Serial Peripheral Interface 0 (SPI0)" bool "Serial Peripheral Interface 0 (SPI0)"
default n default n
select SPI
config SAM34_SPI1 config SAM34_SPI1
bool "Serial Peripheral Interface 1 (SPI1)" bool "Serial Peripheral Interface 1 (SPI1)"
default n default n
depends on ARCH_CHIP_SAM3X || ARCH_CHIP_SAM3A depends on ARCH_CHIP_SAM3X || ARCH_CHIP_SAM3A
select SPI
config SAM34_SSC config SAM34_SSC
bool "Synchronous Serial Controller (SSC)" bool "Synchronous Serial Controller (SSC)"
@@ -871,6 +873,47 @@ config GPIOF_IRQ
endif # GPIO_IRQ endif # GPIO_IRQ
endmenu # AT91SAM3/4 GPIO Interrupt Configuration endmenu # AT91SAM3/4 GPIO Interrupt Configuration
if SAM34_SPI0 || SAM34_SPI1
menu "SPI device driver options"
config SAM34_SPI_DMA
bool "SPI DMA"
default n
depends on (SAM34_DMAC0 && SAM34_SPI0) || (SAM34_DMAC1 && SAM34_SPI1)
---help---
Use DMA to improve SPI transfer performance.
config SAM34_SPI_DMATHRESHOLD
int "SPI DMA threshold"
default 4
depends on SAM34_SPI_DMA
---help---
When SPI DMA is enabled, small DMA transfers will still be performed
by polling logic. But we need a threshold value to determine what
is small. That value is provided by SAM34_SPI_DMATHRESHOLD.
config SAM34_SPI_DMADEBUG
bool "SPI DMA transfer debug"
depends on SAM34_SPI_DMA && DEBUG && DEBUG_DMA
default n
---help---
Enable special debug instrumentation analyze SPI DMA data transfers.
This logic is as non-invasive as possible: It samples DMA
registers at key points in the data transfer and then dumps all of
the registers at the end of the transfer.
config SAM34_SPI_REGDEBUG
bool "SPI Register level debug"
depends on DEBUG
default n
---help---
Output detailed register-level SPI device debug information.
Requires also DEBUG.
endmenu # SPI device driver options
endif # SAM34_SPI0 || SAM34_SPI1
if SAM34_EMAC if SAM34_EMAC
menu "AT91SAM3/4 EMAC device driver options" menu "AT91SAM3/4 EMAC device driver options"
+4
View File
@@ -114,4 +114,8 @@ endif
ifeq ($(CONFIG_SAM34_SPI0),y) ifeq ($(CONFIG_SAM34_SPI0),y)
CHIP_CSRCS += sam_spi.c CHIP_CSRCS += sam_spi.c
else
ifeq ($(CONFIG_SAM34_SPI1),y)
CHIP_CSRCS += sam_spi.c
endif
endif endif
+1059 -176
View File
File diff suppressed because it is too large Load Diff
+83 -37
View File
@@ -1,7 +1,7 @@
/************************************************************************************ /****************************************************************************
* arch/arm/src/sam34/sam_spi.h * arch/arm/src/sam34/sam_spi.h
* *
* Copyright (C) 2009-2011, 2013 Gregory Nutt. All rights reserved. * Copyright (C) 2009-2011, 2013-2014 Gregory Nutt. All rights reserved.
* Author: Gregory Nutt <gnutt@nuttx.org> * Author: Gregory Nutt <gnutt@nuttx.org>
* *
* Redistribution and use in source and binary forms, with or without * Redistribution and use in source and binary forms, with or without
@@ -31,14 +31,14 @@
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE. * POSSIBILITY OF SUCH DAMAGE.
* *
************************************************************************************/ ****************************************************************************/
#ifndef __ARCH_ARM_SRC_SAM34_SAM_SPI_H #ifndef __ARCH_ARM_SRC_SAM34_SAM_SPI_H
#define __ARCH_ARM_SRC_SAM34_SAM_SPI_H #define __ARCH_ARM_SRC_SAM34_SAM_SPI_H
/************************************************************************************ /****************************************************************************
* Included Files * Included Files
************************************************************************************/ ****************************************************************************/
#include <nuttx/config.h> #include <nuttx/config.h>
@@ -47,23 +47,53 @@
#include "chip.h" #include "chip.h"
/************************************************************************************ /****************************************************************************
* Definitions * Pre-processor Definitions
************************************************************************************/ ****************************************************************************/
/************************************************************************************ /* The SPI port number used as an input to up_spiinitialize encodes
* information about the SPI controller (0 or 1) and the SPI chip select
* (0-3).
*
* NOTE that this is this is backward compatible with older implementations
* that support only SPI0 and provide only the chip select number to
* up_spiinitialize().
*/
#define __SPI_CS_SHIFT (0) /* Bits 0-1: SPI chip select number */
#define __SPI_CS_MASK (3 << __SPI_CS_SHIFT)
# define __SPI_CS0 (0 << __SPI_CS_SHIFT)
# define __SPI_CS1 (1 << __SPI_CS_SHIFT)
# define __SPI_CS2 (2 << __SPI_CS_SHIFT)
# define __SPI_CS3 (3 << __SPI_CS_SHIFT)
#define __SPI_SPI_SHIFT (2) /* Bit 2: SPI controller number */
#define __SPI_SPI_MASK (1 << __SPI_SPI_SHIFT)
# define __SPI_SPI0 (0 << __SPI_SPI_SHIFT) /* SPI0 */
# define __SPI_SPI1 (1 << __SPI_SPI_SHIFT) /* SPI1 */
#define SPI0_CS0 (__SPI_SPI0 | __SPI_CS0)
#define SPI0_CS1 (__SPI_SPI0 | __SPI_CS1)
#define SPI0_CS2 (__SPI_SPI0 | __SPI_CS2)
#define SPI0_CS3 (__SPI_SPI0 | __SPI_CS3)
#define SPI1_CS0 (__SPI_SPI1 | __SPI_CS0)
#define SPI1_CS1 (__SPI_SPI1 | __SPI_CS1)
#define SPI1_CS2 (__SPI_SPI1 | __SPI_CS2)
#define SPI1_CS3 (__SPI_SPI1 | __SPI_CS3)
/****************************************************************************
* Public Types * Public Types
************************************************************************************/ ****************************************************************************/
/************************************************************************************ /****************************************************************************
* Inline Functions * Inline Functions
************************************************************************************/ ****************************************************************************/
#ifndef __ASSEMBLY__ #ifndef __ASSEMBLY__
/************************************************************************************ /****************************************************************************
* Public Data * Public Data
************************************************************************************/ ****************************************************************************/
#undef EXTERN #undef EXTERN
#if defined(__cplusplus) #if defined(__cplusplus)
@@ -74,33 +104,34 @@ extern "C"
#define EXTERN extern #define EXTERN extern
#endif #endif
/************************************************************************************ /****************************************************************************
* Public Function Prototypes * Public Function Prototypes
************************************************************************************/ ****************************************************************************/
/**************************************************************************** /****************************************************************************
* Name: sam_spiselect, sam_spistatus, and sam_spicmddata * Name: sam_spi[0|1]select, sam_spi[0|1]status, and sam_spi[0|1]cmddata
* *
* Description: * Description:
* These external functions must be provided by board-specific logic. They * These external functions must be provided by board-specific logic.
* include: * They include:
* *
* o sam_spiselect is a functions tomanage the board-specific chip selects * o sam_spi[0|1]select is a functions tomanage the board-specific chip
* o sam_spistatus and sam_spicmddata: Implementations of the status * selects
* and cmddata methods of the SPI interface defined by struct spi_ops_ * o sam_spi[0|1]status and sam_spi[0|1]cmddata: Implementations of the
* (see include/nuttx/spi/spi.h). All other methods including * status and cmddata methods of the SPI interface defined by struct
* spi_ops_ (see include/nuttx/spi/spi.h). All other methods including
* up_spiinitialize()) are provided by common SAM3/4 logic. * up_spiinitialize()) are provided by common SAM3/4 logic.
* *
* To use this common SPI logic on your board: * To use this common SPI logic on your board:
* *
* 1. Provide logic in sam_boardinitialize() to configure SPI chip select * 1. Provide logic in sam_boardinitialize() to configure SPI chip select
* pins. * pins.
* 2. Provide sam_spiselect() and sam_spistatus() functions in your board- * 2. Provide sam_spi[0|1]select() and sam_spi[0|1]status() functions in
* specific logic. These functions will perform chip selection and * our board-specific logic. These functions will perform chip selection
* status operations using GPIOs in the way your board is configured. * and status operations using PIOs in the way your board is configured.
* 2. If CONFIG_SPI_CMDDATA is defined in the NuttX configuration, provide * 2. If CONFIG_SPI_CMDDATA is defined in the NuttX configuration, provide
* sam_spicmddata() functions in your board-specific logic. This * sam_spi[0|1]cmddata() functions in your board-specific logic. This
* function will perform cmd/data selection operations using GPIOs in * function will perform cmd/data selection operations using PIOs in
* the way your board is configured. * the way your board is configured.
* 3. Add a call to up_spiinitialize() in your low level application * 3. Add a call to up_spiinitialize() in your low level application
* initialization logic * initialization logic
@@ -116,7 +147,7 @@ struct spi_dev_s;
enum spi_dev_e; enum spi_dev_e;
/**************************************************************************** /****************************************************************************
* Name: sam_spiselect * Name: sam_spi[0|1]select
* *
* Description: * Description:
* PIO chip select pins may be programmed by the board specific logic in * PIO chip select pins may be programmed by the board specific logic in
@@ -126,9 +157,9 @@ enum spi_dev_e;
* a stub. * a stub.
* *
* An alternative way to program the PIO chip select pins is as a normal * An alternative way to program the PIO chip select pins is as a normal
* GPIO output. In that case, the automatic control of the CS pins is * PIO output. In that case, the automatic control of the CS pins is
* bypassed and this function must provide control of the chip select. * bypassed and this function must provide control of the chip select.
* NOTE: In this case, the GPIO output pin does *not* have to be the * NOTE: In this case, the PIO output pin does *not* have to be the
* same as the NPCS pin normal associated with the chip select number. * same as the NPCS pin normal associated with the chip select number.
* *
* Input Parameters: * Input Parameters:
@@ -141,10 +172,15 @@ enum spi_dev_e;
* *
****************************************************************************/ ****************************************************************************/
void sam_spiselect(enum spi_dev_e devid, bool selected); #ifdef CONFIG_SAM34_SPI0
void sam_spi0select(enum spi_dev_e devid, bool selected);
#endif
#ifdef CONFIG_SAM34_SPI1
void sam_spi1select(enum spi_dev_e devid, bool selected);
#endif
/**************************************************************************** /****************************************************************************
* Name: sam_spistatus * Name: sam_spi[0|1]status
* *
* Description: * Description:
* Return status information associated with the SPI device. * Return status information associated with the SPI device.
@@ -158,10 +194,15 @@ void sam_spiselect(enum spi_dev_e devid, bool selected);
* *
****************************************************************************/ ****************************************************************************/
uint8_t sam_spistatus(FAR struct spi_dev_s *dev, enum spi_dev_e devid); #ifdef CONFIG_SAM34_SPI0
uint8_t sam_spi0status(FAR struct spi_dev_s *dev, enum spi_dev_e devid);
#endif
#ifdef CONFIG_SAM34_SPI1
uint8_t sam_spi1status(FAR struct spi_dev_s *dev, enum spi_dev_e devid);
#endif
/**************************************************************************** /****************************************************************************
* Name: sam_spicmddata * Name: sam_spi[0|1]cmddata
* *
* Description: * Description:
* Some SPI devices require an additional control to determine if the SPI * Some SPI devices require an additional control to determine if the SPI
@@ -172,7 +213,7 @@ uint8_t sam_spistatus(FAR struct spi_dev_s *dev, enum spi_dev_e devid);
* may be configured to use 9-bit data transfers with the 9th bit * may be configured to use 9-bit data transfers with the 9th bit
* indicating command or data. That same hardware may be configurable, * indicating command or data. That same hardware may be configurable,
* instead, to use 8-bit data but to require an additional, board- * instead, to use 8-bit data but to require an additional, board-
* specific GPIO control to distinguish command and data. This function * specific PIO control to distinguish command and data. This function
* would be needed in that latter case. * would be needed in that latter case.
* *
* Input Parameters: * Input Parameters:
@@ -185,7 +226,12 @@ uint8_t sam_spistatus(FAR struct spi_dev_s *dev, enum spi_dev_e devid);
****************************************************************************/ ****************************************************************************/
#ifdef CONFIG_SPI_CMDDATA #ifdef CONFIG_SPI_CMDDATA
int sam_spicmddata(FAR struct spi_dev_s *dev, enum spi_dev_e devid, bool cmd); #ifdef CONFIG_SAM34_SPI0
int sam_spi0cmddata(FAR struct spi_dev_s *dev, enum spi_dev_e devid, bool cmd);
#endif
#ifdef CONFIG_SAM34_SPI1
int sam_spi1cmddata(FAR struct spi_dev_s *dev, enum spi_dev_e devid, bool cmd);
#endif
#endif #endif
#endif /* CONFIG_SAM34_SPI0 */ #endif /* CONFIG_SAM34_SPI0 */
+1 -1
View File
@@ -1310,7 +1310,7 @@ config SAMA5_CAN_REGDEBUG
Output detailed register-level CAN device debug information. Output detailed register-level CAN device debug information.
Requires also DEBUG. Requires also DEBUG.
endmenu # SPI device driver options endmenu # CAN device driver options
endif # SAMA5_CAN0 || SAMA5_CAN1 endif # SAMA5_CAN0 || SAMA5_CAN1
if SAMA5_SPI0 || SAMA5_SPI1 if SAMA5_SPI0 || SAMA5_SPI1
+2
View File
@@ -736,6 +736,7 @@ static void spi_dma_sampledone(struct sam_spics_s *spics)
* *
****************************************************************************/ ****************************************************************************/
#ifdef CONFIG_SAMA5_SPI_DMA
static void spi_dmatimeout(int argc, uint32_t arg) static void spi_dmatimeout(int argc, uint32_t arg)
{ {
struct sam_spics_s *spics = (struct sam_spics_s *)arg; struct sam_spics_s *spics = (struct sam_spics_s *)arg;
@@ -755,6 +756,7 @@ static void spi_dmatimeout(int argc, uint32_t arg)
sem_post(&spics->dmawait); sem_post(&spics->dmawait);
} }
#endif
/**************************************************************************** /****************************************************************************
* Name: spi_rxcallback * Name: spi_rxcallback
+14 -14
View File
@@ -1,4 +1,4 @@
/************************************************************************************ /****************************************************************************
* arch/arm/src/sama5/sam_spi.h * arch/arm/src/sama5/sam_spi.h
* *
* Copyright (C) 2013 Gregory Nutt. All rights reserved. * Copyright (C) 2013 Gregory Nutt. All rights reserved.
@@ -31,14 +31,14 @@
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE. * POSSIBILITY OF SUCH DAMAGE.
* *
************************************************************************************/ ****************************************************************************/
#ifndef __ARCH_ARM_SRC_SAMA5_SAM_SPI_H #ifndef __ARCH_ARM_SRC_SAMA5_SAM_SPI_H
#define __ARCH_ARM_SRC_SAMA5_SAM_SPI_H #define __ARCH_ARM_SRC_SAMA5_SAM_SPI_H
/************************************************************************************ /****************************************************************************
* Included Files * Included Files
************************************************************************************/ ****************************************************************************/
#include <nuttx/config.h> #include <nuttx/config.h>
@@ -47,9 +47,9 @@
#include "chip.h" #include "chip.h"
/************************************************************************************ /****************************************************************************
* Pre-processor Definitions * Pre-processor Definitions
************************************************************************************/ ****************************************************************************/
/* The SPI port number used as an input to up_spiinitialize encodes information /* The SPI port number used as an input to up_spiinitialize encodes information
* about the SPI controller (0 or 1) and the SPI chip select (0-3) * about the SPI controller (0 or 1) and the SPI chip select (0-3)
@@ -76,19 +76,19 @@
#define SPI1_CS2 (__SPI_SPI1 | __SPI_CS2) #define SPI1_CS2 (__SPI_SPI1 | __SPI_CS2)
#define SPI1_CS3 (__SPI_SPI1 | __SPI_CS3) #define SPI1_CS3 (__SPI_SPI1 | __SPI_CS3)
/************************************************************************************ /****************************************************************************
* Public Types * Public Types
************************************************************************************/ ****************************************************************************/
/************************************************************************************ /****************************************************************************
* Inline Functions * Inline Functions
************************************************************************************/ ****************************************************************************/
#ifndef __ASSEMBLY__ #ifndef __ASSEMBLY__
/************************************************************************************ /****************************************************************************
* Public Data * Public Data
************************************************************************************/ ****************************************************************************/
#undef EXTERN #undef EXTERN
#if defined(__cplusplus) #if defined(__cplusplus)
@@ -99,9 +99,9 @@ extern "C"
#define EXTERN extern #define EXTERN extern
#endif #endif
/************************************************************************************ /****************************************************************************
* Public Function Prototypes * Public Function Prototypes
************************************************************************************/ ****************************************************************************/
/**************************************************************************** /****************************************************************************
* Name: sam_spi[0|1]select, sam_spi[0|1]status, and sam_spi[0|1]cmddata * Name: sam_spi[0|1]select, sam_spi[0|1]status, and sam_spi[0|1]cmddata