From accd99db25ebcbc8a9cb080b431d01a74f540778 Mon Sep 17 00:00:00 2001 From: Gregory Nutt Date: Sat, 23 Jan 2016 15:12:45 -0600 Subject: [PATCH] Add an optional hwfeatures method to the SPI interface --- ChangeLog | 2 ++ arch | 2 +- configs | 2 +- drivers/spi/Kconfig | 17 +++++++++++++ drivers/spi/spi_bitbang.c | 29 ++++++++++++---------- include/nuttx/spi/spi.h | 51 ++++++++++++++++++++++++++++++++++++++- 6 files changed, 87 insertions(+), 16 deletions(-) diff --git a/ChangeLog b/ChangeLog index 1d6caa8bc7..7ba0f26784 100755 --- a/ChangeLog +++ b/ChangeLog @@ -11348,4 +11348,6 @@ buffering and race conditions. These were necessary for for the NuttX networking later to be stable in some stress testing. From Andrew Webster (2016-01-22). + * include/spi/spi.h: Add an optional hwfeaqtures() method to the + SPI interface (2016-01-22). diff --git a/arch b/arch index eabf13f41e..10e420a652 160000 --- a/arch +++ b/arch @@ -1 +1 @@ -Subproject commit eabf13f41e38c104b907bb4cb29655b3cba9f35f +Subproject commit 10e420a652fd8bcf9441f542172182f5db05e70a diff --git a/configs b/configs index bc84da3069..5f36fcd26e 160000 --- a/configs +++ b/configs @@ -1 +1 @@ -Subproject commit bc84da30695b62f2d559ce49993b72489d605480 +Subproject commit 5f36fcd26edfb955c28974a2d335ad5e82a3c515 diff --git a/drivers/spi/Kconfig b/drivers/spi/Kconfig index 488c08c251..c416b67b56 100644 --- a/drivers/spi/Kconfig +++ b/drivers/spi/Kconfig @@ -62,6 +62,23 @@ config SPI_BITBANG Enable support for a generic SPI bit-bang device. See include/nuttx/spi/spi_bitbang.h for further information. +config SPI_HWFEATURES + bool + default n + ---help--- + Selected only if a specific H/W feature is selected. This is + basically the OR of any specific hardware feature and eanbles + the SPI hwfeatures() interface method. + +config SPI_CRCGENERATION + bool + default n + select SPI_HWFEATURES + ---help--- + Selected by MCU Kconfig logic if implementation supports automatic + generation of SPI CRCs. Enables the HWFEAT_CRCGENERATION option + as well as the hwfeartures() interface method. + if SPI_BITBANG config SPI_BITBANG_VARWIDTH diff --git a/drivers/spi/spi_bitbang.c b/drivers/spi/spi_bitbang.c index fae90a75ad..7f3a41c549 100644 --- a/drivers/spi/spi_bitbang.c +++ b/drivers/spi/spi_bitbang.c @@ -1,7 +1,7 @@ /**************************************************************************** * drivers/spi/spi_bitbang.c * - * Copyright (C) 2013 Gregory Nutt. All rights reserved. + * Copyright (C) 2013, 2016 Gregory Nutt. All rights reserved. * Author: Gregory Nutt * * Redistribution and use in source and binary forms, with or without @@ -145,24 +145,27 @@ static int spi_cmddata(FAR struct spi_dev_s *dev, enum spi_dev_e devid, static const struct spi_ops_s g_spiops = { #ifndef CONFIG_SPI_OWNBUS - .lock = spi_lock, + spi_lock, /* lock */ #endif - .select = spi_select, - .setfrequency = spi_setfrequency, - .setmode = spi_setmode, - .setbits = spi_setbits, - .status = spi_status, + spi_select, /* select */ + spi_setfrequency, /* setfrequency */ + spi_setmode, /* setmode */ + spi_setbits, /* setbits */ +#ifdef CONFIG_SPI_HWFEATURES + 0, /* hwfeatures */ +#endif + spi_status, /* status */ #ifdef CONFIG_SPI_CMDDATA - .cmddata = spi_cmddata, + spi_cmddata, /* cmddata */ #endif - .send = spi_send, + spi_send, /* send */ #ifdef CONFIG_SPI_EXCHANGE - .exchange = spi_exchange, + spi_exchange, /* exchange */ #else - .sndblock = spi_sndblock, - .recvblock = spi_recvblock, + spi_sndblock, /* sndblock */ + spi_recvblock, /* recvblock */ #endif - .registercallback = 0, /* Not implemented */ + 0 /* registercallback */ }; /**************************************************************************** diff --git a/include/nuttx/spi/spi.h b/include/nuttx/spi/spi.h index ebd4d872e1..fb2b012c97 100644 --- a/include/nuttx/spi/spi.h +++ b/include/nuttx/spi/spi.h @@ -1,7 +1,7 @@ /**************************************************************************** * include/nuttx/spi/spi.h * - * Copyright(C) 2008-2013, 2015 Gregory Nutt. All rights reserved. + * Copyright(C) 2008-2013, 2015-2016 Gregory Nutt. All rights reserved. * Author: Gregory Nutt * * Redistribution and use in source and binary forms, with or without @@ -45,6 +45,7 @@ #include #include #include +#include /**************************************************************************** * Pre-processor Definitions @@ -166,6 +167,44 @@ #define SPI_SETBITS(d,b) \ do { if ((d)->ops->setbits) (d)->ops->setbits(d,b); } while (0) +/**************************************************************************** + * Name: SPI_HWFEATURES + * + * Description: + * Set hardware-specific feature flags. + * + * Input Parameters: + * dev - Device-specific state data + * flags - H/W feature flags + * + * Returned Value: + * Zero (OK) if the selected H/W features are enabled; A negated errno + * value if any H/W feature is not supportable. + * + ****************************************************************************/ + +#ifdef CONFIG_SPI_HWFEATURES + /* If there are multiple SPI drivers, some may not support hardware + * feature selection. + */ + +# define SPI_HWFEATURES(d,f) \ + (((d)->ops->hwfeatures) ? (d)->ops->hwfeatures(d,f) : ((f) == 0 ? OK : -ENOSYS)) + + /* These are currently defined feature flags */ + +# ifdef CONFIG_SPI_CRCGENERATION +# HWFEAT_CRCGENERATION (1 << 0) /* Bit 0: Hardward CRC generation */ +# endif + +#else + /* Any attempt to select hardware features with CONFIG_SPI_HWFEATURES + * deselected will cause an assertion. + */ + +# define SPI_HWFEATURES(d,f) (((f) == 0) ? OK : -ENOSYS) +#endif + /**************************************************************************** * Name: SPI_STATUS * @@ -378,6 +417,12 @@ enum spi_mode_e SPIDEV_MODE3 /* CPOL=1 CHPHA=1 */ }; +#ifdef CONFIG_SPI_HWFEATURES +/* This is a type wide enough to support all hardware features */ + +typedef uint8_t spi_hwfeatures_t; +#endif + /* The SPI vtable */ struct spi_dev_s; @@ -391,6 +436,10 @@ struct spi_ops_s CODE uint32_t (*setfrequency)(FAR struct spi_dev_s *dev, uint32_t frequency); CODE void (*setmode)(FAR struct spi_dev_s *dev, enum spi_mode_e mode); CODE void (*setbits)(FAR struct spi_dev_s *dev, int nbits); +#ifdef CONFIG_SPI_HWFEATURES + CODE int (*hwfeatures)(FAR struct spi_dev_s *dev, + spi_hwfeatures_t features); +#endif CODE uint8_t (*status)(FAR struct spi_dev_s *dev, enum spi_dev_e devid); #ifdef CONFIG_SPI_CMDDATA CODE int (*cmddata)(FAR struct spi_dev_s *dev, enum spi_dev_e devid,