diff --git a/arch/arm/include/stm32/chip.h b/arch/arm/include/stm32/chip.h index e476bff892e..8f06701b518 100644 --- a/arch/arm/include/stm32/chip.h +++ b/arch/arm/include/stm32/chip.h @@ -1101,7 +1101,6 @@ * c = C (48pins) R (68 pins) V (100 pins) * c = K (32 pins), C (48 pins), R (68 pins), V (100 pins) * f = 6 (32KB FLASH), 8 (64KB FLASH), B (128KB FLASH), C (256KB FLASH) - * f = 8 (64KB FLASH), B (128KB FLASH), C (256KB FLASH) * xxx = Package, temperature range, options (ignored here) */ @@ -1534,7 +1533,8 @@ # define STM32_NLCD 0 /* (0) No LCD */ # define STM32_NUSBOTG 0 /* USB FS device, but no USB OTG FS/HS */ # define STM32_NGPIO 87 /* GPIOA-F */ -# define STM32_NADC 1 /* (3) 12-bit ADC1 */ +# define STM32_NADC 1 /* (1) 12-bit ADC1 */ +# define STM32_NSDADC 3 /* (3) 16-bit SDADC1-3 */ # define STM32_NDAC 2 /* (2) 12-bit DAC1-2 */ # define STM32_NCAPSENSE 0 /* (0) No capacitive sensing channels */ # define STM32_NCRC 1 /* (1) CRC calculation unit */ diff --git a/arch/arm/src/stm32/Kconfig b/arch/arm/src/stm32/Kconfig index f914f760e19..abfdf719855 100644 --- a/arch/arm/src/stm32/Kconfig +++ b/arch/arm/src/stm32/Kconfig @@ -1394,6 +1394,9 @@ config STM32_STM32F37XX select STM32_HAVE_TIM15 select STM32_HAVE_TIM16 select STM32_HAVE_TIM17 + select STM32_HAVE_SDADC1 + select STM32_HAVE_SDADC2 + select STM32_HAVE_SDADC3 select STM32_HAVE_CAN1 select STM32_HAVE_DAC1 select STM32_HAVE_DAC2 @@ -1777,6 +1780,30 @@ config STM32_HAVE_ADC4_DMA bool default n +config STM32_HAVE_SDADC1 + bool + default n + +config STM32_HAVE_SDADC2 + bool + default n + +config STM32_HAVE_SDADC3 + bool + default n + +config STM32_HAVE_SDADC1_DMA + bool + default n + +config STM32_HAVE_SDADC2_DMA + bool + default n + +config STM32_HAVE_SDADC3_DMA + bool + default n + config STM32_HAVE_CAN1 bool default n @@ -1844,6 +1871,7 @@ config STM32_ADC1 default n select STM32_ADC select STM32_HAVE_ADC1_DMA if STM32_STM32F10XX && STM32_DMA1 + select STM32_HAVE_ADC1_DMA if STM32_STM32F37XX && STM32_DMA1 select STM32_HAVE_ADC1_DMA if !STM32_STM32F10XX && STM32_DMA2 config STM32_ADC2 @@ -1867,6 +1895,27 @@ config STM32_ADC4 depends on STM32_HAVE_ADC4 select STM32_HAVE_ADC4_DMA if STM32_DMA2 +config STM32_SDADC1 + bool "SDADC1" + default n + select STM32_SDADC + depends on STM32_HAVE_SDADC1 + select STM32_HAVE_SDADC1_DMA if STM32_DMA2 + +config STM32_SDADC2 + bool "SDADC2" + default n + select STM32_SDADC + depends on STM32_HAVE_SDADC2 + select STM32_HAVE_SDADC2_DMA if STM32_DMA2 + +config STM32_SDADC3 + bool "SDADC3" + default n + select STM32_SDADC + depends on STM32_HAVE_SDADC3 + select STM32_HAVE_SDADC3_DMA if STM32_DMA2 + config STM32_COMP bool "COMP" default n @@ -2239,6 +2288,9 @@ endmenu config STM32_ADC bool +config STM32_SDADC + bool + config STM32_DAC bool @@ -5403,6 +5455,38 @@ config STM32_ADC4_DMA endmenu +menu "SDADC Configuration" + depends on STM32_SDADC + +config STM32_SDADC1_DMA + bool "SDADC1 DMA" + depends on STM32_SDADC1 && STM32_HAVE_SDADC1_DMA + default n + ---help--- + If DMA is selected, then the SDADC may be configured to support + DMA transfer, which is advisable if multiple channels are read + or if very high trigger frequencies are used. + +config STM32_SDADC2_DMA + bool "SDADC2 DMA" + depends on STM32_SDADC2 && STM32_HAVE_SDADC2_DMA + default n + ---help--- + If DMA is selected, then the SDADC may be configured to support + DMA transfer, which is advisable if multiple channels are read + or if very high trigger frequencies are used. + +config STM32_SDADC3_DMA + bool "SDADC3 DMA" + depends on STM32_SDADC3 && STM32_HAVE_SDADC3_DMA + default n + ---help--- + If DMA is selected, then the SDADC may be configured to support + DMA transfer, which is advisable if multiple channels are read + or if very high trigger frequencies are used. + +endmenu + menu "DAC Configuration" depends on STM32_DAC1 || STM32_DAC2 diff --git a/arch/arm/src/stm32/Make.defs b/arch/arm/src/stm32/Make.defs index 31bd92eee42..5cd35648931 100644 --- a/arch/arm/src/stm32/Make.defs +++ b/arch/arm/src/stm32/Make.defs @@ -148,6 +148,8 @@ ifeq ($(CONFIG_STM32_I2C_ALT),y) CHIP_CSRCS += stm32_i2c_alt.c else ifeq ($(CONFIG_STM32_STM32F30XX),y) CHIP_CSRCS += stm32f30xxx_i2c.c +else ifeq ($(CONFIG_STM32_STM32F37XX),y) +CHIP_CSRCS += stm32f30xxx_i2c.c else ifeq ($(CONFIG_STM32_STM32F40XX),y) CHIP_CSRCS += stm32f40xxx_i2c.c else @@ -217,6 +219,10 @@ ifeq ($(CONFIG_STM32_ADC),y) CHIP_CSRCS += stm32_adc.c endif +ifeq ($(CONFIG_STM32_SDADC),y) +CHIP_CSRCS += stm32_sdadc.c +endif + ifeq ($(CONFIG_DAC),y) CHIP_CSRCS += stm32_dac.c endif diff --git a/arch/arm/src/stm32/chip/stm32_dac.h b/arch/arm/src/stm32/chip/stm32_dac.h index 1eadecb8949..81a69b71e68 100644 --- a/arch/arm/src/stm32/chip/stm32_dac.h +++ b/arch/arm/src/stm32/chip/stm32_dac.h @@ -66,20 +66,56 @@ /* Register Addresses ***************************************************************/ -#define STM32_DAC_CR (STM32_DAC_BASE+STM32_DAC_CR_OFFSET) -#define STM32_DAC_SWTRIGR (STM32_DAC_BASE+STM32_DAC_SWTRIGR_OFFSET) -#define STM32_DAC_DHR12R1 (STM32_DAC_BASE+STM32_DAC_DHR12R1_OFFSET) -#define STM32_DAC_DHR12L1 (STM32_DAC_BASE+STM32_DAC_DHR12L1_OFFSET) -#define STM32_DAC_DHR8R1 (STM32_DAC_BASE+STM32_DAC_DHR8R1_OFFSET) -#define STM32_DAC_DHR12R2 (STM32_DAC_BASE+STM32_DAC_DHR12R2_OFFSET) -#define STM32_DAC_DHR12L2 (STM32_DAC_BASE+STM32_DAC_DHR12L2_OFFSET) -#define STM32_DAC_DHR8R2 (STM32_DAC_BASE+STM32_DAC_DHR8R2_OFFSET) -#define STM32_DAC_DHR12RD (STM32_DAC_BASE+STM32_DAC_DHR12RD_OFFSET) -#define STM32_DAC_DHR12LD (STM32_DAC_BASE+STM32_DAC_DHR12LD_OFFSET) -#define STM32_DAC_DHR8RD (STM32_DAC_BASE+STM32_DAC_DHR8RD_OFFSET) -#define STM32_DAC_DOR1 (STM32_DAC_BASE+STM32_DAC_DOR1_OFFSET) -#define STM32_DAC_DOR2 (STM32_DAC_BASE+STM32_DAC_DOR2_OFFSET) -#define STM32_DAC_SR (STM32_DAC_BASE+STM32_DAC_SR_OFFSET) +#if STM32_NDAC < 2 +# define STM32_DAC_CR (STM32_DAC_BASE+STM32_DAC_CR_OFFSET) +# define STM32_DAC_SWTRIGR (STM32_DAC_BASE+STM32_DAC_SWTRIGR_OFFSET) +# define STM32_DAC_DHR12R1 (STM32_DAC_BASE+STM32_DAC_DHR12R1_OFFSET) +# define STM32_DAC_DHR12L1 (STM32_DAC_BASE+STM32_DAC_DHR12L1_OFFSET) +# define STM32_DAC_DHR8R1 (STM32_DAC_BASE+STM32_DAC_DHR8R1_OFFSET) +# define STM32_DAC_DHR12R2 (STM32_DAC_BASE+STM32_DAC_DHR12R2_OFFSET) +# define STM32_DAC_DHR12L2 (STM32_DAC_BASE+STM32_DAC_DHR12L2_OFFSET) +# define STM32_DAC_DHR8R2 (STM32_DAC_BASE+STM32_DAC_DHR8R2_OFFSET) +# define STM32_DAC_DHR12RD (STM32_DAC_BASE+STM32_DAC_DHR12RD_OFFSET) +# define STM32_DAC_DHR12LD (STM32_DAC_BASE+STM32_DAC_DHR12LD_OFFSET) +# define STM32_DAC_DHR8RD (STM32_DAC_BASE+STM32_DAC_DHR8RD_OFFSET) +# define STM32_DAC_DOR1 (STM32_DAC_BASE+STM32_DAC_DOR1_OFFSET) +# define STM32_DAC_DOR2 (STM32_DAC_BASE+STM32_DAC_DOR2_OFFSET) +# define STM32_DAC_SR (STM32_DAC_BASE+STM32_DAC_SR_OFFSET) +#else +/* DAC1 */ + +# define STM32_DAC1_CR (STM32_DAC1_BASE+STM32_DAC_CR_OFFSET) +# define STM32_DAC1_SWTRIGR (STM32_DAC1_BASE+STM32_DAC_SWTRIGR_OFFSET) +# define STM32_DAC1_DHR12R1 (STM32_DAC1_BASE+STM32_DAC_DHR12R1_OFFSET) +# define STM32_DAC1_DHR12L1 (STM32_DAC1_BASE+STM32_DAC_DHR12L1_OFFSET) +# define STM32_DAC1_DHR8R1 (STM32_DAC1_BASE+STM32_DAC_DHR8R1_OFFSET) +# define STM32_DAC1_DHR12R2 (STM32_DAC1_BASE+STM32_DAC_DHR12R2_OFFSET) +# define STM32_DAC1_DHR12L2 (STM32_DAC1_BASE+STM32_DAC_DHR12L2_OFFSET) +# define STM32_DAC1_DHR8R2 (STM32_DAC1_BASE+STM32_DAC_DHR8R2_OFFSET) +# define STM32_DAC1_DHR12RD (STM32_DAC1_BASE+STM32_DAC_DHR12RD_OFFSET) +# define STM32_DAC1_DHR12LD (STM32_DAC1_BASE+STM32_DAC_DHR12LD_OFFSET) +# define STM32_DAC1_DHR8RD (STM32_DAC1_BASE+STM32_DAC_DHR8RD_OFFSET) +# define STM32_DAC1_DOR1 (STM32_DAC1_BASE+STM32_DAC_DOR1_OFFSET) +# define STM32_DAC1_DOR2 (STM32_DAC1_BASE+STM32_DAC_DOR2_OFFSET) +# define STM32_DAC1_SR (STM32_DAC1_BASE+STM32_DAC_SR_OFFSET) + +/* DAC2 */ + +# define STM32_DAC2_CR (STM32_DAC2_BASE+STM32_DAC_CR_OFFSET) +# define STM32_DAC2_SWTRIGR (STM32_DAC2_BASE+STM32_DAC_SWTRIGR_OFFSET) +# define STM32_DAC2_DHR12R1 (STM32_DAC2_BASE+STM32_DAC_DHR12R1_OFFSET) +# define STM32_DAC2_DHR12L1 (STM32_DAC2_BASE+STM32_DAC_DHR12L1_OFFSET) +# define STM32_DAC2_DHR8R1 (STM32_DAC2_BASE+STM32_DAC_DHR8R1_OFFSET) +# define STM32_DAC2_DHR12R2 (STM32_DAC2_BASE+STM32_DAC_DHR12R2_OFFSET) +# define STM32_DAC2_DHR12L2 (STM32_DAC2_BASE+STM32_DAC_DHR12L2_OFFSET) +# define STM32_DAC2_DHR8R2 (STM32_DAC2_BASE+STM32_DAC_DHR8R2_OFFSET) +# define STM32_DAC2_DHR12RD (STM32_DAC2_BASE+STM32_DAC_DHR12RD_OFFSET) +# define STM32_DAC2_DHR12LD (STM32_DAC2_BASE+STM32_DAC_DHR12LD_OFFSET) +# define STM32_DAC2_DHR8RD (STM32_DAC2_BASE+STM32_DAC_DHR8RD_OFFSET) +# define STM32_DAC2_DOR1 (STM32_DAC2_BASE+STM32_DAC_DOR1_OFFSET) +# define STM32_DAC2_DOR2 (STM32_DAC2_BASE+STM32_DAC_DOR2_OFFSET) +# define STM32_DAC2_SR (STM32_DAC2_BASE+STM32_DAC_SR_OFFSET) +#endif /* Register Bitfield Definitions ****************************************************/ diff --git a/arch/arm/src/stm32/chip/stm32_pwr.h b/arch/arm/src/stm32/chip/stm32_pwr.h index 9c1e64e57bd..f2c2fdde0bf 100644 --- a/arch/arm/src/stm32/chip/stm32_pwr.h +++ b/arch/arm/src/stm32/chip/stm32_pwr.h @@ -105,6 +105,12 @@ # endif #endif +#if defined(CONFIG_STM32_STM32F37XX) +#define PWR_CR_ENSD1 (1 << 9) /* Bit 9: Enable SDADC1 */ +#define PWR_CR_ENSD2 (1 << 10) /* Bit 10: Enable SDADC2 */ +#define PWR_CR_ENSD3 (1 << 11) /* Bit 11: Enable SDADC3 */ +#endif + #if defined(CONFIG_STM32_STM32L15XX) # define PWR_CR_ULP (1 << 9) /* Ultralow power mode */ # define PWR_CR_FWU (1 << 10) /* Fast wake-up */ @@ -132,7 +138,8 @@ #define PWR_CSR_SBF (1 << 1) /* Bit 1: Standby Flag */ #define PWR_CSR_PVDO (1 << 2) /* Bit 2: PVD Output */ -#if defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F40XX) +#if defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F37XX) || \ + defined(CONFIG_STM32_STM32F40XX) # define PWR_CSR_BRR (1 << 3) /* Bit 3: Backup regulator ready */ #elif defined(CONFIG_STM32_STM32L15XX) # define PWR_CSR_VREFINTRDYF (1 << 3) /* Bit 3: Internal voltage reference (VREFINT) ready flag */ @@ -143,7 +150,7 @@ #if defined(CONFIG_STM32_STM32F30XX) # define PWR_CSR_EWUP1 (1 << 8) /* Bit 8: Enable WKUP1 pin */ # define PWR_CSR_EWUP2 (1 << 9) /* Bit 9: Enable WKUP2 pin */ -#elif defined(CONFIG_STM32_STM32L15XX) +#elif defined(CONFIG_STM32_STM32L15XX) || defined(CONFIG_STM32_STM32F37XX) # define PWR_CSR_EWUP1 (1 << 8) /* Bit 8: Enable WKUP1 pin */ # define PWR_CSR_EWUP2 (1 << 9) /* Bit 9: Enable WKUP2 pin */ # define PWR_CSR_EWUP3 (1 << 10) /* Bit 8: Enable WKUP3 pin */ diff --git a/arch/arm/src/stm32/chip/stm32f30xxx_adc.h b/arch/arm/src/stm32/chip/stm32f30xxx_adc.h index 5763260eb9c..7c9da24b0c1 100644 --- a/arch/arm/src/stm32/chip/stm32f30xxx_adc.h +++ b/arch/arm/src/stm32/chip/stm32f30xxx_adc.h @@ -60,8 +60,8 @@ #define STM32_ADC_SMPR1_OFFSET 0x0014 /* ADC sample time register 1 */ #define STM32_ADC_SMPR2_OFFSET 0x0018 /* ADC sample time register 2 */ #define STM32_ADC_TR1_OFFSET 0x0020 /* ADC watchdog threshold register 1 */ -#define STM32_ADC_TR2_OFFSET 0x0020 /* ADC watchdog threshold register 2 */ -#define STM32_ADC_TR3_OFFSET 0x0020 /* ADC watchdog threshold register 3 */ +#define STM32_ADC_TR2_OFFSET 0x0024 /* ADC watchdog threshold register 2 */ +#define STM32_ADC_TR3_OFFSET 0x0028 /* ADC watchdog threshold register 3 */ #define STM32_ADC_SQR1_OFFSET 0x0030 /* ADC regular sequence register 1 */ #define STM32_ADC_SQR2_OFFSET 0x0034 /* ADC regular sequence register 2 */ #define STM32_ADC_SQR3_OFFSET 0x0038 /* ADC regular sequence register 3 */ diff --git a/arch/arm/src/stm32/chip/stm32f37xxx_adc.h b/arch/arm/src/stm32/chip/stm32f37xxx_adc.h new file mode 100644 index 00000000000..95a40ade448 --- /dev/null +++ b/arch/arm/src/stm32/chip/stm32f37xxx_adc.h @@ -0,0 +1,321 @@ +/**************************************************************************************************** + * arch/arm/src/stm32/chip/stm32f30xxx_adc.h + * + * Copyright (C) 2009, 2011, 2013 Gregory Nutt. All rights reserved. + * Copyright (C) 2016 Studelec SA. All rights reserved. + * Authors: Gregory Nutt + * Marc Rechté + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************************************/ + +#ifndef __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_ADC_H +#define __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_ADC_H + +/**************************************************************************************************** + * Included Files + ****************************************************************************************************/ + +#include + +#include "chip.h" + +/**************************************************************************************************** + * Pre-processor Definitions + ****************************************************************************************************/ + +/* Register Offsets *********************************************************************************/ + +#define STM32_ADC_SR_OFFSET 0x0000 /* ADC status register */ +#define STM32_ADC_CR1_OFFSET 0x0004 /* ADC control register 1 */ +#define STM32_ADC_CR2_OFFSET 0x0008 /* ADC control register 2 */ +#define STM32_ADC_SMPR1_OFFSET 0x000c /* ADC sample time register 1 */ +#define STM32_ADC_SMPR2_OFFSET 0x0010 /* ADC sample time register 2 */ +#define STM32_ADC_JOFR1_OFFSET 0x0014 /* ADC injected channel data offset register 1 */ +#define STM32_ADC_JOFR2_OFFSET 0x0018 /* ADC injected channel data offset register 2 */ +#define STM32_ADC_JOFR3_OFFSET 0x001c /* ADC injected channel data offset register 3 */ +#define STM32_ADC_JOFR4_OFFSET 0x0020 /* ADC injected channel data offset register 4 */ +#define STM32_ADC_HTR_OFFSET 0x0024 /* ADC watchdog high threshold register */ +#define STM32_ADC_LTR_OFFSET 0x0028 /* ADC watchdog low threshold register */ +#define STM32_ADC_SQR1_OFFSET 0x002c /* ADC regular sequence register 1 */ +#define STM32_ADC_SQR2_OFFSET 0x0030 /* ADC regular sequence register 2 */ +#define STM32_ADC_SQR3_OFFSET 0x0034 /* ADC regular sequence register 3 */ +#define STM32_ADC_JSQR_OFFSET 0x0038 /* ADC injected sequence register */ +#define STM32_ADC_JDR1_OFFSET 0x003c /* ADC injected data register 1 */ +#define STM32_ADC_JDR2_OFFSET 0x0040 /* ADC injected data register 2 */ +#define STM32_ADC_JDR3_OFFSET 0x0044 /* ADC injected data register 3 */ +#define STM32_ADC_JDR4_OFFSET 0x0048 /* ADC injected data register 4 */ +#define STM32_ADC_DR_OFFSET 0x004c /* ADC regular data register */ + +/* Register Addresses *******************************************************************************/ + +#define STM32_ADC_SR (STM32_ADC_BASE+STM32_ADC_SR_OFFSET) +#define STM32_ADC_CR1 (STM32_ADC_BASE+STM32_ADC_CR1_OFFSET) +#define STM32_ADC_CR2 (STM32_ADC_BASE+STM32_ADC_CR2_OFFSET) +#define STM32_ADC_SMPR1 (STM32_ADC_BASE+STM32_ADC_SMPR1_OFFSET) +#define STM32_ADC_SMPR2 (STM32_ADC_BASE+STM32_ADC_SMPR2_OFFSET) +#define STM32_ADC_JOFR1 (STM32_ADC_BASE+STM32_ADC_JOFR1_OFFSET) +#define STM32_ADC_JOFR2 (STM32_ADC_BASE+STM32_ADC_JOFR2_OFFSET) +#define STM32_ADC_JOFR3 (STM32_ADC_BASE+STM32_ADC_JOFR3_OFFSET) +#define STM32_ADC_JOFR4 (STM32_ADC_BASE+STM32_ADC_JOFR4_OFFSET) +#define STM32_ADC_HTR (STM32_ADC_BASE+STM32_ADC_HTR_OFFSET) +#define STM32_ADC_LTR (STM32_ADC_BASE+STM32_ADC_LTR_OFFSET) +#define STM32_ADC_SQR1 (STM32_ADC_BASE+STM32_ADC_SQR1_OFFSET) +#define STM32_ADC_SQR2 (STM32_ADC_BASE+STM32_ADC_SQR2_OFFSET) +#define STM32_ADC_SQR3 (STM32_ADC_BASE+STM32_ADC_SQR3_OFFSET) +#define STM32_ADC_JSQR (STM32_ADC_BASE+STM32_ADC_JSQR_OFFSET) +#define STM32_ADC_JDR1 (STM32_ADC_BASE+STM32_ADC_JDR1_OFFSET) +#define STM32_ADC_JDR2 (STM32_ADC_BASE+STM32_ADC_JDR2_OFFSET) +#define STM32_ADC_JDR3 (STM32_ADC_BASE+STM32_ADC_JDR3_OFFSET) +#define STM32_ADC_JDR4 (STM32_ADC_BASE+STM32_ADC_JDR4_OFFSET) +#define STM32_ADC_DR (STM32_ADC_BASE+STM32_ADC_DR_OFFSET) + +/* Register Bitfield Definitions ********************************************************************/ +/* ADC status register (SR) */ + +#define ADC_SR_AWD (1 << 0) /* Bit 0: Analog wtchdog flag */ +#define ADC_SR_EOC (1 << 1) /* Bit 1: End of conversion */ +#define ADC_SR_JEOC (1 << 2) /* Bit 2: Injected channel end of conversion */ +#define ADC_SR_JSTRT (1 << 3) /* Bit 3: Injected channel start flag */ +#define ADC_SR_RSTRT (1 << 4) /* Bit 4: Regular channel start flag */ + +/* ADC control register 1 */ + +#define ADC_CR1_AWDCH_SHIFT (0) /* Bits 0-4: Analog watchdog channel select bits */ +#define ADC_CR1_AWDCH_MASK (0x1f << ADC_CR1_AWDCH_SHIFT) +#define ADC_CR1_EOCIE (1 << 5) /* Bit 5: Interrupt enable EOC */ +#define ADC_CR1_AWDIE (1 << 6) /* Bit 6: Analog watchdog interrupt enable */ +#define ADC_CR1_JEOCIE (1 << 7) /* Bit 7: Interrupt enable for injected channels */ +#define ADC_CR1_SCAN (1 << 8) /* Bit 8: Scan mode */ +#define ADC_CR1_AWDSGL (1 << 9) /* Bit 9: Enable the watchdog on a single channel in scan mode */ +#define ADC_CR1_JAUTO (1 << 10) /* Bit 10: Automatic Injected Group conversion */ +#define ADC_CR1_DISCEN (1 << 11) /* Bit 11: Discontinuous mode on regular channels */ +#define ADC_CR1_JDISCEN (1 << 12) /* Bit 12: Discontinuous mode on injected channels */ +#define ADC_CR1_DISNUM_SHIFT (13) /* Bit 13-15: Discontinuous mode channel count */ +#define ADC_CR1_DISNUM_MASK (0x7 << ADC_CR1_DISNUM_SHIFT) +#define ADC_CR1_JAWDEN (1 << 22) /* Bit 22: Analog watchdog enable on injected channels */ +#define ADC_CR1_AWDEN (1 << 23) /* Bit 23: Analog watchdog enable on regular channels */ + +/* ADC control register 2 */ + +#define ADC_CR2_ADON (1 << 0) /* Bit 0: A/D converter ON / OFF */ +#define ADC_CR2_CONT (1 << 1) /* Bit 1: Continuous conversion */ +#define ADC_CR2_CAL (1 << 2) /* Bit 2: A/D Calibration */ +#define ADC_CR2_RSTCAL (1 << 3) /* Bit 3: Reset calibration */ +#define ADC_CR2_DMA (1 << 8) /* Bit 8: Direct memory access mode */ +#define ADC_CR2_ALIGN (1 << 11) /* Bit 11: Data alignment */ +#define ADC_CR2_JEXTSEL_SHIFT (12) /* Bit 12-14: External event select for injected group */ +#define ADC_CR2_JEXTSEL_MASK (0x7 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_TIM19_CC1 (0 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_TIM19_CC2 (1 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_TIM2_TRGO (2 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_TIM2_CC1 (3 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_TIM3_CC4 (4 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_TIM4_TRGO (5 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_EXTI15 (6 << ADC_CR2_JEXTSEL_SHIFT) +# define ADC_CR2_JEXTSEL_JSWSTART (7 << ADC_CR2_JEXTSEL_SHIFT) +#define ADC_CR2_JEXTTRIG (1 << 15) /* Bit 15: External trigger conversion mode for injected channels */ +#define ADC_CR2_EXTSEL_SHIFT (17) /* Bit 17-19: External event select for regular group */ +#define ADC_CR2_EXTSEL_MASK (0x7 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_TIM19_TRGO (0 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_TIM19_CC3 (1 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_TIM19_CC4 (2 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_TIM2_CC2 (3 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_TIM3_TRGO (4 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_TIM4_CC4 (5 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_EXTI11 (6 << ADC_CR2_EXTSEL_SHIFT) +# define ADC_CR2_EXTSEL_SWSTART (7 << ADC_CR2_EXTSEL_SHIFT) +#define ADC_CR2_EXTTRIG (1 << 20) /* Bit 20: External trigger conversion mode for regular channels */ +#define ADC_CR2_JSWSTART (1 << 21) /* Bit 21: Start conversion of injected channels */ +#define ADC_CR2_SWSTART (1 << 22) /* Bit 22: Start conversion of regular channels */ +#define ADC_CR2_TSVREFE (1 << 23) /* Bit 23: Temperature sensor and V REFINT enable */ + +/* ADC sample time register 1 */ + +#define ADC_SMPR_1p5 0 /* 000: 1.5 cycles */ +#define ADC_SMPR_7p5 1 /* 001: 7.5 cycles */ +#define ADC_SMPR_13p5 2 /* 010: 13.5 cycles */ +#define ADC_SMPR_28p5 3 /* 011: 28.5 cycles */ +#define ADC_SMPR_41p5 4 /* 100: 41.5 cycles */ +#define ADC_SMPR_55p5 5 /* 101: 55.5 cycles */ +#define ADC_SMPR_71p5 6 /* 110: 71.5 cycles */ +#define ADC_SMPR_239p5 7 /* 111: 239.5 cycles */ + +#define ADC_SMPR1_SMP10_SHIFT (0) /* Bits 0-2: Channel 10 Sample time selection */ +#define ADC_SMPR1_SMP10_MASK (7 << ADC_SMPR1_SMP10_SHIFT) +#define ADC_SMPR1_SMP11_SHIFT (3) /* Bits 3-5: Channel 11 Sample time selection */ +#define ADC_SMPR1_SMP11_MASK (7 << ADC_SMPR1_SMP11_SHIFT) +#define ADC_SMPR1_SMP12_SHIFT (6) /* Bits 6-8: Channel 12 Sample time selection */ +#define ADC_SMPR1_SMP12_MASK (7 << ADC_SMPR1_SMP12_SHIFT) +#define ADC_SMPR1_SMP13_SHIFT (9) /* Bits 9-11: Channel 13 Sample time selection */ +#define ADC_SMPR1_SMP13_MASK (7 << ADC_SMPR1_SMP13_SHIFT) +#define ADC_SMPR1_SMP14_SHIFT (12) /* Bits 12-14: Channel 14 Sample time selection */ +#define ADC_SMPR1_SMP14_MASK (7 << ADC_SMPR1_SMP14_SHIFT) +#define ADC_SMPR1_SMP15_SHIFT (15) /* Bits 15-17: Channel 15 Sample time selection */ +#define ADC_SMPR1_SMP15_MASK (7 << ADC_SMPR1_SMP15_SHIFT) +#define ADC_SMPR1_SMP16_SHIFT (18) /* Bits 18-20: Channel 16 Sample time selection */ +#define ADC_SMPR1_SMP16_MASK (7 << ADC_SMPR1_SMP16_SHIFT) +#define ADC_SMPR1_SMP17_SHIFT (21) /* Bits 21-23: Channel 17 Sample time selection */ +#define ADC_SMPR1_SMP17_MASK (7 << ADC_SMPR1_SMP17_SHIFT) +#define ADC_SMPR1_SMP18_SHIFT (21) /* Bits 24-26: Channel 18 Sample time selection */ +#define ADC_SMPR1_SMP18_MASK (7 << ADC_SMPR1_SMP17_SHIFT) + +/* ADC sample time register 2 */ + +#define ADC_SMPR2_SMP0_SHIFT (0) /* Bits 2-0: Channel 0 Sample time selection */ +#define ADC_SMPR2_SMP0_MASK (7 << ADC_SMPR2_SMP0_SHIFT) +#define ADC_SMPR2_SMP1_SHIFT (3) /* Bits 5-3: Channel 1 Sample time selection */ +#define ADC_SMPR2_SMP1_MASK (7 << ADC_SMPR2_SMP1_SHIFT) +#define ADC_SMPR2_SMP2_SHIFT (6) /* Bits 8-6: Channel 2 Sample time selection */ +#define ADC_SMPR2_SMP2_MASK (7 << ADC_SMPR2_SMP2_SHIFT) +#define ADC_SMPR2_SMP3_SHIFT (9) /* Bits 11-9: Channel 3 Sample time selection */ +#define ADC_SMPR2_SMP3_MASK (7 << ADC_SMPR2_SMP3_SHIFT) +#define ADC_SMPR2_SMP4_SHIFT (12) /* Bits 14-12: Channel 4 Sample time selection */ +#define ADC_SMPR2_SMP4_MASK (7 << ADC_SMPR2_SMP4_SHIFT) +#define ADC_SMPR2_SMP5_SHIFT (15) /* Bits 17-15: Channel 5 Sample time selection */ +#define ADC_SMPR2_SMP5_MASK (7 << ADC_SMPR2_SMP5_SHIFT) +#define ADC_SMPR2_SMP6_SHIFT (18) /* Bits 20-18: Channel 6 Sample time selection */ +#define ADC_SMPR2_SMP6_MASK (7 << ADC_SMPR2_SMP6_SHIFT) +#define ADC_SMPR2_SMP7_SHIFT (21) /* Bits 23-21: Channel 7 Sample time selection */ +#define ADC_SMPR2_SMP7_MASK (7 << ADC_SMPR2_SMP7_SHIFT) +#define ADC_SMPR2_SMP8_SHIFT (24) /* Bits 26-24: Channel 8 Sample time selection */ +#define ADC_SMPR2_SMP8_MASK (7 << ADC_SMPR2_SMP8_SHIFT) +#define ADC_SMPR2_SMP9_SHIFT (27) /* Bits 29-27: Channel 9 Sample time selection */ +#define ADC_SMPR2_SMP9_MASK (7 << ADC_SMPR2_SMP9_SHIFT) + +/* ADC injected channel data offset register 1, 2, 3, and 4 */ + +#define ADC_JOFR_OFFSETX_SHIFT (0) /* Bits 0-11: Data offset for injected channel x */ +#define ADC_JOFR_OFFSETX_MASK (0x0fff << ADC_JOFR_OFFSETX_SHIFT) + +/* ADC watchdog high threshold register */ + +#define ADC_HTR_HT_SHIFT (0) /* Bits 0-11: Analog watchdog high threshold */ +#define ADC_HTR_HT_MASK (0xfff << ADC_HTR_HT_SHIFT) + +/* ADC watchdog low threshold register */ + +#define ADC_LTR_LT_SHIFT (0) /* Bits 0-11: Analog watchdog low threshold */ +#define ADC_LTR_LT_MASK (0xfff << ADC_LTR_LT_SHIFT) + +/* Offset between SQ bits */ + +#define ADC_SQ_OFFSET (5) + +/* ADC regular sequence register 1 */ + +#define ADC_SQR1_SQ13_SHIFT (0) /* Bits 0-4: 13th conversion in regular sequence */ +#define ADC_SQR1_SQ13_MASK (0x1f << ADC_SQR1_SQ13_SHIFT) +#define ADC_SQR1_SQ14_SHIFT (5) /* Bits 5-9: 14th conversion in regular sequence */ +#define ADC_SQR1_SQ14_MASK (0x1f << ADC_SQR1_SQ14_SHIFT) +#define ADC_SQR1_SQ15_SHIFT (10) /* Bits 10-14: 15th conversion in regular sequence */ +#define ADC_SQR1_SQ15_MASK (0x1f << ADC_SQR1_SQ15_SHIFT) +#define ADC_SQR1_SQ16_SHIFT (15) /* Bits 15-19: 16th conversion in regular sequence */ +#define ADC_SQR1_SQ16_MASK (0x1f << ADC_SQR1_SQ16_SHIFT) +#define ADC_SQR1_L_SHIFT (20) /* Bits 20-23: Regular channel sequence length */ +#define ADC_SQR1_L_MASK (0xf << ADC_SQR1_L_SHIFT) +#define ADC_SQR1_RESERVED (0xff000000) +#define ADC_SQR1_FIRST (13) +#define ADC_SQR1_LAST (16) +#define ADC_SQR1_SQ_OFFSET (0) + +/* ADC regular sequence register 2 */ + +#define ADC_SQR2_SQ7_SHIFT (0) /* Bits 0-4: 7th conversion in regular sequence */ +#define ADC_SQR2_SQ7_MASK (0x1f << ADC_SQR2_SQ7_SHIFT) +#define ADC_SQR2_SQ8_SHIFT (5) /* Bits 5-9: 8th conversion in regular sequence */ +#define ADC_SQR2_SQ8_MASK (0x1f << ADC_SQR2_SQ8_SHIFT) +#define ADC_SQR2_SQ9_SHIFT (10) /* Bits 10-14: 9th conversion in regular sequence */ +#define ADC_SQR2_SQ9_MASK (0x1f << ADC_SQR2_SQ9_SHIFT) +#define ADC_SQR2_SQ10_SHIFT (15) /* Bits 15-19: 10th conversion in regular sequence */ +#define ADC_SQR2_SQ10_MASK (0x1f << ADC_SQR2_SQ10_SHIFT) +#define ADC_SQR2_SQ11_SHIFT (15) /* Bits 20-24: 11th conversion in regular sequence */ +#define ADC_SQR2_SQ11_MASK (0x1f << ADC_SQR2_SQ11_SHIFT) +#define ADC_SQR2_SQ12_SHIFT (15) /* Bits 25-29: 12th conversion in regular sequence */ +#define ADC_SQR2_SQ12_MASK (0x1f << ADC_SQR2_SQ12_SHIFT) +#define ADC_SQR2_RESERVED (0xc0000000) +#define ADC_SQR2_FIRST (7) +#define ADC_SQR2_LAST (12) +#define ADC_SQR2_SQ_OFFSET (0) + +/* ADC regular sequence register 3 */ + +#define ADC_SQR3_SQ1_SHIFT (0) /* Bits 0-4: 1rst conversion in regular sequence */ +#define ADC_SQR3_SQ1_MASK (0x1f << ADC_SQR3_SQ1_SHIFT) +#define ADC_SQR3_SQ2_SHIFT (5) /* Bits 5-9: 2nd conversion in regular sequence */ +#define ADC_SQR3_SQ2_MASK (0x1f << ADC_SQR3_SQ2_SHIFT) +#define ADC_SQR3_SQ3_SHIFT (10) /* Bits 10-14: 3rd conversion in regular sequence */ +#define ADC_SQR3_SQ3_MASK (0x1f << ADC_SQR3_SQ3_SHIFT) +#define ADC_SQR3_SQ4_SHIFT (15) /* Bits 15-19: 4th conversion in regular sequence */ +#define ADC_SQR3_SQ4_MASK (0x1f << ADC_SQR3_SQ4_SHIFT) +#define ADC_SQR3_SQ5_SHIFT (15) /* Bits 20-24: 5th conversion in regular sequence */ +#define ADC_SQR3_SQ5_MASK (0x1f << ADC_SQR3_SQ5_SHIFT) +#define ADC_SQR3_SQ6_SHIFT (15) /* Bits 25-29: 6th conversion in regular sequence */ +#define ADC_SQR3_SQ6_MASK (0x1f << ADC_SQR3_SQ6_SHIFT) +#define ADC_SQR3_RESERVED (0xc0000000) +#define ADC_SQR3_FIRST (1) +#define ADC_SQR3_LAST (6) +#define ADC_SQR3_SQ_OFFSET (0) + +/* ADC injected sequence register */ + +#define ADC_JSQR_JSQ1_SHIFT (0) /* Bits 0-4: 1rst conversion in injected sequence */ +#define ADC_JSQR_JSQ1_MASK (0x1f << ADC_JSQR_JSQ1_SHIFT) +#define ADC_JSQR_JSQ2_SHIFT (5) /* Bits 5-9: 2nd conversion in injected sequence */ +#define ADC_JSQR_JSQ2_MASK (0x1f << ADC_JSQR_JSQ2_SHIFT) +#define ADC_JSQR_JSQ3_SHIFT (10) /* Bits 10-14: 3rd conversion in injected sequence */ +#define ADC_JSQR_JSQ3_MASK (0x1f << ADC_JSQR_JSQ3_SHIFT) +#define ADC_JSQR_JSQ4_SHIFT (15) /* Bits 15-19: 4th conversion in injected sequence */ +#define ADC_JSQR_JSQ4_MASK (0x1f << ADC_JSQR_JSQ4_SHIFT) +#define ADC_JSQR_JL_SHIFT (20) /* Bits 20-21: Injected sequence length */ +#define ADC_JSQR_JL_MASK (0x3 << ADC_JSQR_JL_SHIFT) + +/* ADC injected data register 1, 2, 3, and 4 */ + +#define ADC_JDR_JDATA_SHIFT (0) +#define ADC_JDR_JDATA_MASK (0xffff << ADC_JDR_JDATA_SHIFT) + +/* ADC regular data register */ + +#define ADC_DR_RDATA_SHIFT (0) +#define ADC_DR_RDATA_MASK (0xffff << ADC_DR_RDATA_SHIFT) + +/**************************************************************************************************** + * Public Types + ****************************************************************************************************/ + +/**************************************************************************************************** + * Public Data + ****************************************************************************************************/ + +/**************************************************************************************************** + * Public Function Prototypes + ****************************************************************************************************/ + +#endif /* __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_ADC_H */ diff --git a/arch/arm/src/stm32/chip/stm32f37xxx_memorymap.h b/arch/arm/src/stm32/chip/stm32f37xxx_memorymap.h index a9116019bfe..4c703be930c 100644 --- a/arch/arm/src/stm32/chip/stm32f37xxx_memorymap.h +++ b/arch/arm/src/stm32/chip/stm32f37xxx_memorymap.h @@ -117,7 +117,7 @@ #define STM32_SYSCFG_BASE 0x40010000 /* 0x40010000-0x400103FF SYSCFG + COMP + OPAMP */ #define STM32_EXTI_BASE 0x40010400 /* 0x40010400-0x400107FF EXTI */ -#define STM32_ADC1_BASE 0x40012400 /* 0x40012400-0x400127ff ADC1 */ +#define STM32_ADC_BASE 0x40012400 /* 0x40012400-0x400127ff ADC */ #define STM32_SPI1_BASE 0x40013000 /* 0x40013000-0x400133ff SPI1 */ #define STM32_USART1_BASE 0x40013800 /* 0x40013800-0x40013bff USART1 */ #define STM32_TIM15_BASE 0x40014000 /* 0x40014000-0x400143ff TIM15 */ @@ -128,6 +128,8 @@ #define STM32_SDADC2_BASE 0x40016400 /* 0x40016000-0x400167ff SDADC2 */ #define STM32_SDADC3_BASE 0x40016800 /* 0x40016000-0x40016bff SDADC3 */ +#define STM32_ADC1_BASE STM32_ADC_BASE + /* AHB1 Base Addresses **************************************************************/ #define STM32_DMA1_BASE 0x40020000 /* 0x40020000-0x400203ff: DMA1 */ diff --git a/arch/arm/src/stm32/chip/stm32f37xxx_pinmap.h b/arch/arm/src/stm32/chip/stm32f37xxx_pinmap.h index 6f48b4bf1e8..a20ae8577f3 100644 --- a/arch/arm/src/stm32/chip/stm32f37xxx_pinmap.h +++ b/arch/arm/src/stm32/chip/stm32f37xxx_pinmap.h @@ -69,6 +69,71 @@ * pins in this file. */ +/* ADC */ + +#define GPIO_ADC_IN1 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN1) +#define GPIO_ADC_IN2 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN2) +#define GPIO_ADC_IN3 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN3) +#define GPIO_ADC_IN4 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN4) +#define GPIO_ADC_IN5 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN5) +#define GPIO_ADC_IN6 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN6) +#define GPIO_ADC_IN7 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN7) +#define GPIO_ADC_IN8 (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN0) +#define GPIO_ADC_IN9 (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN1) +#define GPIO_ADC_IN10 (GPIO_ANALOG|GPIO_PORTC|GPIO_PIN0) +#define GPIO_ADC_IN11 (GPIO_ANALOG|GPIO_PORTC|GPIO_PIN1) +#define GPIO_ADC_IN12 (GPIO_ANALOG|GPIO_PORTC|GPIO_PIN2) +#define GPIO_ADC_IN13 (GPIO_ANALOG|GPIO_PORTC|GPIO_PIN3) +#define GPIO_ADC_IN14 (GPIO_ANALOG|GPIO_PORTC|GPIO_PIN4) +#define GPIO_ADC_IN15 (GPIO_ANALOG|GPIO_PORTC|GPIO_PIN5) + +/* SDADC */ + +#define GPIO_SDADC1_AIN0P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN12) +#define GPIO_SDADC1_AIN0M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN13) +#define GPIO_SDADC1_AIN1P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN11) +#define GPIO_SDADC1_AIN2P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN10) +#define GPIO_SDADC1_AIN2M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN11) +#define GPIO_SDADC1_AIN3P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN7) +#define GPIO_SDADC1_AIN4P (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN2) +#define GPIO_SDADC1_AIN4M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN7) +#define GPIO_SDADC1_AIN5P (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN1) +#define GPIO_SDADC1_AIN6P (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN0) +#define GPIO_SDADC1_AIN6M (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN1) +#define GPIO_SDADC1_AIN7P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN9) +#define GPIO_SDADC1_AIN8P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN8) +#define GPIO_SDADC1_AIN8M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN9) + +#define GPIO_SDADC2_AIN0P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN15) +#define GPIO_SDADC2_AIN0M (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN10) +#define GPIO_SDADC2_AIN1P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN14) +#define GPIO_SDADC2_AIN2P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN13) +#define GPIO_SDADC2_AIN2M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN14) +#define GPIO_SDADC2_AIN3P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN12) +#define GPIO_SDADC2_AIN4P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN11) +#define GPIO_SDADC2_AIN4M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN12) +#define GPIO_SDADC2_AIN5P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN7) +#define GPIO_SDADC2_AIN6P (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN2) +#define GPIO_SDADC2_AIN6M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN7) +#define GPIO_SDADC2_AIN7P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN9) +#define GPIO_SDADC2_AIN8P (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN8) +#define GPIO_SDADC2_AIN8M (GPIO_ANALOG|GPIO_PORTE|GPIO_PIN9) + +#define GPIO_SDADC3_AIN0P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN14) +#define GPIO_SDADC3_AIN0M (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN15) +#define GPIO_SDADC3_AIN1P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN13) +#define GPIO_SDADC3_AIN2P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN12) +#define GPIO_SDADC3_AIN2M (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN13) +#define GPIO_SDADC3_AIN3P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN11) +#define GPIO_SDADC3_AIN4P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN10) +#define GPIO_SDADC3_AIN4M (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN11) +#define GPIO_SDADC3_AIN5P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN9) +#define GPIO_SDADC3_AIN6P (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN8) +#define GPIO_SDADC3_AIN6M (GPIO_ANALOG|GPIO_PORTD|GPIO_PIN9) +#define GPIO_SDADC3_AIN7P (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN15) +#define GPIO_SDADC3_AIN8P (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN14) +#define GPIO_SDADC3_AIN8M (GPIO_ANALOG|GPIO_PORTB|GPIO_PIN15) + /* CAN */ #define GPIO_CAN_RX_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN11) @@ -96,9 +161,9 @@ * should first be configured to analog (AIN)". */ -#define GPIO_DAC1_1_OUT (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN4) -#define GPIO_DAC1_2_OUT (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN5) -#define GPIO_DAC2_1_OUT (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN6) +#define GPIO_DAC1_OUT1 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN4) +#define GPIO_DAC1_OUT2 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN5) +#define GPIO_DAC2_OUT1 (GPIO_ANALOG|GPIO_PORTA|GPIO_PIN6) /* I2C */ @@ -233,7 +298,6 @@ #define GPIO_SPI3_SCK_2 (GPIO_ALT|GPIO_AF6|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN3) #define GPIO_SPI3_SCK_3 (GPIO_ALT|GPIO_AF6|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN10) - /* Timers */ #define GPIO_TIM2_CH1_ETR_1 (GPIO_ALT|GPIO_FLOAT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PORTA|GPIO_PIN0) @@ -544,6 +608,5 @@ #define GPIO_PF9_EVENT_OUT (GPIO_ALT|GPIO_AF1|GPIO_PORTF|GPIO_PIN9) #define GPIO_PF10_EVENT_OUT (GPIO_ALT|GPIO_AF1|GPIO_PORTF|GPIO_PIN10) - #endif /* __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_PINMAP_H */ diff --git a/arch/arm/src/stm32/chip/stm32f37xxx_rcc.h b/arch/arm/src/stm32/chip/stm32f37xxx_rcc.h index 9c48bbd5d57..1e1f6daf6a6 100644 --- a/arch/arm/src/stm32/chip/stm32f37xxx_rcc.h +++ b/arch/arm/src/stm32/chip/stm32f37xxx_rcc.h @@ -128,6 +128,12 @@ # define RCC_CFGR_PPRE2_HCLKd4 (5 << RCC_CFGR_PPRE2_SHIFT) /* 101: HCLK divided by 4 */ # define RCC_CFGR_PPRE2_HCLKd8 (6 << RCC_CFGR_PPRE2_SHIFT) /* 110: HCLK divided by 8 */ # define RCC_CFGR_PPRE2_HCLKd16 (7 << RCC_CFGR_PPRE2_SHIFT) /* 111: HCLK divided by 16 */ +#define RCC_CFGR_ADCPRE_SHIFT (13) /* Bits 14-15: ADC prescaler */ +#define RCC_CFGR_ADCPRE_MASK (7 << RCC_CFGR_ADCPRE_SHIFT) +# define RCC_CFGR_ADCPRE_PCLKd2 (0 << RCC_CFGR_ADCPRE_SHIFT) /* 00: PCLK divided by 2 */ +# define RCC_CFGR_ADCPRE_PCLKd4 (1 << RCC_CFGR_ADCPRE_SHIFT) /* 01: PCLK divided by 4 */ +# define RCC_CFGR_ADCPRE_PCLKd6 (2 << RCC_CFGR_ADCPRE_SHIFT) /* 10: PCLK divided by 6 */ +# define RCC_CFGR_ADCPRE_PCLKd8 (3 << RCC_CFGR_ADCPRE_SHIFT) /* 11: PCLK divided by 8 */ #define RCC_CFGR_PLLSRC (1 << 16) /* Bit 16: PLL entry clock source */ #define RCC_CFGR_PLLXTPRE (1 << 17) /* Bit 17: HSE divider for PLL entry */ #define RCC_CFGR_PLLMUL_SHIFT (18) /* Bits 21-18: PLL Multiplication Factor */ @@ -157,24 +163,24 @@ # define RCC_CFGR_MCO_HSICLK (5 << RCC_CFGR_MCO_SHIFT) /* 101: HSI clock selected */ # define RCC_CFGR_MCO_HSECLK (6 << RCC_CFGR_MCO_SHIFT) /* 101: HSE clock selected */ # define RCC_CFGR_PLLCLKd2 (7 << RCC_CFGR_MCO_SHIFT) /* 111: PLL clock divided by 2 selected */ -#define RCC_CFGR_SDADCPRE_SHIFT (24) /* Bits 27-31: SDADC Prescaler */ -#define RCC_CFGR_SDADCPRE_MASK (31 << RCC_CFGR_SDADCPRE_SHIFT) -# define RCC_CFGR_SDADCPRE_DIV2 (0 << RCC_CFGR_SDADCPRE_SHIFT) /* 0xxxx: System clock divided by 2 */ -# define RCC_CFGR_SDADCPRE_DIV4 (17 << RCC_CFGR_SDADCPRE_SHIFT) /* 10001: System clock divided by 4 */ -# define RCC_CFGR_SDADCPRE_DIV6 (18 << RCC_CFGR_SDADCPRE_SHIFT) /* 10010: System clock divided by 6 */ -# define RCC_CFGR_SDADCPRE_DIV8 (19 << RCC_CFGR_SDADCPRE_SHIFT) /* 10011: System clock divided by 8 */ -# define RCC_CFGR_SDADCPRE_DIV10 (20 << RCC_CFGR_SDADCPRE_SHIFT) /* 10100: System clock divided by 10 */ -# define RCC_CFGR_SDADCPRE_DIV12 (21 << RCC_CFGR_SDADCPRE_SHIFT) /* 10101: System clock divided by 12 */ -# define RCC_CFGR_SDADCPRE_DIV14 (22 << RCC_CFGR_SDADCPRE_SHIFT) /* 10110: System clock divided by 14 */ -# define RCC_CFGR_SDADCPRE_DIV16 (23 << RCC_CFGR_SDADCPRE_SHIFT) /* 10111: System clock divided by 16 */ -# define RCC_CFGR_SDADCPRE_DIV20 (24 << RCC_CFGR_SDADCPRE_SHIFT) /* 11000: System clock divided by 20 */ -# define RCC_CFGR_SDADCPRE_DIV24 (25 << RCC_CFGR_SDADCPRE_SHIFT) /* 11001: System clock divided by 24 */ -# define RCC_CFGR_SDADCPRE_DIV28 (26 << RCC_CFGR_SDADCPRE_SHIFT) /* 11010: System clock divided by 28 */ -# define RCC_CFGR_SDADCPRE_DIV32 (27 << RCC_CFGR_SDADCPRE_SHIFT) /* 11011: System clock divided by 32 */ -# define RCC_CFGR_SDADCPRE_DIV36 (28 << RCC_CFGR_SDADCPRE_SHIFT) /* 11100: System clock divided by 36 */ -# define RCC_CFGR_SDADCPRE_DIV40 (29 << RCC_CFGR_SDADCPRE_SHIFT) /* 11101: System clock divided by 40 */ -# define RCC_CFGR_SDADCPRE_DIV44 (30 << RCC_CFGR_SDADCPRE_SHIFT) /* 11110: System clock divided by 44 */ -# define RCC_CFGR_SDADCPRE_DIV48 (31 << RCC_CFGR_SDADCPRE_SHIFT) /* 11111: System clock divided by 48 */ +#define RCC_CFGR_SDPRE_SHIFT (27) /* Bits 27-31: SDADC Prescaler */ +#define RCC_CFGR_SDPRE_MASK (0x1f << RCC_CFGR_SDPRE_SHIFT) +# define RCC_CFGR_SDPRE_DIV2 (0 << RCC_CFGR_SDPRE_SHIFT) /* 0xxxx: System clock divided by 2 */ +# define RCC_CFGR_SDPRE_DIV4 (17 << RCC_CFGR_SDPRE_SHIFT) /* 10001: System clock divided by 4 */ +# define RCC_CFGR_SDPRE_DIV6 (18 << RCC_CFGR_SDPRE_SHIFT) /* 10010: System clock divided by 6 */ +# define RCC_CFGR_SDPRE_DIV8 (19 << RCC_CFGR_SDPRE_SHIFT) /* 10011: System clock divided by 8 */ +# define RCC_CFGR_SDPRE_DIV10 (20 << RCC_CFGR_SDPRE_SHIFT) /* 10100: System clock divided by 10 */ +# define RCC_CFGR_SDPRE_DIV12 (21 << RCC_CFGR_SDPRE_SHIFT) /* 10101: System clock divided by 12 */ +# define RCC_CFGR_SDPRE_DIV14 (22 << RCC_CFGR_SDPRE_SHIFT) /* 10110: System clock divided by 14 */ +# define RCC_CFGR_SDPRE_DIV16 (23 << RCC_CFGR_SDPRE_SHIFT) /* 10111: System clock divided by 16 */ +# define RCC_CFGR_SDPRE_DIV20 (24 << RCC_CFGR_SDPRE_SHIFT) /* 11000: System clock divided by 20 */ +# define RCC_CFGR_SDPRE_DIV24 (25 << RCC_CFGR_SDPRE_SHIFT) /* 11001: System clock divided by 24 */ +# define RCC_CFGR_SDPRE_DIV28 (26 << RCC_CFGR_SDPRE_SHIFT) /* 11010: System clock divided by 28 */ +# define RCC_CFGR_SDPRE_DIV32 (27 << RCC_CFGR_SDPRE_SHIFT) /* 11011: System clock divided by 32 */ +# define RCC_CFGR_SDPRE_DIV36 (28 << RCC_CFGR_SDPRE_SHIFT) /* 11100: System clock divided by 36 */ +# define RCC_CFGR_SDPRE_DIV40 (29 << RCC_CFGR_SDPRE_SHIFT) /* 11101: System clock divided by 40 */ +# define RCC_CFGR_SDPRE_DIV44 (30 << RCC_CFGR_SDPRE_SHIFT) /* 11110: System clock divided by 44 */ +# define RCC_CFGR_SDPRE_DIV48 (31 << RCC_CFGR_SDPRE_SHIFT) /* 11111: System clock divided by 48 */ /* Clock interrupt register */ @@ -199,7 +205,7 @@ /* APB2 Peripheral reset register */ #define RCC_APB2RSTR_SYSCFGRST (1 << 0) /* Bit 0: SYSCFG, Comparators and operational amplifiers reset */ -#define RCC_APB2RSTR_ADC1RST (1 << 9) /* Bit 9: ADC1 reset */ +#define RCC_APB2RSTR_ADCRST (1 << 9) /* Bit 9: ADC reset */ #define RCC_APB2RSTR_SPI1RST (1 << 12) /* Bit 12: SPI 1 reset */ #define RCC_APB2RSTR_USART1RST (1 << 14) /* Bit 14: USART1 reset */ #define RCC_APB2RSTR_TIM15RST (1 << 16) /* Bit 16: TIM15 reset */ @@ -232,7 +238,7 @@ #define RCC_APB1RSTR_USBRST (1 << 23) /* Bit 23: USB reset */ #define RCC_APB1RSTR_CANRST (1 << 25) /* Bit 25: CAN reset */ #define RCC_APB1RSTR_CAN1RST (1 << 25) /* Bit 25: CAN reset */ -#define RCC_APB1RSTR_DAC2RST (1 << 26) /* Bit 26: DAC1 interface reset */ +#define RCC_APB1RSTR_DAC2RST (1 << 26) /* Bit 26: DAC2 interface reset */ #define RCC_APB1RSTR_PWRRST (1 << 28) /* Bit 28: Power interface reset */ #define RCC_APB1RSTR_DAC1RST (1 << 29) /* Bit 29: DAC1 interface reset */ #define RCC_APB1RSTR_CECRST (1 << 30) /* Bit 30: CEC reset */ diff --git a/arch/arm/src/stm32/chip/stm32f37xxx_sdadc.h b/arch/arm/src/stm32/chip/stm32f37xxx_sdadc.h new file mode 100644 index 00000000000..011ab4d58fd --- /dev/null +++ b/arch/arm/src/stm32/chip/stm32f37xxx_sdadc.h @@ -0,0 +1,304 @@ +/**************************************************************************************************** + * arch/arm/src/stm32/chip/stm32f37xxx_sdadc.h + * + * Copyright (C) 2009, 2011, 2013 Gregory Nutt. All rights reserved. + * Copyright (C) 2016 Studelec SA. All rights reserved. + * Authors: Gregory Nutt + * Marc Rechté + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************************************/ + +#ifndef __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_SDADC_H +#define __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_SDADC_H + +/**************************************************************************************************** + * Included Files + ****************************************************************************************************/ + +#include + +#include "chip.h" + +/**************************************************************************************************** + * Pre-processor Definitions + ****************************************************************************************************/ + +/* Register Offsets *********************************************************************************/ + +#define STM32_SDADC_CR1_OFFSET 0x0000 /* SDADC control register 1 */ +#define STM32_SDADC_CR2_OFFSET 0x0004 /* SDADC control register 2 */ +#define STM32_SDADC_ISR_OFFSET 0x0008 /* SDADC interrupt and status register */ +#define STM32_SDADC_CLRISR_OFFSET 0x000c /* SDADC interrupt and status clear register */ +#define STM32_SDADC_JCHGR_OFFSET 0x0014 /* SDADC injected channel group selection register */ +#define STM32_SDADC_CONF0R_OFFSET 0x0020 /* SDADC configuration 0 register */ +#define STM32_SDADC_CONF1R_OFFSET 0x0024 /* SDADC configuration 1 register */ +#define STM32_SDADC_CONF2R_OFFSET 0x0028 /* SDADC configuration 2 register */ +#define STM32_SDADC_CONFCHR1_OFFSET 0x0040 /* SDADC channel configuration register 1 */ +#define STM32_SDADC_CONFCHR2_OFFSET 0x0044 /* SDADC channel configuration register 2 */ +#define STM32_SDADC_JDATAR_OFFSET 0x0060 /* SDADC data register for injected group */ +#define STM32_SDADC_RDATAR_OFFSET 0x0064 /* SDADC data register for the regular channel */ +#define STM32_SDADC_JDATA12R_OFFSET 0x0070 /* SDADC1 and SDADC2 injected data register */ +#define STM32_SDADC_RDATA12R_OFFSET 0x0074 /* SDADC1 and SDADC2 regular data register */ +#define STM32_SDADC_JDATA13R_OFFSET 0x0078 /* SDADC1 and SDADC3 injected data register */ +#define STM32_SDADC_RDATA13R_OFFSET 0x007c /* SDADC1 and SDADC3 regular data register */ + + +/* Register Addresses *******************************************************************************/ + +#define STM32_SDADC1_CR1 (STM32_SDADC1_BASE+STM32_SDADC_CR1_OFFSET) +#define STM32_SDADC1_CR2 (STM32_SDADC1_BASE+STM32_SDADC_CR2_OFFSET) +#define STM32_SDADC1_ISR (STM32_SDADC1_BASE+STM32_SDADC_ISR_OFFSET) +#define STM32_SDADC1_CLRISR (STM32_SDADC1_BASE+STM32_SDADC_CLRISR_OFFSET) +#define STM32_SDADC1_JCHGR (STM32_SDADC1_BASE+STM32_SDADC_JCHGR_OFFSET) +#define STM32_SDADC1_CONF0R (STM32_SDADC1_BASE+STM32_SDADC_CONF0R_OFFSET) +#define STM32_SDADC1_CONF1R (STM32_SDADC1_BASE+STM32_SDADC_CONF1R_OFFSET) +#define STM32_SDADC1_CONF2R (STM32_SDADC1_BASE+STM32_SDADC_CONF2R_OFFSET) +#define STM32_SDADC1_CONFCHR1 (STM32_SDADC1_BASE+STM32_SDADC_CONFCHR1_OFFSET) +#define STM32_SDADC1_CONFCHR2 (STM32_SDADC1_BASE+STM32_SDADC_CONFCHR2_OFFSET) +#define STM32_SDADC1_JDATAR (STM32_SDADC1_BASE+STM32_SDADC_JDATAR_OFFSET) +#define STM32_SDADC1_RDATAR (STM32_SDADC1_BASE+STM32_SDADC_RDATAR_OFFSET) +#define STM32_SDADC1_JDATA12R (STM32_SDADC1_BASE+STM32_SDADC_JDATA12R_OFFSET) +#define STM32_SDADC1_RDATA12R (STM32_SDADC1_BASE+STM32_SDADC_RDATA12R_OFFSET) +#define STM32_SDADC1_JDATA13R (STM32_SDADC1_BASE+STM32_SDADC_JDATA13R_OFFSET) +#define STM32_SDADC1_RDATA13R (STM32_SDADC1_BASE+STM32_SDADC_RDATA13R_OFFSET) + +#define STM32_SDADC2_CR1 (STM32_SDADC2_BASE+STM32_SDADC_CR1_OFFSET) +#define STM32_SDADC2_CR2 (STM32_SDADC2_BASE+STM32_SDADC_CR2_OFFSET) +#define STM32_SDADC2_ISR (STM32_SDADC2_BASE+STM32_SDADC_ISR_OFFSET) +#define STM32_SDADC2_CLRISR (STM32_SDADC2_BASE+STM32_SDADC_CLRISR_OFFSET) +#define STM32_SDADC2_JCHGR (STM32_SDADC2_BASE+STM32_SDADC_JCHGR_OFFSET) +#define STM32_SDADC2_CONF0R (STM32_SDADC2_BASE+STM32_SDADC_CONF0R_OFFSET) +#define STM32_SDADC2_CONF1R (STM32_SDADC2_BASE+STM32_SDADC_CONF1R_OFFSET) +#define STM32_SDADC2_CONF2R (STM32_SDADC2_BASE+STM32_SDADC_CONF2R_OFFSET) +#define STM32_SDADC2_CONFCHR1 (STM32_SDADC2_BASE+STM32_SDADC_CONFCHR1_OFFSET) +#define STM32_SDADC2_CONFCHR2 (STM32_SDADC2_BASE+STM32_SDADC_CONFCHR2_OFFSET) +#define STM32_SDADC2_JDATAR (STM32_SDADC2_BASE+STM32_SDADC_JDATAR_OFFSET) +#define STM32_SDADC2_RDATAR (STM32_SDADC2_BASE+STM32_SDADC_RDATAR_OFFSET) + +#define STM32_SDADC3_CR1 (STM32_SDADC3_BASE+STM32_SDADC_CR1_OFFSET) +#define STM32_SDADC3_CR2 (STM32_SDADC3_BASE+STM32_SDADC_CR2_OFFSET) +#define STM32_SDADC3_ISR (STM32_SDADC3_BASE+STM32_SDADC_ISR_OFFSET) +#define STM32_SDADC3_CLRISR (STM32_SDADC3_BASE+STM32_SDADC_CLRISR_OFFSET) +#define STM32_SDADC3_JCHGR (STM32_SDADC3_BASE+STM32_SDADC_JCHGR_OFFSET) +#define STM32_SDADC3_CONF0R (STM32_SDADC3_BASE+STM32_SDADC_CONF0R_OFFSET) +#define STM32_SDADC3_CONF1R (STM32_SDADC3_BASE+STM32_SDADC_CONF1R_OFFSET) +#define STM32_SDADC3_CONF2R (STM32_SDADC3_BASE+STM32_SDADC_CONF2R_OFFSET) +#define STM32_SDADC3_CONFCHR1 (STM32_SDADC3_BASE+STM32_SDADC_CONFCHR1_OFFSET) +#define STM32_SDADC3_CONFCHR2 (STM32_SDADC3_BASE+STM32_SDADC_CONFCHR2_OFFSET) +#define STM32_SDADC3_JDATAR (STM32_SDADC3_BASE+STM32_SDADC_JDATAR_OFFSET) +#define STM32_SDADC3_RDATAR (STM32_SDADC3_BASE+STM32_SDADC_RDATAR_OFFSET) + + +/* Register Bitfield Definitions ********************************************************************/ +/* SDADC control register 1 */ + +#define SDADC_CR1_EOCALIE (1 << 0) /* Bit 0: End of calibration interrupt enable */ +#define SDADC_CR1_JEOCIE (1 << 1) /* Bit 1: Injected end of conversion interrupt enable */ +#define SDADC_CR1_JOVRIE (1 << 2) /* Bit 2: Injected data overrun interrupt enable */ +#define SDADC_CR1_REOCIE (1 << 3) /* Bit 3: Regular end of conversion interrupt enable */ +#define SDADC_CR1_ROVRIE (1 << 4) /* Bit 4: Regular data overrun interrupt enable */ +#define SDADC_CR1_REFV_SHIFT (8) /* Bits 8-9: Reference voltage selection */ +#define SDADC_CR1_REFV_MASK (0x3 << SDADC_CR1_REFV_SHIFT) +# define SDADC_CR1_REFV_EXT (0 << SDADC_CR1_REFV_SHIFT) +# define SDADC_CR1_REFV_INT1p2 (1 << SDADC_CR1_REFV_SHIFT) +# define SDADC_CR1_REFV_INT1p8 (2 << SDADC_CR1_REFV_SHIFT) +# define SDADC_CR1_REFV_INT (3 << SDADC_CR1_REFV_SHIFT) +#define SDADC_CR1_SLOWCK (1 << 10) /* Bit 10: Slow clock mode enable */ +#define SDADC_CR1_SBI (1 << 11) /* Bit 11: Enter Standby mode when idle */ +#define SDADC_CR1_PDI (1 << 12) /* Bit 12: Enter power down mode when idle */ +#define SDADC_CR1_JSYNC (1 << 14) /* Bit 14: Launch a injected conversion synchronously with SDADC1 */ +#define SDADC_CR1_RSYNC (1 << 15) /* Bit 15: Launch regular conversion synchronously with SDADC1 */ +#define SDADC_CR1_JDMAEN (1 << 16) /* Bit 16: DMA channel enabled to read data for the injected channel group */ +#define SDADC_CR1_RDMAEN (1 << 17) /* Bit 17: DMA channel enabled to read data for the regular channel */ +#define SDADC_CR1_INIT (1 << 31) /* Bit 31: Initialization mode request */ + +/* SDADC control register 2 */ + +#define SDADC_CR2_ADON (1 << 0) /* Bit 0: SDADC enable */ +#define SDADC_CR2_CALIBCNT_SHIFT (1) /* Bit 1-2: Number of calibration sequences to be performed (number of valid configurations) */ +#define SDADC_CR2_CALIBCNT_MASK (0x3 << SDADC_CR2_CALIBCNT_SHIFT) +#define SDADC_CR2_STARTCALIB (1 << 4) /* Bit 4: Start calibration */ +#define SDADC_CR2_JCONT (1 << 5) /* Bit 5: Continuous mode selection for injected conversions */ +#define SDADC_CR2_JDS (1 << 6) /* Bit 6: Delay start of injected conversions */ +#define SDADC_CR2_JEXTSEL_SHIFT (8) /* Bit 8-10: Trigger signal selection for launching injected conversions */ +#define SDADC_CR2_JEXTSEL_MASK (0x7 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_TIM13_CH1 (0 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_TIM14_CH1 (1 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_TIM15_CH2 (2 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_TIM3_CH1 (3 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_TIM4_CH1 (4 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_TIM19_CH2 (5 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_EXTI15 (6 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC1_CR2_JEXTSEL_EXTI11 (7 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_TIM17_CH1 (0 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_TIM12_CH1 (1 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_TIM2_CH3 (2 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_TIM3_CH2 (3 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_TIM4_CH2 (4 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_TIM19_CH3 (5 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_EXTI15 (6 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC2_CR2_JEXTSEL_EXTI11 (7 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_TIM16_CH1 (0 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_TIM12_CH1 (1 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_TIM2_CH4 (2 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_TIM3_CH3 (3 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_TIM4_CH3 (4 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_TIM19_CH4 (5 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_EXTI15 (6 << SDADC_CR2_JEXTSEL_SHIFT) +# define SDADC3_CR2_JEXTSEL_EXTI11 (7 << SDADC_CR2_JEXTSEL_SHIFT) +#define SDADC_CR2_JEXTEN_SHIFT (13) /* Bit 13-14: Trigger enable and trigger edge selection for injected conversions */ +#define SDADC_CR2_JEXTEN_MASK (0x3 << SDADC_CR2_JEXTEN_SHIFT) +# define SDADC_CR2_JEXTEN_NONE (0 << SDADC_CR2_JEXTEN_SHIFT) +# define SDADC_CR2_JEXTEN_RISING (1 << SDADC_CR2_JEXTEN_SHIFT) +# define SDADC_CR2_JEXTEN_FALLING (2 << SDADC_CR2_JEXTEN_SHIFT) +# define SDADC_CR2_JEXTEN_BOTH (3 << SDADC_CR2_JEXTEN_SHIFT) +#define SDADC_CR2_JSWSTART (1 << 15) /* Bit 15: Start a conversion of the injected group of channels */ +#define SDADC_CR2_RCH_SHIFT (16) /* Bit 16-19: Regular channel selection */ +#define SDADC_CR2_RCH_MASK (0xf << SDADC_CR2_RCH_SHIFT) +#define SDADC_CR2_RCONT (1 << 22) /* Bit 22: Continuous mode selection for regular conversions */ +#define SDADC_CR2_RSWSTART (1 << 23) /* Bit 23: Software start of a conversion on the regular channel */ +#define SDADC_CR2_FAST (1 << 24) /* Bit 24: Fast conversion mode selection */ + +/* SDADC interrupt and status register */ + +#define SDADC_ISR_EOCALF (1 << 0) /* Bit 0: End of calibration flag */ +#define SDADC_ISR_JEOCF (1 << 1) /* Bit 1: End of injected conversion flag */ +#define SDADC_ISR_JOVRF (1 << 2) /* Bit 2: Injected conversion overrun flag */ +#define SDADC_ISR_REOCF (1 << 3) /* Bit 3: End of regular conversion flag */ +#define SDADC_ISR_ROVRF (1 << 4) /* Bit 4: Regular conversion overrun flag */ +#define SDADC_ISR_CALIBIP (1 << 12) /* Bit 12: Calibration in progress status */ +#define SDADC_ISR_JCIP (1 << 13) /* Bit 13: Injected conversion in progress status */ +#define SDADC_ISR_RCIP (1 << 14) /* Bit 14: Regular conversion in progress status */ +#define SDADC_ISR_STABIP (1 << 15) /* Bit 15: Stabilization in progress status */ +#define SDADC_ISR_INITRDY (1 << 31) /* Bit 31: Initialization mode is ready */ + +/* SDADC interrupt and status clear register */ + +#define SDADC_CLRISR_CLREOCALF (1 << 0) /* Bit 0: Clear the end of calibration flag */ +#define SDADC_CLRISR_CLRJOVRF (1 << 2) /* Bit 2: Clear the injected conversion overrun flag */ +#define SDADC_CLRISR_CLRROVRF (1 << 4) /* Bit 4: Clear the regular conversion overrun flag */ + +/* SDADC injected channel group selection register */ + +#define SDADC_JCHGR_JCHG_SHIFT (0) /* Bit 0-8: Injected channel group selection */ +#define SDADC_JCHGR_JCHG_MASK (0x1ff << SDADC_JCHGR_JCHG_SHIFT) +#define SDADC_JCHGR_JCHG_CH(n) (1 << (n + SDADC_JCHGR_JCHG_SHIFT)) + +/* SDADC configuration 0-2 register */ + +#define SDADC_CONF0R 0 +#define SDADC_CONF1R 1 +#define SDADC_CONF2R 2 + +#define SDADC_CONFR_OFFSET_SHIFT (0) /* Bit 0-11: Twelve-bit calibration offset for configuration 0-2 */ +#define SDADC_CONFR_OFFSET_MASK (0xfff << SDADC_CONFR_OFFSET_SHIFT) +#define SDADC_CONFR_GAIN_SHIFT (20) /* Bit 20-22: Gain setting for configuration 0-2 */ +#define SDADC_CONFR_GAIN_MASK (0x7 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_1X (0 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_2X (1 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_4X (2 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_8X (3 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_16X (4 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_32X (5 << SDADC_CONFR_GAIN_SHIFT) +# define SDADC_CONFR_GAIN_0p5X (7 << SDADC_CONFR_GAIN_SHIFT) +#define SDADC_CONFR_SE_SHIFT (26) /* Bit 27-26: Single-ended mode for configuration 0-2 */ +#define SDADC_CONFR_SE_MASK (0x3 << SDADC_CONFR_SE_SHIFT) +# define SDADC_CONFR_SE_DIF (0 << SDADC_CONFR_SE_SHIFT) +# define SDADC_CONFR_SE_SE_OFFSET (1 << SDADC_CONFR_SE_SHIFT) +# define SDADC_CONFR_SE_SE_ZERO (3 << SDADC_CONFR_SE_SHIFT) +#define SDADC_CONFR_COMMON_SHIFT (30) /* Bit 30-31: Common mode for configuration 0-2 */ +#define SDADC_CONFR_COMMON_MASK (0x3 << SDADC_CONFR_COMMON_SHIFT) +# define SDADC_CONFR_COMMON_GND (0 << SDADC_CONFR_COMMON_SHIFT) +# define SDADC_CONFR_COMMON_VCM (1 << SDADC_CONFR_COMMON_SHIFT) +# define SDADC_CONFR_COMMON_VDD (2 << SDADC_CONFR_COMMON_SHIFT) + +/* SDADC channel configuration register 1 */ + +#define SDADC_CONFCHR1_CH_SHIFT(i) (2*i) /* Bit 0-1: Channel i configuration 0-7 */ +#define SDADC_CONFCHR1_CH_MASK(i) (0x3 << SDADC_CONFCHR1_CH_SHIFT(i)) + +/* SDADC channel configuration register 2 */ + +#define SDADC_CONFCHR2_CH8_SHIFT (0) /* Bit 0-1: Channel 8 configuration */ +#define SDADC_CONFCHR2_CH8_MASK (0x3 << SDADC_CONFCHR2_CH8_SHIFT) + +/* SDADC data register for injected group */ + +#define SDADC_JDATAR_JDATA_SHIFT (0) /* Bit 0-15: Injected group conversion data */ +#define SDADC_JDATAR_JDATA_MASK (0xffff << SDADC_JDATAR_JDATA_SHIFT) +#define SDADC_JDATAR_JDATACH_SHIFT (24) /* Bit 24-27: Injected channel most recently converted */ +#define SDADC_JDATAR_JDATACH_MASK (0xf << SDADC_JDATAR_JDATACH_SHIFT) + +/* SDADC data register for the regular channel */ + +#define SDADC_RDATAR_RDATA_SHIFT (0) /* Bit 0-15: Regular channel conversion data */ +#define SDADC_RDATAR_RDATA_MASK (0xffff << SDADC_RDATAR_RDATA_SHIFT) + +/* SDADC1 and SDADC2 injected data register */ + +#define SDADC_JDATA12R_JDATA1_SHIFT (0) /* Bit 0-15: Injected group conversion data for SDADC1 */ +#define SDADC_JDATA12R_JDATA1_MASK (0xffff << SDADC_JDATA12R_JDATA1_SHIFT) +#define SDADC_JDATA12R_JDATA2_SHIFT (16) /* Bit 16-31: Injected group conversion data for SDADC2 */ +#define SDADC_JDATA12R_JDATA2_MASK (0xffff << SDADC_JDATA12R_JDATA2_SHIFT) + +/* SDADC1 and SDADC2 regular data register */ + +#define SDADC_RDATA12R_RDATA1_SHIFT (0) /* Bit 0-15: Regular conversion data for SDADC1 */ +#define SDADC_RDATA12R_RDATA1_MASK (0xffff << SDADC_RDATA12R_RDATA1_SHIFT) +#define SDADC_RDATA12R_RDATA2_SHIFT (16) /* Bit 16-31: Regular conversion data for SDADC2 */ +#define SDADC_RDATA12R_RDATA2_MASK (0xffff << SDADC_RDATA12R_RDATA2_SHIFT) + +/* SDADC1 and SDADC3 injected data register */ + +#define SDADC_JDATA13R_JDATA1_SHIFT (0) /* Bit 0-15: Injected group conversion data for SDADC1 */ +#define SDADC_JDATA13R_JDATA1_MASK (0xffff << SDADC_JDATA13R_JDATA1_SHIFT) +#define SDADC_JDATA13R_JDATA3_SHIFT (16) /* Bit 16-31: Injected group conversion data for SDADC3 */ +#define SDADC_JDATA13R_JDATA3_MASK (0xffff << SDADC_JDATA13R_JDATA3_SHIFT) + +/* SDADC1 and SDADC3 regular data register */ + +#define SDADC_RDATA13R_RDATA1_SHIFT (0) /* Bit 0-15: Regular conversion data for SDADC1 */ +#define SDADC_RDATA13R_RDATA1_MASK (0xffff << SDADC_RDATA13R_RDATA1_SHIFT) +#define SDADC_RDATA13R_RDATA3_SHIFT (16) /* Bit 16-31: Regular conversion data for SDADC3 */ +#define SDADC_RDATA13R_RDATA3_MASK (0xffff << SDADC_RDATA13R_RDATA3_SHIFT) + +/**************************************************************************************************** + * Public Types + ****************************************************************************************************/ + +/**************************************************************************************************** + * Public Data + ****************************************************************************************************/ + +/**************************************************************************************************** + * Public Function Prototypes + ****************************************************************************************************/ + +#endif /* __ARCH_ARM_SRC_STM32_CHIP_STM32F37XXX_SDADC_H */ diff --git a/arch/arm/src/stm32/stm32.h b/arch/arm/src/stm32/stm32.h index af91ea4ea60..f2304e27350 100644 --- a/arch/arm/src/stm32/stm32.h +++ b/arch/arm/src/stm32/stm32.h @@ -61,6 +61,7 @@ #include "stm32_can.h" #include "stm32_dbgmcu.h" #include "stm32_dma.h" +#include "stm32_dac.h" #include "stm32_exti.h" #include "stm32_flash.h" #include "stm32_fsmc.h" diff --git a/arch/arm/src/stm32/stm32_adc.c b/arch/arm/src/stm32/stm32_adc.c index 2972ebaf9a6..acbb707d345 100644 --- a/arch/arm/src/stm32/stm32_adc.c +++ b/arch/arm/src/stm32/stm32_adc.c @@ -79,8 +79,8 @@ /* This implementation is for the STM32 F1, F2, F4 and STM32L15XX only */ #if defined(CONFIG_STM32_STM32F10XX) || defined(CONFIG_STM32_STM32F20XX) || \ - defined(CONFIG_STM32_STM32F30XX) || defined(CONFIG_STM32_STM32F40XX) || \ - defined(CONFIG_STM32_STM32L15XX) + defined(CONFIG_STM32_STM32F30XX) || defined(CONFIG_STM32_STM32F37XX) || \ + defined(CONFIG_STM32_STM32F40XX) || defined(CONFIG_STM32_STM32L15XX) /* At the moment there is no proper implementation for timers external * trigger in STM32L15XX May be added latter @@ -107,6 +107,9 @@ # define RCC_RSTR_ADC2RST RCC_AHBRSTR_ADC12RST # define RCC_RSTR_ADC3RST RCC_AHBRSTR_ADC34RST # define RCC_RSTR_ADC4RST RCC_AHBRSTR_ADC34RST +#elif defined(CONFIG_STM32_STM32F37XX) +# define STM32_RCC_RSTR STM32_RCC_APB2RSTR +# define RCC_RSTR_ADC1RST RCC_APB2RSTR_ADCRST #elif defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F40XX) # define STM32_RCC_RSTR STM32_RCC_APB2RSTR # define RCC_RSTR_ADC1RST RCC_APB2RSTR_ADCRST @@ -148,7 +151,7 @@ # define ADC_IER_AWD ADC_CR1_AWDIE # define ADC_ISR_JEOC ADC_SR_JEOC # define ADC_IER_JEOC ADC_CR1_JEOCIE -# ifdef CONFIG_STM32_STM32F10XX +# if defined(CONFIG_STM32_STM32F10XX) || defined(CONFIG_STM32_STM32F37XX) # define ADC_EXTREG_EXTEN_MASK ADC_CR2_EXTTRIG # define ADC_EXTREG_EXTEN_NONE 0 # define ADC_EXTREG_EXTEN_DEFAULT ADC_CR2_EXTTRIG @@ -180,7 +183,11 @@ #ifdef ADC_HAVE_DMA # define ADC_MAX_SAMPLES ADC_MAX_CHANNELS_DMA #else -# define ADC_MAX_SAMPLES ADC_MAX_CHANNELS_NODMA +# if defined(CONFIG_STM32_STM32F30XX) +# define ADC_MAX_SAMPLES ADC_MAX_CHANNELS_DMA /* Works without DMA should sampling frequency be reduced */ +# else +# define ADC_MAX_SAMPLES ADC_MAX_CHANNELS_NODMA +# endif #endif #if defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F40XX) @@ -219,7 +226,12 @@ (ADC_SMPR_DEFAULT << ADC_SMPR2_SMP8_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR2_SMP9_SHIFT)) #elif defined(CONFIG_STM32_STM32F30XX) -# define ADC_SMPR_DEFAULT ADC_SMPR_61p5 +# ifdef ADC_HAVE_DMA || (ADC_MAX_SAMPLES == 1) +# define ADC_SMPR_DEFAULT ADC_SMPR_61p5 +# else /* Slow down sampling frequency */ +# define ADC_SMPR_DEFAULT ADC_SMPR_601p5 +# endif + # define ADC_SMPR1_DEFAULT ((ADC_SMPR_DEFAULT << ADC_SMPR1_SMP1_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR1_SMP2_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR1_SMP3_SHIFT) | \ @@ -238,8 +250,13 @@ (ADC_SMPR_DEFAULT << ADC_SMPR2_SMP16_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR2_SMP17_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR2_SMP18_SHIFT)) -#elif defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F40XX) -# define ADC_SMPR_DEFAULT ADC_SMPR_112 +#elif defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F37XX) || \ + defined(CONFIG_STM32_STM32F40XX) +# if defined(CONFIG_STM32_STM32F37XX) +# define ADC_SMPR_DEFAULT ADC_SMPR_239p5 /* TODO choose 1p5? */ +# else +# define ADC_SMPR_DEFAULT ADC_SMPR_112 +# endif # define ADC_SMPR1_DEFAULT ((ADC_SMPR_DEFAULT << ADC_SMPR1_SMP10_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR1_SMP11_SHIFT) | \ (ADC_SMPR_DEFAULT << ADC_SMPR1_SMP12_SHIFT) | \ @@ -320,7 +337,8 @@ struct stm32_dev_s /* ADC Register access */ #if defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F30XX) || \ - defined(CONFIG_STM32_STM32F40XX) || defined(CONFIG_STM32_STM32L15XX) + defined(CONFIG_STM32_STM32F37XX) ||defined(CONFIG_STM32_STM32F40XX) || \ + defined(CONFIG_STM32_STM32L15XX) static void stm32_modifyreg32(unsigned int addr, uint32_t clrbits, uint32_t setbits); #endif @@ -587,7 +605,8 @@ static struct adc_dev_s g_adcdev4 = ****************************************************************************/ #if defined(CONFIG_STM32_STM32F20XX) || defined(CONFIG_STM32_STM32F30XX) || \ - defined(CONFIG_STM32_STM32F40XX) || defined(CONFIG_STM32_STM32L15XX) + defined(CONFIG_STM32_STM32F37XX) ||defined(CONFIG_STM32_STM32F40XX) || \ + defined(CONFIG_STM32_STM32L15XX) static void stm32_modifyreg32(unsigned int addr, uint32_t clrbits, uint32_t setbits) { @@ -1626,7 +1645,7 @@ static void adc_write_sample_time_registers(FAR struct adc_dev_s *dev) #endif /**************************************************************************** - * Name: adc_dmacovcallback + * Name: adc_dmaconvcallback * * Description: * Callback for DMA. Called from the DMA transfer complete interrupt after @@ -1850,7 +1869,7 @@ static void adc_reset(FAR struct adc_dev_s *dev) adc_modifyreg(priv, STM32_ADC_IER_OFFSET, clrbits, setbits); -#else +#else /* ifdef CONFIG_STM32_STM32F30XX */ /* Enable the analog watchdog */ @@ -1864,7 +1883,7 @@ static void adc_reset(FAR struct adc_dev_s *dev) clrbits |= ADC_CR1_DUALMOD_MASK; setbits |= ADC_CR1_IND; -#else +#elif (! defined(CONFIG_STM32_STM32F37XX)) /* Set the resolution of the conversion */ @@ -1880,10 +1899,16 @@ static void adc_reset(FAR struct adc_dev_s *dev) } #endif - /* Enable interrupt flags, but disable overrun interrupt */ + /* Enable interrupt flags, but disable overrun interrupt: TODO this is + * done later by upper half when opening device by adc_rxint(). + */ +#ifndef CONFIG_STM32_STM32F37XX clrbits |= ADC_IER_OVR; setbits |= ADC_IER_ALLINTS & ~ADC_IER_OVR; +#else + /* TODO NON DMA mode */ +#endif /* Set CR1 configuration */ @@ -1916,6 +1941,13 @@ static void adc_reset(FAR struct adc_dev_s *dev) clrbits |= ADC_EXTREG_EXTEN_MASK; setbits |= ADC_EXTREG_EXTEN_NONE; + /* Enable software trigger for regular channels */ + +#ifdef CONFIG_STM32_STM32F37XX + clrbits |= ADC_CR2_EXTSEL_MASK; + setbits |= ADC_CR2_EXTSEL_SWSTART | ADC_CR2_EXTTRIG; /* SW is considered as external trigger */ +#endif + #ifdef ADC_HAVE_DMA if (priv->hasdma) { @@ -2176,9 +2208,12 @@ static void adc_rxint(FAR struct adc_dev_s *dev, bool enable) if (enable) { - /* Enable the end-of-conversion ADC and analog watchdog interrupts */ + /* Enable the analog watchdog / overrun interrupts, and if no DMA, + * end-of-conversion ADC. + */ - adc_modifyreg(priv, STM32_ADC_IER_OFFSET, 0, ADC_IER_ALLINTS); + adc_modifyreg(priv, STM32_ADC_IER_OFFSET, 0, + priv->hasdma ? ADC_IER_AWD | ADC_ISR_OVR : ADC_IER_ALLINTS); } else { @@ -2766,8 +2801,10 @@ static int adc_interrupt(FAR struct adc_dev_s *dev) } } - regval &= ~pending; - adc_putreg(priv, STM32_ADC_ISR_OFFSET, regval); + /* by MR regval &= ~pending; */ + /* by MR adc_putreg(priv, STM32_ADC_ISR_OFFSET, regval); + + adc_putreg(priv, STM32_ADC_ISR_OFFSET, pending); */ return OK; } @@ -3039,8 +3076,8 @@ struct adc_dev_s *stm32_adcinitialize(int intf, FAR const uint8_t *chanlist, } #endif /* CONFIG_STM32_STM32F10XX || CONFIG_STM32_STM32F20XX || - * CONFIG_STM32_STM32F30XX || CONFIG_STM32_STM32F40XX || - * CONFIG_STM32_STM32L15XX + * CONFIG_STM32_STM32F30XX || CONFIG_STM32_STM32F47XX || + * CONFIG_STM32_STM32F40XX || CONFIG_STM32_STM32L15XX */ #endif /* CONFIG_STM32_ADC1 || CONFIG_STM32_ADC2 || * CONFIG_STM32_ADC3 || CONFIG_STM32_ADC4 diff --git a/arch/arm/src/stm32/stm32_adc.h b/arch/arm/src/stm32/stm32_adc.h index 25ad161b629..b2f4ee39189 100644 --- a/arch/arm/src/stm32/stm32_adc.h +++ b/arch/arm/src/stm32/stm32_adc.h @@ -48,6 +48,8 @@ #if defined(CONFIG_STM32_STM32F30XX) # include "chip/stm32f30xxx_adc.h" +#elif defined(CONFIG_STM32_STM32F37XX) +# include "chip/stm32f37xxx_adc.h" #else # include "chip/stm32_adc.h" #endif diff --git a/arch/arm/src/stm32/stm32_dac.c b/arch/arm/src/stm32/stm32_dac.c index 528faf1786c..fdcbaf050a9 100644 --- a/arch/arm/src/stm32/stm32_dac.c +++ b/arch/arm/src/stm32/stm32_dac.c @@ -348,7 +348,9 @@ struct stm32_chan_s uint8_t timer; /* Timer number 2-8 */ #endif uint8_t intf; /* DAC zero-based interface number (0 or 1) */ + uint32_t pin; /* Pin configuration */ uint32_t dro; /* Data output register */ + uint32_t cr; /* Control register */ uint32_t tsel; /* CR trigger select value */ #ifdef HAVE_DMA uint16_t dmachan; /* DMA channel needed by this DAC */ @@ -408,10 +410,20 @@ static const struct dac_ops_s g_dacops = }; #ifdef CONFIG_STM32_DAC1 +/* Channel 1 */ + static struct stm32_chan_s g_dac1priv = { .intf = 0, +#if STM32_NDAC < 2 + .pin = GPIO_DAC1_OUT, .dro = STM32_DAC_DHR12R1, + .cr = STM32_DAC_CR, +#else + .pin = GPIO_DAC1_OUT1, + .dro = STM32_DAC1_DHR12R1, + .cr = STM32_DAC1_CR, +#endif #ifdef CONFIG_STM32_DAC1_DMA .hasdma = 1, .dmachan = DAC1_DMA_CHAN, @@ -427,13 +439,21 @@ static struct dac_dev_s g_dac1dev = .ad_ops = &g_dacops, .ad_priv = &g_dac1priv, }; -#endif -#ifdef CONFIG_STM32_DAC2 +/* Channel 2 */ + static struct stm32_chan_s g_dac2priv = { .intf = 1, +#if STM32_NDAC < 2 + .pin = GPIO_DAC2_OUT, .dro = STM32_DAC_DHR12R2, + .cr = STM32_DAC_CR, +#else + .pin = GPIO_DAC1_OUT2, + .dro = STM32_DAC1_DHR12R2, + .cr = STM32_DAC1_CR, +#endif #ifdef CONFIG_STM32_DAC2_DMA .hasdma = 1, .dmachan = DAC2_DMA_CHAN, @@ -451,6 +471,24 @@ static struct dac_dev_s g_dac2dev = }; #endif +#ifdef CONFIG_STM32_DAC2 +/* Channel 1 */ + +static struct stm32_chan_s g_dac3priv = +{ + .intf = 2, + .pin = GPIO_DAC2_OUT1, + .dro = STM32_DAC2_DHR12R1, + .cr = STM32_DAC2_CR, +}; + +static struct dac_dev_s g_dac3dev = +{ + .ad_ops = &g_dacops, + .ad_priv = &g_dac3priv, +}; +#endif + static struct stm32_dac_s g_dacblock; /**************************************************************************** @@ -479,7 +517,7 @@ static inline void stm32_dac_modify_cr(FAR struct stm32_chan_s *chan, uint32_t shift; shift = chan->intf * 16; - modifyreg32(STM32_DAC_CR, clearbits << shift, setbits << shift); + modifyreg32(chan->cr, clearbits << shift, setbits << shift); } /**************************************************************************** @@ -738,16 +776,7 @@ static int dac_send(FAR struct dac_dev_s *dev, FAR struct dac_msg_s *msg) /* Non-DMA transfer */ putreg16(msg->am_data, chan->dro); -#ifdef CONFIG_STM32_DAC2 - if (chan->intf) - { - dac_txdone(&g_dac2dev); - } - else -#endif - { - dac_txdone(&g_dac1dev); - } + dac_txdone(dev); } /* Reset counters (generate an update) */ @@ -978,7 +1007,7 @@ static int dac_chaninit(FAR struct stm32_chan_s *chan) * should first be configured to analog (AIN)". */ - stm32_configgpio(chan->intf ? GPIO_DAC2_OUT : GPIO_DAC1_OUT); + stm32_configgpio(chan->pin); /* DAC channel configuration: * @@ -1041,7 +1070,7 @@ static int dac_chaninit(FAR struct stm32_chan_s *chan) * Name: dac_blockinit * * Description: - * All ioctl calls will be routed through this method. + * Initialize the DAC block. * * Input Parameters: * @@ -1055,7 +1084,7 @@ static int dac_blockinit(void) irqstate_t flags; uint32_t regval; - /* Has the DMA block already been initialized? */ + /* Has the DAC block already been initialized? */ if (g_dacblock.init) { @@ -1068,12 +1097,30 @@ static int dac_blockinit(void) flags = enter_critical_section(); regval = getreg32(STM32_RCC_APB1RSTR); +#if STM32_NDAC < 2 regval |= RCC_APB1RSTR_DACRST; +#else +#ifdef CONFIG_STM32_DAC1 + regval |= RCC_APB1RSTR_DAC1RST; +#endif +#ifdef CONFIG_STM32_DAC2 + regval |= RCC_APB1RSTR_DAC2RST; +#endif +#endif putreg32(regval, STM32_RCC_APB1RSTR); /* Take the DAC out of reset state */ +#if STM32_NDAC < 2 regval &= ~RCC_APB1RSTR_DACRST; +#else +#ifdef CONFIG_STM32_DAC1 + regval &= ~RCC_APB1RSTR_DAC1RST; +#endif +#ifdef CONFIG_STM32_DAC2 + regval &= ~RCC_APB1RSTR_DAC2RST; +#endif +#endif putreg32(regval, STM32_RCC_APB1RSTR); leave_critical_section(flags); @@ -1114,16 +1161,22 @@ FAR struct dac_dev_s *stm32_dacinitialize(int intf) #ifdef CONFIG_STM32_DAC1 if (intf == 1) { - ainfo("DAC1 Selected\n"); + ainfo("DAC1-1 Selected\n"); dev = &g_dac1dev; } else + if (intf == 2) + { + ainfo("DAC1-2 Selected\n"); + dev = &g_dac2dev; + } + else #endif #ifdef CONFIG_STM32_DAC2 - if (intf == 2) + if (intf == 3) { - ainfo("DAC2 Selected\n"); - dev = &g_dac2dev; + ainfo("DAC2-1 Selected\n"); + dev = &g_dac3dev; } else #endif diff --git a/arch/arm/src/stm32/stm32_i2c.h b/arch/arm/src/stm32/stm32_i2c.h index 05f57ee46fb..7274325f548 100644 --- a/arch/arm/src/stm32/stm32_i2c.h +++ b/arch/arm/src/stm32/stm32_i2c.h @@ -44,7 +44,7 @@ #include #include "chip.h" -#if defined(CONFIG_STM32_STM32F30XX) +#if defined(CONFIG_STM32_STM32F30XX) || defined(CONFIG_STM32_STM32F37XX) # include "chip/stm32f30xxx_i2c.h" #else # include "chip/stm32_i2c.h" diff --git a/arch/arm/src/stm32/stm32_pwr.c b/arch/arm/src/stm32/stm32_pwr.c index 5eda6c08ccc..13fbdb34706 100644 --- a/arch/arm/src/stm32/stm32_pwr.c +++ b/arch/arm/src/stm32/stm32_pwr.c @@ -76,6 +76,46 @@ static inline void stm32_pwr_modifyreg(uint8_t offset, uint16_t clearbits, uint1 * Public Functions ************************************************************************************/ +/************************************************************************************ + * Name: stm32_pwr_enablesdadc + * + * Description: + * Enables SDADC power + * + * Input Parameters: + * sdadc - SDADC number 1-3 + * + * Returned Value: + * None + * + ************************************************************************************/ + +#if defined(CONFIG_STM32_STM32F37XX) +void stm32_pwr_enablesdadc(uint8_t sdadc) +{ + uint32_t setbits = 0; + + switch (sdadc) + { + case 1: + setbits = PWR_CR_ENSD1; + break; + + case 2: + setbits = PWR_CR_ENSD2; + break; + + case 3: + setbits = PWR_CR_ENSD3; + break; + } + + stm32_pwr_modifyreg(STM32_PWR_CR_OFFSET, 0, setbits); + +} +#endif + + /************************************************************************************ * Name: stm32_pwr_enablebkp * diff --git a/arch/arm/src/stm32/stm32_pwr.h b/arch/arm/src/stm32/stm32_pwr.h index 344834c0678..700dd602945 100644 --- a/arch/arm/src/stm32/stm32_pwr.h +++ b/arch/arm/src/stm32/stm32_pwr.h @@ -66,6 +66,24 @@ extern "C" * Public Functions ************************************************************************************/ +/************************************************************************************ + * Name: stm32_pwr_enablesdadc + * + * Description: + * Enables SDADC power + * + * Input Parameters: + * sdadc - SDADC number 1-3 + * + * Returned Value: + * None + * + ************************************************************************************/ + +#if defined(CONFIG_STM32_STM32F37XX) +void stm32_pwr_enablesdadc(uint8_t sdadc); +#endif + /************************************************************************************ * Name: stm32_pwr_enablebkp * diff --git a/arch/arm/src/stm32/stm32_sdadc.c b/arch/arm/src/stm32/stm32_sdadc.c new file mode 100644 index 00000000000..a16cade9cd2 --- /dev/null +++ b/arch/arm/src/stm32/stm32_sdadc.c @@ -0,0 +1,1456 @@ +/**************************************************************************** + * arch/arm/src/stm32/stm32_sdadc.c + * + * Copyright (C) 2011, 2013, 2015-2016 Gregory Nutt. All rights reserved. + * Copyright (C) 2016 Studelec. All rights reserved. + * Authors: Gregory Nutt + * Marc Rechté + * + * derived from arch/arm/src/stm32/stm32_adc.c + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************/ + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include "up_internal.h" +#include "up_arch.h" + +#include "chip.h" +#include "stm32.h" +#include "stm32_dma.h" +#include "stm32_pwr.h" +#include "stm32_sdadc.h" + +#ifdef CONFIG_STM32_SDADC + +/* Some SDADC peripheral must be enabled */ + +#if defined(CONFIG_STM32_SDADC1) || defined(CONFIG_STM32_SDADC2) || \ + defined(CONFIG_STM32_SDADC3) + +/* This implementation is for the STM32F37XX only */ + +#ifndef CONFIG_STM32_STM32F37XX +# error "This chip is not yet supported" +#endif + +/* TODO: At the moment there is no implementation + for timer and external triggers */ + +#if defined(SDADC_HAVE_TIMER) +# error "There is no proper implementation for TIMER TRIGGERS at the moment" +#endif + +/**************************************************************************** + * Pre-processor Definitions + ****************************************************************************/ +/* RCC reset ****************************************************************/ + +#define STM32_RCC_RSTR STM32_RCC_APB2RSTR +#define RCC_RSTR_SDADC1RST RCC_APB2RSTR_SDADC1RST +#define RCC_RSTR_SDADC2RST RCC_APB2RSTR_SDADC2RST +#define RCC_RSTR_SDADC3RST RCC_APB2RSTR_SDADC3RST + +/* SDADC interrupts *********************************************************/ + +#define SDADC_ISR_ALLINTS (SDADC_ISR_JEOCF | SDADC_ISR_JOVRF) + +/* SDADC Channels/DMA *******************************************************/ + + +#define SDADC_DMA_CONTROL_WORD (DMA_CCR_MSIZE_16BITS | \ + DMA_CCR_PSIZE_16BITS | \ + DMA_CCR_MINC | \ + DMA_CCR_CIRC) + +/**************************************************************************** + * Private Types + ****************************************************************************/ + +/* This structure describes the state of one SDADC block */ + +struct stm32_dev_s +{ + FAR const struct adc_callback_s *cb; + uint8_t irq; /* Interrupt generated by this SDADC block */ + uint8_t nchannels; /* Number of channels */ + uint8_t cchannels; /* Number of configured channels */ + uint8_t intf; /* SDADC interface number */ + uint8_t current; /* Current SDADC channel being converted */ + uint8_t refv; /* Reference voltage selection */ +#ifdef SDADC_HAVE_DMA + uint8_t dmachan; /* DMA channel needed by this SDADC */ + bool hasdma; /* True: This channel supports DMA */ +#endif +#ifdef SDADC_HAVE_TIMER + uint8_t trigger; /* Timer trigger selection: see SDADCx_JEXTSEL_TIMxx */ +#endif + xcpt_t isr; /* Interrupt handler for this SDADC block */ + uint32_t base; /* Base address of registers unique to this SDADC + * block */ +#ifdef SDADC_HAVE_TIMER + uint32_t tbase; /* Base address of timer used by this SDADC block */ + uint32_t jextsel /* JEXTSEL value used by this SDADC block */ + uint32_t pclck; /* The PCLK frequency that drives this timer */ + uint32_t freq; /* The desired frequency of conversions */ +#endif +#ifdef SDADC_HAVE_DMA + DMA_HANDLE dma; /* Allocated DMA channel */ + + /* DMA transfer buffer */ + + int16_t dmabuffer[SDADC_MAX_SAMPLES]; +#endif + + /* List of selected SDADC injected channels to sample */ + + uint8_t chanlist[SDADC_MAX_SAMPLES]; +}; + +/**************************************************************************** + * Private Function Prototypes + ****************************************************************************/ + +/* ADC Register access */ + +static uint32_t sdadc_getreg(FAR struct stm32_dev_s *priv, int offset); +static void sdadc_putreg(FAR struct stm32_dev_s *priv, int offset, + uint32_t value); +static void sdadc_modifyreg(FAR struct stm32_dev_s *priv, int offset, + uint32_t clrbits, uint32_t setbits); +#ifdef ADC_HAVE_TIMER +static uint16_t tim_getreg(FAR struct stm32_dev_s *priv, int offset); +static void tim_putreg(FAR struct stm32_dev_s *priv, int offset, + uint16_t value); +static void tim_modifyreg(FAR struct stm32_dev_s *priv, int offset, + uint16_t clrbits, uint16_t setbits); +static void tim_dumpregs(FAR struct stm32_dev_s *priv, + FAR const char *msg); +#endif + +static void sdadc_rccreset(FAR struct stm32_dev_s *priv, bool reset); + +/* ADC Interrupt Handler */ + +static int sdadc_interrupt(FAR struct adc_dev_s *dev); +#if defined(CONFIG_STM32_SDADC1) +static int sdadc1_interrupt(int irq, FAR void *context); +#endif +#if defined(CONFIG_STM32_SDADC2) +static int sdadc2_interrupt(int irq, FAR void *context); +#endif +#if defined(CONFIG_STM32_SDADC3) +static int sdadc3_interrupt(int irq, FAR void *context); +#endif + +/* ADC Driver Methods */ + +static int sdadc_bind(FAR struct adc_dev_s *dev, + FAR const struct adc_callback_s *callback); +static void sdadc_reset(FAR struct adc_dev_s *dev); +static int sdadc_setup(FAR struct adc_dev_s *dev); +static void sdadc_shutdown(FAR struct adc_dev_s *dev); +static void sdadc_rxint(FAR struct adc_dev_s *dev, bool enable); +static int sdadc_ioctl(FAR struct adc_dev_s *dev, int cmd, + unsigned long arg); +static void sdadc_enable(FAR struct stm32_dev_s *priv, bool enable); + +static int sdadc_set_ch(FAR struct adc_dev_s *dev, uint8_t ch); + +#ifdef ADC_HAVE_TIMER +static void sdadc_timstart(FAR struct stm32_dev_s *priv, bool enable); +static int sdadc_timinit(FAR struct stm32_dev_s *priv); +#endif + +#ifdef ADC_HAVE_DMA +static void sdadc_dmaconvcallback(DMA_HANDLE handle, uint8_t isr, + FAR void *arg); +#endif + +static void sdadc_startconv(FAR struct stm32_dev_s *priv, bool enable); + +/**************************************************************************** + * Private Data + ****************************************************************************/ + +/* SDADC interface operations */ + +static const struct adc_ops_s g_sdadcops = +{ + .ao_bind = sdadc_bind, + .ao_reset = sdadc_reset, + .ao_setup = sdadc_setup, + .ao_shutdown = sdadc_shutdown, + .ao_rxint = sdadc_rxint, + .ao_ioctl = sdadc_ioctl, +}; + +/* SDADC1 state */ + +#ifdef CONFIG_STM32_SDADC1 +static struct stm32_dev_s g_sdadcpriv1 = +{ + .irq = STM32_IRQ_SDADC1, + .isr = sdadc1_interrupt, + .intf = 1, + .base = STM32_SDADC1_BASE, + .refv = SDADC1_REFV, +#ifdef SDADC1_HAVE_TIMER + .trigger = CONFIG_STM32_SDADC1_TIMTRIG, + .tbase = SDADC1_TIMER_BASE, + .extsel = SDADC1_EXTSEL_VALUE, + .pclck = SDADC1_TIMER_PCLK_FREQUENCY, + .freq = CONFIG_STM32_SDADC1_SAMPLE_FREQUENCY, +#endif +#ifdef SDADC1_HAVE_DMA + .dmachan = DMACHAN_SDADC1, + .hasdma = true, +#endif +}; + +static struct adc_dev_s g_sdadcdev1 = +{ + .ad_ops = &g_sdadcops, + .ad_priv = &g_sdadcpriv1, +}; +#endif + +/* SDADC2 state */ + +#ifdef CONFIG_STM32_SDADC2 +static struct stm32_dev_s g_sdadcpriv2 = +{ + .irq = STM32_IRQ_SDADC2, + .isr = sdadc2_interrupt, + .intf = 2, + .base = STM32_SDADC2_BASE, + .refv = SDADC2_REFV, +#ifdef SDADC2_HAVE_TIMER + .trigger = CONFIG_STM32_SDADC2_TIMTRIG, + .tbase = SDADC2_TIMER_BASE, + .extsel = SDADC2_EXTSEL_VALUE, + .pclck = SDADC2_TIMER_PCLK_FREQUENCY, + .freq = CONFIG_STM32_SDADC2_SAMPLE_FREQUENCY, +#endif +#ifdef SDADC2_HAVE_DMA + .dmachan = DMACHAN_SDADC2, + .hasdma = true, +#endif +}; + +static struct adc_dev_s g_sdadcdev2 = +{ + .ad_ops = &g_sdadcops, + .ad_priv = &g_sdadcpriv2, +}; +#endif + +/* SDADC3 state */ + +#ifdef CONFIG_STM32_SDADC3 +static struct stm32_dev_s g_sdadcpriv3 = +{ + .irq = STM32_IRQ_SDADC3, + .isr = sdadc3_interrupt, + .intf = 3, + .base = STM32_SDADC3_BASE, + .refv = SDADC3_REFV, +#ifdef SDADC3_HAVE_TIMER + .trigger = CONFIG_STM32_SDADC3_TIMTRIG, + .tbase = SDADC3_TIMER_BASE, + .extsel = SDADC3_EXTSEL_VALUE, + .pclck = SDADC3_TIMER_PCLK_FREQUENCY, + .freq = CONFIG_STM32_SDADC3_SAMPLE_FREQUENCY, +#endif +#ifdef SDADC3_HAVE_DMA + .dmachan = DMACHAN_SDADC3, + .hasdma = true, +#endif +}; + +static struct adc_dev_s g_sdadcdev3 = +{ + .ad_ops = &g_sdadcops, + .ad_priv = &g_sdadcpriv3, +}; +#endif + +/**************************************************************************** + * Private Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: sdadc_getreg + * + * Description: + * Read the value of an SDADC register. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * offset - The offset to the register to read + * + * Returned Value: + * The current contents of the specified register + * + ****************************************************************************/ + +static uint32_t sdadc_getreg(FAR struct stm32_dev_s *priv, int offset) +{ + return getreg32(priv->base + offset); +} + +/**************************************************************************** + * Name: sdadc_putreg + * + * Description: + * Write a value to an SDADC register. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * offset - The offset to the register to write to + * value - The value to write to the register + * + * Returned Value: + * None + * + ****************************************************************************/ + +static void sdadc_putreg(FAR struct stm32_dev_s *priv, int offset, + uint32_t value) +{ + putreg32(value, priv->base + offset); +} + +/**************************************************************************** + * Name: sdadc_modifyreg + * + * Description: + * Modify the value of an SDADC register (not atomic). + * + * Input Parameters: + * priv - A reference to the SDADC block state + * offset - The offset to the register to modify + * clrbits - The bits to clear + * setbits - The bits to set + * + * Returned Value: + * None + * + ****************************************************************************/ + +static void sdadc_modifyreg(FAR struct stm32_dev_s *priv, int offset, + uint32_t clrbits, uint32_t setbits) +{ + sdadc_putreg(priv, offset, (sdadc_getreg(priv, offset) & ~clrbits) | setbits); +} + +/**************************************************************************** + * Name: tim_getreg + * + * Description: + * Read the value of an SDADC timer register. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * offset - The offset to the register to read + * + * Returned Value: + * The current contents of the specified register + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_TIMER +static uint16_t tim_getreg(FAR struct stm32_dev_s *priv, int offset) +{ + return getreg16(priv->tbase + offset); +} +#endif + +/**************************************************************************** + * Name: tim_putreg + * + * Description: + * Write a value to an SDADC timer register. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * offset - The offset to the register to write to + * value - The value to write to the register + * + * Returned Value: + * None + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_TIMER +static void tim_putreg(FAR struct stm32_dev_s *priv, int offset, + uint16_t value) +{ + putreg16(value, priv->tbase + offset); +} +#endif + +/**************************************************************************** + * Name: tim_modifyreg + * + * Description: + * Modify the value of an SDADC timer register (not atomic). + * + * Input Parameters: + * priv - A reference to the SDADC block state + * offset - The offset to the register to modify + * clrbits - The bits to clear + * setbits - The bits to set + * + * Returned Value: + * None + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_TIMER +static void tim_modifyreg(FAR struct stm32_dev_s *priv, int offset, + uint16_t clrbits, uint16_t setbits) +{ + tim_putreg(priv, offset, (tim_getreg(priv, offset) & ~clrbits) | setbits); +} +#endif + +/**************************************************************************** + * Name: tim_dumpregs + * + * Description: + * Dump all timer registers. + * + * Input parameters: + * priv - A reference to the SDADC block state + * + * Returned Value: + * None + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_TIMER +static void tim_dumpregs(FAR struct stm32_dev_s *priv, FAR const char *msg) +{ + ainfo("%s:\n", msg); + + /* TODO */ +} +#endif + +/**************************************************************************** + * Name: sdadc_timstart + * + * Description: + * Start (or stop) the timer counter + * + * Input Parameters: + * priv - A reference to the SDADC block state + * enable - True: Start conversion + * + * Returned Value: + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_TIMER +static void sdadc_timstart(FAR struct stm32_dev_s *priv, bool enable) +{ + ainfo("enable: %d\n", enable ? 1 : 0); + + if (enable) + { + /* Start the counter */ + + tim_modifyreg(priv, STM32_GTIM_CR1_OFFSET, 0, GTIM_CR1_CEN); + } + else + { + /* Disable the counter */ + + tim_modifyreg(priv, STM32_GTIM_CR1_OFFSET, GTIM_CR1_CEN, 0); + } +} +#endif + +/**************************************************************************** + * Name: sdadc_timinit + * + * Description: + * Initialize the timer that drivers the SDADC sampling for this channel + * using the pre-calculated timer divider definitions. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * + * Returned Value: + * Zero on success; a negated errno value on failure. + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_TIMER +static int sdadc_timinit(FAR struct stm32_dev_s *priv) +{ + /* TODO */ + + aerr("ERROR: not implemented"); + return ERROR; +} +#endif + +/**************************************************************************** + * Name: sdadc_startconv + * + * Description: + * Start (or stop) the SDADC conversion process + * + * Input Parameters: + * priv - A reference to the SDADC block state + * enable - True: Start conversion + * + * Returned Value: + * + ****************************************************************************/ + +static void sdadc_startconv(FAR struct stm32_dev_s *priv, bool enable) +{ + ainfo("enable: %d\n", enable ? 1 : 0); + + if (enable) + { + /* Start the conversion of injected channels */ + + sdadc_modifyreg(priv, STM32_SDADC_CR2_OFFSET, 0, SDADC_CR2_JSWSTART); + } + else + { + /* Wait for a possible conversion to stop */ + + while ((sdadc_getreg(priv, STM32_SDADC_ISR_OFFSET) & SDADC_ISR_JCIP) != 0); + } +} + +/**************************************************************************** + * Name: sdadc_rccreset + * + * Description: + * (De)Initializes the SDADC block registers to their default + * reset values. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * reset - true: to put in reset state, false: to revert to normal state + * + * Returned Value: + * + ****************************************************************************/ + +static void sdadc_rccreset(FAR struct stm32_dev_s *priv, bool reset) +{ + uint32_t adcbit; + + /* Pick the appropriate bit in the APB2 reset register. + */ + + switch (priv->intf) + { +#ifdef CONFIG_STM32_SDADC1 + case 1: + adcbit = RCC_RSTR_SDADC1RST; + break; +#endif +#ifdef CONFIG_STM32_SDADC2 + case 2: + adcbit = RCC_RSTR_SDADC2RST; + break; +#endif +#ifdef CONFIG_STM32_SDADC3 + case 3: + adcbit = RCC_RSTR_SDADC3RST; + break; +#endif + default: + return; + } + + /* Set or clear the selected bit in the APB2 reset register. + * modifyreg32() disables interrupts. Disabling interrupts is necessary + * because the APB2RSTR register is used by several different drivers. + */ + + if (reset) + { + /* Enable SDADC reset state */ + + modifyreg32(STM32_RCC_RSTR, 0, adcbit); + } + else + { + /* Release SDADC from reset state */ + + modifyreg32(STM32_RCC_RSTR, adcbit, 0); + } +} + +/**************************************************************************** + * Name: sdadc_power_down_idle + * + * Description : Enables or disables power down during the idle phase. + * + * Input Parameters: + * priv - A reference to the SDADC block state + * pdi_high - true: The SDADC is powered down when waiting for a start event + * false: The SDADC is powered up when waiting for a start event + * + * Returned Value: + * None. + * + ****************************************************************************/ + +#if 0 +static void sdadc_power_down_idle(FAR struct stm32_dev_s *priv, bool pdi_high) +{ + uint32_t regval; + + ainfo("PDI: %d\n", pdi_high ? 1 : 0); + + regval = sdadc_getreg(priv, STM32_SDADC_CR2_OFFSET); + + if ((regval & SDADC_CR2_ADON) == 0) + { + regval = sdadc_getreg(priv, STM32_SDADC_CR1_OFFSET); + if (pdi_high) + { + regval |= SDADC_CR1_PDI; + } + else + { + regval &= ~SDADC_CR1_PDI; + } + + sdadc_putreg(priv, STM32_SDADC_CR1_OFFSET, regval); + } +} +#endif + +/**************************************************************************** + * Name: sdadc_enable + * + * Description : Enables or disables the specified SDADC peripheral. + * Does not start conversion unless the SDADC is + * triggered by timer + * + * Input Parameters: + * priv - A reference to the SDADC block state + * enable - true: enable SDADC conversion + * false: disable SDADC conversion + * + * Returned Value: + * + ****************************************************************************/ + +static void sdadc_enable(FAR struct stm32_dev_s *priv, bool enable) +{ + uint32_t regval; + + ainfo("enable: %d\n", enable ? 1 : 0); + + regval = sdadc_getreg(priv, STM32_SDADC_CR2_OFFSET); + + if (enable) + { + /* Enable the SDADC */ + + sdadc_putreg(priv, STM32_SDADC_CR2_OFFSET, regval | SDADC_CR2_ADON); + + /* Wait for the SDADC to be stabilized */ + + while (sdadc_getreg(priv, STM32_SDADC_ISR_OFFSET) & SDADC_ISR_STABIP); + } + else if ((regval & SDADC_CR2_ADON) != 0) + { + /* Ongoing conversions will be stopped implicitly */ + + /* Disable the SDADC */ + + sdadc_putreg(priv, STM32_SDADC_CR2_OFFSET, regval & ~SDADC_CR2_ADON); + + } +} + +/**************************************************************************** + * Name: sdadc_dmaconvcallback + * + * Description: + * Callback for DMA. Called from the DMA transfer complete interrupt after + * all channels have been converted and transferred with DMA. + * + * Input Parameters: + * handle - handle to DMA + * isr - + * arg - SDADC device + * + * Returned Value: + * + ****************************************************************************/ + +#ifdef SDADC_HAVE_DMA +static void sdadc_dmaconvcallback(DMA_HANDLE handle, uint8_t isr, FAR void *arg) +{ + FAR struct adc_dev_s *dev = (FAR struct adc_dev_s *)arg; + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + int i; + + /* Verify that the upper-half driver has bound its callback functions */ + + if (priv->cb != NULL) + { + DEBUGASSERT(priv->cb->au_receive != NULL); + + for (i = 0; i < priv->nchannels; i++) + { + priv->cb->au_receive(dev, priv->chanlist[priv->current], + priv->dmabuffer[priv->current]); + priv->current++; + if (priv->current >= priv->nchannels) + { + /* Restart the conversion sequence from the beginning */ + + priv->current = 0; + } + } + } +} +#endif + +/**************************************************************************** + * Name: sdadc_bind + * + * Description: + * Bind the upper-half driver callbacks to the lower-half implementation. + * This must be called early in order to receive SDADC event notifications. + * + ****************************************************************************/ + +static int sdadc_bind(FAR struct adc_dev_s *dev, + FAR const struct adc_callback_s *callback) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + + DEBUGASSERT(priv != NULL); + priv->cb = callback; + return OK; +} + +/**************************************************************************** + * Name: sdadc_reset + * + * Description: + * Reset the SDADC device. + * This is firstly called whenever the SDADC device is registered by + * sdadc_register() + * Does mostly the SDAC register setting. + * Leave the device in power down mode. + * Note that SDACx clock is already enable (for all SDADC) by the + * rcc_enableapb2() + * + * Input Parameters: + * dev - pointer to the sdadc device structure + * + * Returned Value: + * + ****************************************************************************/ + +static void sdadc_reset(FAR struct adc_dev_s *dev) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + irqstate_t flags; + uint32_t setbits = 0; + + ainfo("intf: %d\n", priv->intf); + + /* TODO: why critical ? */ + + flags = enter_critical_section(); + + /* Enable SDADC reset state */ + + sdadc_rccreset(priv, true); + + /* Enable power */ + + stm32_pwr_enablesdadc(priv->intf); + + /* Release SDADC from reset state */ + + sdadc_rccreset(priv, false); + + /* Enable the SDADC (and wait it stabilizes) */ + + sdadc_enable(priv, true); + + /* Put SDADC in in initialization mode */ + + sdadc_putreg(priv, STM32_SDADC_CR1_OFFSET, SDADC_CR1_INIT); + + /* Wait for the SDADC to be ready */ + + while ((sdadc_getreg(priv, STM32_SDADC_ISR_OFFSET) & SDADC_ISR_INITRDY) == 0); + + /* Load configurations */ + + sdadc_putreg(priv, STM32_SDADC_CONF0R_OFFSET, SDADC_CONF0R_DEFAULT); + sdadc_putreg(priv, STM32_SDADC_CONF1R_OFFSET, SDADC_CONF1R_DEFAULT); + sdadc_putreg(priv, STM32_SDADC_CONF2R_OFFSET, SDADC_CONF2R_DEFAULT); + + sdadc_putreg(priv, STM32_SDADC_CONFCHR1_OFFSET, SDADC_CONFCHR1_DEFAULT); + sdadc_putreg(priv, STM32_SDADC_CONFCHR2_OFFSET, SDADC_CONFCHR2_DEFAULT); + + /* Configuration of the injected channels group */ + + sdadc_set_ch(dev, 0); + + /* CR1 ********************************************************************/ + + /* Enable interrupt / dma flags, is done later by upper half when opening + * device by calling sdadc_rxint() + */ + + setbits = SDADC_CR1_INIT; /* remains in init mode while configuring */ + + /* Reference voltage */ + + setbits |= priv->refv; + + /* Set CR1 configuration */ + + sdadc_putreg(priv, STM32_SDADC_CR1_OFFSET, setbits); + + /* CR2 ********************************************************************/ + + setbits = SDADC_CR2_ADON; // leave it ON ! + + /* TODO: JEXTEN / JEXTSEL */ + + /* Number of calibrations is for 3 configurations */ + + setbits |= (2 << SDADC_CR2_CALIBCNT_SHIFT); + + /* Set CR2 configuration */ + + sdadc_putreg(priv, STM32_SDADC_CR2_OFFSET, setbits); + + /* Release INIT mode ******************************************************/ + + sdadc_modifyreg(priv, STM32_SDADC_CR1_OFFSET, SDADC_CR1_INIT, 0); + + /* Calibrate the SDADC */ + + sdadc_modifyreg(priv, STM32_SDADC_CR2_OFFSET, 0, SDADC_CR2_STARTCALIB); + + /* Wait for the calibration to complete (may take up to 5ms) */ + + while ((sdadc_getreg(priv, STM32_SDADC_ISR_OFFSET) & SDADC_ISR_EOCALF) == 0); + + /* Clear this flag */ + + sdadc_modifyreg(priv, STM32_SDADC_CLRISR_OFFSET, SDADC_CLRISR_CLREOCALF, 0); + +#ifdef SDADC_HAVE_TIMER + if (priv->tbase != 0) + { + ret = sdadc_timinit(priv); + if (ret < 0) + { + aerr("ERROR: sdadc_timinit failed: %d\n", ret); + } + } +#endif + + /* Put the device in low power mode until it is actually used by + * application code. + */ + + sdadc_enable(priv, false); + + leave_critical_section(flags); + + ainfo("CR1: 0x%08x CR2: 0x%08x\n", + sdadc_getreg(priv, STM32_SDADC_CR1_OFFSET), + sdadc_getreg(priv, STM32_SDADC_CR2_OFFSET)); + + ainfo("CONF0R: 0x%08x CONF1R: 0x%08x CONF3R: 0x%08x\n", + sdadc_getreg(priv, STM32_SDADC_CONF0R_OFFSET), + sdadc_getreg(priv, STM32_SDADC_CONF1R_OFFSET), + sdadc_getreg(priv, STM32_SDADC_CONF2R_OFFSET)); + + ainfo("CONFCHR1: 0x%08x CONFCHR2: 0x%08x JCHGR: 0x%08x\n", + sdadc_getreg(priv, STM32_SDADC_CONFCHR1_OFFSET), + sdadc_getreg(priv, STM32_SDADC_CONFCHR2_OFFSET), + sdadc_getreg(priv, STM32_SDADC_JCHGR_OFFSET)); +} + +/**************************************************************************** + * Name: sdadc_setup + * + * Description: + * Configure the ADC. This method is called the first time that the SDADC + * device is opened. + * This is called by the upper half driver sdadc_open(). + * This will occur when the port is first + * opened in the application code (/dev/sdadcN). + * It would be called again after closing all references to this file and + * reopening it. + * This function wakes up the device and setup the DMA / IRQ + * + * Input Parameters: + * dev - pointer to the sdadc device structure + * + * Returned Value: + * + ****************************************************************************/ + +static int sdadc_setup(FAR struct adc_dev_s *dev) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + int ret; + + /* Wakes up the device */ + + sdadc_enable(priv, true); + + /* Setup DMA or interrupt control. Note that either DMA or interrupt is + * setup not both. + */ + +#ifdef SDADC_HAVE_DMA + if (priv->hasdma) + { + /* Setup DMA */ + /* Stop and free DMA if it was started before */ + + if (priv->dma != NULL) + { + stm32_dmastop(priv->dma); + stm32_dmafree(priv->dma); + } + + priv->dma = stm32_dmachannel(priv->dmachan); + + stm32_dmasetup(priv->dma, + priv->base + STM32_SDADC_JDATAR_OFFSET, + (uint32_t)priv->dmabuffer, + priv->nchannels, + SDADC_DMA_CONTROL_WORD); + + stm32_dmastart(priv->dma, sdadc_dmaconvcallback, dev, false); + } + else + { + /* Attach the SDADC interrupt */ + + ret = irq_attach(priv->irq, priv->isr); + if (ret < 0) + { + ainfo("irq_attach failed: %d\n", ret); + return ret; + } + } +#else + /* Attach the SDADC interrupt */ + + ret = irq_attach(priv->irq, priv->isr); + if (ret < 0) + { + ainfo("irq_attach failed: %d\n", ret); + return ret; + } +#endif + + return OK; +} + +/**************************************************************************** + * Name: sdadc_shutdown + * + * Description: + * Disable the ADC. This method is called when the last instance + * of the SDADC device is closed by the user application. + * This method reverses the operation the setup method. + * + * Input Parameters: + * dev - pointer to the sdadc device structure + * + * Returned Value: + * + ****************************************************************************/ + +static void sdadc_shutdown(FAR struct adc_dev_s *dev) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + + /* Put the device in low power mode */ + + sdadc_enable(priv, false); + + /* Disable intrerrupt / dma */ + + sdadc_rxint(dev, false); + +#ifdef SDADC_HAVE_DMA + if (priv->hasdma) + { + /* Stop and free DMA if it was started before */ + + if (priv->dma != NULL) + { + stm32_dmastop(priv->dma); + stm32_dmafree(priv->dma); + } + } + else + { + /* Disable ADC interrupts and detach the SDADC interrupt handler */ + + up_disable_irq(priv->irq); + irq_detach(priv->irq); + } +#else + /* Disable ADC interrupts and detach the SDADC interrupt handler */ + + up_disable_irq(priv->irq); + irq_detach(priv->irq); +#endif +} + +/**************************************************************************** + * Name: sdadc_rxint + * + * Description: + * Call to enable or disable RX interrupts. + * + * Input Parameters: + * + * Returned Value: + * + ****************************************************************************/ + +static void sdadc_rxint(FAR struct adc_dev_s *dev, bool enable) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + uint32_t setbits; + + ainfo("intf: %d enable: %d\n", priv->intf, enable ? 1 : 0); + + /* DMA mode */ + +#ifdef SDADC_HAVE_DMA + if (priv->hasdma) + { + setbits = SDADC_CR1_JDMAEN; // DMA enabled for injected channels group + } + else + { + /* Interrupt enable for injected channel group overrun + and end of conversion */ + setbits = SDADC_CR1_JOVRIE | SDADC_CR1_JEOCIE; + } +#else + setbits = SDADC_CR1_JOVRIE | SDADC_CR1_JEOCIE; +#endif + + if (enable) + { + /* Enable */ + + sdadc_modifyreg(priv, STM32_SDADC_CR1_OFFSET, 0, setbits); + } + else + { + /* Disable all ADC interrupts and DMA */ + + sdadc_modifyreg(priv, STM32_SDADC_CR1_OFFSET, + SDADC_CR1_JOVRIE | SDADC_CR1_JEOCIE | SDADC_CR1_JDMAEN, + 0); + } +} + +/**************************************************************************** + * Name: sdadc_set_ch + * + * Description: + * Sets the SDADC injected channel group. + * + * Input Parameters: + * dev - pointer to device structure used by the driver + * ch - ADC channel number + 1. 0 reserved for all configured channels + * + * Returned Value: + * int - errno + * + ****************************************************************************/ + +static int sdadc_set_ch(FAR struct adc_dev_s *dev, uint8_t ch) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + uint32_t bits = 0; + int i; + + if (ch == 0) + { + priv->current = 0; + priv->nchannels = priv->cchannels; + } + else + { + for (i = 0; i < priv->cchannels && priv->chanlist[i] != ch - 1; i++); + + if (i >= priv->cchannels) + { + return -ENODEV; + } + + priv->current = i; + priv->nchannels = 1; + } + + for (i = 0; i < priv->nchannels; i++) + { + bits |= (uint32_t)(1 << priv->chanlist[i]); + } + + sdadc_putreg(priv, STM32_SDADC_JCHGR_OFFSET, bits); + + return OK; +} + +/**************************************************************************** + * Name: sdadc_ioctl + * + * Description: + * All ioctl calls will be routed through this method. + * + * Input Parameters: + * dev - pointer to device structure used by the driver + * cmd - command + * arg - arguments passed with command + * + * Returned Value: + * + ****************************************************************************/ + +static int sdadc_ioctl(FAR struct adc_dev_s *dev, int cmd, unsigned long arg) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + int ret = OK; + + switch (cmd) + { + case ANIOC_TRIGGER: + sdadc_startconv(priv, true); + break; + + default: + aerr("ERROR: Unknown cmd: %d\n", cmd); + ret = -ENOTTY; + break; + } + + return ret; +} + +/**************************************************************************** + * Name: sdadc_interrupt + * + * Description: + * Common SDADC interrupt handler. + * + * Input Parameters: + * + * Returned Value: + * + ****************************************************************************/ + +static int sdadc_interrupt(FAR struct adc_dev_s *dev) +{ + FAR struct stm32_dev_s *priv = (FAR struct stm32_dev_s *)dev->ad_priv; + uint32_t regval; + uint32_t pending; + int32_t data; + uint8_t chan; + + regval = sdadc_getreg(priv, STM32_SDADC_ISR_OFFSET); + pending = regval & SDADC_ISR_ALLINTS; + if (pending == 0) + { + return OK; + } + + /* JOVRF: overrun flag */ + + if ((regval & SDADC_ISR_JOVRF) != 0) + { + awarn("WARNING: Overrun has occurred!\n"); + } + + /* JEOCF: End of conversion */ + + if ((regval & SDADC_ISR_JEOCF) != 0) + { + /* Read the converted value and clear JEOCF bit + * (It is cleared by reading the SDADC_JDATAR) */ + + data = sdadc_getreg(priv, STM32_SDADC_JDATAR_OFFSET) & SDADC_JDATAR_JDATA_MASK; + chan = sdadc_getreg(priv, STM32_SDADC_JDATAR_OFFSET) & SDADC_JDATAR_JDATACH_MASK; + + DEBUGASSERT(priv->chanlist[priv->current] == chan); + + /* Verify that the upper-half driver has bound its callback functions */ + + if (priv->cb != NULL) + { + /* Give the SDADC data to the ADC driver. The ADC receive() method + * accepts 3 parameters: + * + * 1) The first is the ADC device instance for this SDADC block. + * 2) The second is the channel number for the data, and + * 3) The third is the converted data for the channel. + */ + + DEBUGASSERT(priv->cb->au_receive != NULL); + priv->cb->au_receive(dev, chan, data); + } + + /* Set the channel number of the next channel that will complete + * conversion. + */ + + priv->current++; + + if (priv->current >= priv->nchannels) + { + /* Restart the conversion sequence from the beginning */ + + priv->current = 0; + } + + /* do no clear this interrupt (cleared by reading data) */ + + pending &= ~SDADC_ISR_JEOCF; + } + + /* Clears interrupt flags, if any */ + + if (pending) + { + sdadc_putreg(priv, STM32_SDADC_CLRISR_OFFSET, pending); + } + + return OK; +} + +/**************************************************************************** + * Name: adc1_interrupt + * + * Description: + * ADC interrupt handler SDADC1 + * + * Input Parameters: + * irq - The IRQ number that generated the interrupt. + * context - Architecture specific register save information. + * + * Returned Value: + * + ****************************************************************************/ + +#if defined(CONFIG_STM32_SDADC1) +static int sdadc1_interrupt(int irq, FAR void *context) +{ + sdadc_interrupt(&g_sdadcdev1); + + return OK; +} +#endif + +/**************************************************************************** + * Name: adc2_interrupt + * + * Description: + * ADC interrupt handler SDADC2 + * + * Input Parameters: + * irq - The IRQ number that generated the interrupt. + * context - Architecture specific register save information. + * + * Returned Value: + * + ****************************************************************************/ + +#if defined(CONFIG_STM32_SDADC2) +static int sdadc2_interrupt(int irq, FAR void *context) +{ + sdadc_interrupt(&g_sdadcdev2); + + return OK; +} +#endif + +/**************************************************************************** + * Name: adc3_interrupt + * + * Description: + * ADC interrupt handler SDADC3 + * + * Input Parameters: + * irq - The IRQ number that generated the interrupt. + * context - Architecture specific register save information. + * + * Returned Value: + * + ****************************************************************************/ + +#if defined(CONFIG_STM32_SDADC3) +static int sdadc3_interrupt(int irq, FAR void *context) +{ + sdadc_interrupt(&g_sdadcdev3); + + return OK; +} +#endif + +/**************************************************************************** + * Public Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: stm32_sdadcinitialize + * + * Description: + * Initialize one SDADC block + * + * The logic is, save and initialize the channel list in the private driver + * structure and return the corresponding adc device structure. + * + * Each SDADC will convert the channels indicated each + * time a conversion is triggered either by sofware, timer or external event. + * Channels are numbered from 0 - 8 and must be given in order (contrarily + * to what says ST RM0313 doc !!!). + * + * Input Parameters: + * intf - Could be {1,2,3} for SDADC1, SDADC2, or SDADC3 + * chanlist - The list of channels eg. { 0, 3, 7, 8 } + * cchannels - Number of channels + * + * Returned Value: + * Valid ADC device structure reference on succcess; a NULL on failure + * + ****************************************************************************/ + +struct adc_dev_s *stm32_sdadcinitialize(int intf, FAR const uint8_t *chanlist, + int cchannels) +{ + FAR struct adc_dev_s *dev; + FAR struct stm32_dev_s *priv; + int i; + + ainfo("intf: %d cchannels: %d\n", intf, cchannels); + + switch (intf) + { +#ifdef CONFIG_STM32_SDADC1 + case 1: + ainfo("SDADC1 selected\n"); + dev = &g_sdadcdev1; + break; +#endif +#ifdef CONFIG_STM32_SDADC2 + case 2: + ainfo("SDADC2 selected\n"); + dev = &g_sdadcdev2; + break; +#endif +#ifdef CONFIG_STM32_SDADC3 + case 3: + ainfo("SDADC3 selected\n"); + dev = &g_sdadcdev3; + break; +#endif + default: + aerr("ERROR: No SDADC interface defined\n"); + return NULL; + } + + /* Check channel list in order */ + + DEBUGASSERT((cchannels <= SDADC_MAX_SAMPLES) && (cchannels > 0)); + for (i = 0; i < cchannels - 1; i ++) + { + if (chanlist[i] >= chanlist[i+1]) + { + aerr("ERROR: SDADC channel list must be given in order\n"); + return NULL; + } + } + + /* Configure the selected SDADC */ + + priv = (FAR struct stm32_dev_s *)dev->ad_priv; + + priv->cb = NULL; + priv->cchannels = cchannels; + + memcpy(priv->chanlist, chanlist, cchannels); + + return dev; +} + +#endif /* CONFIG_STM32_SDADC1 || CONFIG_STM32_SDADC2 || + * CONFIG_STM32_SDADC3 */ +#endif /* CONFIG_STM32_SDADC */ diff --git a/arch/arm/src/stm32/stm32_sdadc.h b/arch/arm/src/stm32/stm32_sdadc.h new file mode 100644 index 00000000000..b2f7ffedd9a --- /dev/null +++ b/arch/arm/src/stm32/stm32_sdadc.h @@ -0,0 +1,426 @@ +/************************************************************************************ + * arch/arm/src/stm32/stm32_sdadc.h + * + * Copyright (C) 2009, 2011, 2015 Gregory Nutt. All rights reserved. + * Copyright (C) 2016 Studelec. All rights reserved. + * Authors: Gregory Nutt + * Marc Rechté + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ************************************************************************************/ + +#ifndef __ARCH_ARM_SRC_STM32_STM32_SDADC_H +#define __ARCH_ARM_SRC_STM32_STM32_SDADC_H + +/************************************************************************************ + * Included Files + ************************************************************************************/ + +#include + +#include "chip.h" + +#if defined(CONFIG_STM32_STM32F37XX) +# include "chip/stm32f37xxx_sdadc.h" +#else +/* No generic chip/stm32_sdadc.h yet */ + +# error "This chip is not yet supported" +#endif + +#include + +/************************************************************************************ + * Pre-processor Definitions + ************************************************************************************/ +/* Configuration ********************************************************************/ +/* Timer devices may be used for different purposes. One special purpose is to + * control periodic SDADC sampling. If CONFIG_STM32_TIMn is defined then + * CONFIG_STM32_TIMn_SDADC must also be defined to indicate that timer "n" is intended + * to be used for that purpose. + */ + +/* For the STM32 F37XX line, timers 2-4, 12-17 an 19 may be used. */ + +/* TODO cf. stm32_adc.h */ + +/* Up to 3 SDADC interfaces are supported */ + +#if STM32_NSDADC < 3 +# undef CONFIG_STM32_SDADC3 +#endif + +#if STM32_NSDADC < 2 +# undef CONFIG_STM32_SDADC2 +#endif + +#if STM32_NSDADC < 1 +# undef CONFIG_STM32_SDADC1 +#endif + +#if defined(CONFIG_STM32_SDADC1) || defined(CONFIG_STM32_SDADC2) || \ + defined(CONFIG_STM32_SDADC3) + +/* DMA support */ + +#if defined(CONFIG_STM32_SDADC1_DMA) || defined(CONFIG_STM32_SDADC2_DMA) || \ + defined(CONFIG_STM32_SDADC3_DMA) +# define SDADC_HAVE_DMA 1 +#endif + +#ifdef CONFIG_STM32_SDADC1_DMA +# define SDADC1_HAVE_DMA 1 +#else +# undef SDADC1_HAVE_DMA +#endif + +#ifdef CONFIG_STM32_SDADC2_DMA +# define SDADC2_HAVE_DMA 1 +#else +# undef SDADC2_HAVE_DMA +#endif + +#ifdef CONFIG_STM32_SDADC3_DMA +# define SDADC3_HAVE_DMA 1 +#else +# undef SDADC3_HAVE_DMA +#endif + +/* SDADC Channels/DMA ****************************************************** + * The maximum number of channels that can be sampled at each scan. + * If DMA support is not enabled, then only a single channel + * ought to be sampled. + * Otherwise, unless sampling frequency is reduced, + * data overruns would occur. + */ + +#define SDADC_MAX_CHANNELS_DMA 9 +#define SDADC_MAX_CHANNELS_NODMA 1 + +#ifndef SDADC_MAX_SAMPLES +#ifdef SDADC_HAVE_DMA +# define SDADC_MAX_SAMPLES SDADC_MAX_CHANNELS_DMA +#else +# define SDADC_MAX_SAMPLES SDADC_MAX_CHANNELS_NODMA +#endif +#endif + +/* Timer configuration: If a timer trigger is specified, then get + * information about the timer. + */ + +#if defined(CONFIG_STM32_TIM3_SDADC1) +# define SDADC1_HAVE_TIMER 1 +# define SDADC1_TIMER_BASE STM32_TIM3_BASE +# define SDADC1_TIMER_PCLK_FREQUENCY STM32_APB1_TIM3_CLKIN +#elif defined(CONFIG_STM32_TIM4_SDADC1) +# define SDADC1_HAVE_TIMER 1 +# define SDADC1_TIMER_BASE STM32_TIM4_BASE +# define SDADC1_TIMER_PCLK_FREQUENCY STM32_APB1_TIM4_CLKIN +#elif defined(CONFIG_STM32_TIM13_SDADC1) +# define SDADC1_HAVE_TIMER 1 +# define SDADC1_TIMER_BASE STM32_TIM13_BASE +# define SDADC1_TIMER_PCLK_FREQUENCY STM32_APB1_TIM13_CLKIN +#elif defined(CONFIG_STM32_TIM14_SDADC1) +# define SDADC1_HAVE_TIMER 1 +# define SDADC1_TIMER_BASE STM32_TIM14_BASE +# define SDADC1_TIMER_PCLK_FREQUENCY STM32_APB1_TIM14_CLKIN +#elif defined(CONFIG_STM32_TIM15_SDADC1) +# define SDADC1_HAVE_TIMER 1 +# define SDADC1_TIMER_BASE STM32_TIM15_BASE +# define SDADC1_TIMER_PCLK_FREQUENCY STM32_APB2_TIM15_CLKIN +#elif defined(CONFIG_STM32_TIM19_SDADC1) +# define SDADC1_HAVE_TIMER 1 +# define SDADC1_TIMER_BASE STM32_TIM19_BASE +# define SDADC1_TIMER_PCLK_FREQUENCY STM32_APB1_TIM19_CLKIN +#else +# undef SDADC1_HAVE_TIMER +#endif + +#ifdef SDADC1_HAVE_TIMER +# ifndef CONFIG_STM32_SDADC1_SAMPLE_FREQUENCY +# error "CONFIG_STM32_SDADC1_SAMPLE_FREQUENCY not defined" +# endif +# ifndef CONFIG_STM32_SDADC1_TIMTRIG +# error "CONFIG_STM32_SDADC1_TIMTRIG not defined" +# warning "Values 0:TIM13_CH1 1:TIM14_CH1 2:TIM15_CH2 3:TIM3_CH1 4:TIM4_CH1 5:TIM19_CH2" +# endif +#endif + +#if defined(CONFIG_STM32_TIM2_SDADC2) +# define SDADC2_HAVE_TIMER 1 +# define SDADC2_TIMER_BASE STM32_TIM2_BASE +# define SDADC2_TIMER_PCLK_FREQUENCY STM32_APB1_TIM2_CLKIN +#elif defined(CONFIG_STM32_TIM3_SDADC2) +# define SDADC2_HAVE_TIMER 1 +# define SDADC2_TIMER_BASE STM32_TIM3_BASE +# define SDADC2_TIMER_PCLK_FREQUENCY STM32_APB1_TIM3_CLKIN +#elif defined(CONFIG_STM32_TIM4_SDADC2) +# define SDADC2_HAVE_TIMER 1 +# define SDADC2_TIMER_BASE STM32_TIM4_BASE +# define SDADC2_TIMER_PCLK_FREQUENCY STM32_APB1_TIM4_CLKIN +#elif defined(CONFIG_STM32_TIM12_SDADC2) +# define SDADC2_HAVE_TIMER 1 +# define SDADC2_TIMER_BASE STM32_TIM12_BASE +# define SDADC2_TIMER_PCLK_FREQUENCY STM32_APB1_TIM12_CLKIN +#elif defined(CONFIG_STM32_TIM17_SDADC2) +# define SDADC2_HAVE_TIMER 1 +# define SDADC2_TIMER_BASE STM32_TIM17_BASE +# define SDADC2_TIMER_PCLK_FREQUENCY STM32_APB2_TIM17_CLKIN +#elif defined(CONFIG_STM32_TIM19_SDADC2) +# define SDADC2_HAVE_TIMER 1 +# define SDADC2_TIMER_BASE STM32_TIM19_BASE +# define SDADC2_TIMER_PCLK_FREQUENCY STM32_APB1_TIM19_CLKIN +#else +# undef SDADC2_HAVE_TIMER +#endif + +#ifdef SDADC2_HAVE_TIMER +# ifndef CONFIG_STM32_SDADC2_SAMPLE_FREQUENCY +# error "CONFIG_STM32_SDADC2_SAMPLE_FREQUENCY not defined" +# endif +# ifndef CONFIG_STM32_SDADC2_TIMTRIG +# error "CONFIG_STM32_SDADC2_TIMTRIG not defined" +# warning "Values 0:TIM17_CH1 1:TIM12_CH1 2:TIM2_CH3 3:TIM3_CH2 4:TIM4_CH2 5:TIM19_CH3" +# endif +#endif + +#if defined(CONFIG_STM32_TIM2_SDADC3) +# define SDADC3_HAVE_TIMER 1 +# define SDADC3_TIMER_BASE STM32_TIM2_BASE +# define SDADC3_TIMER_PCLK_FREQUENCY STM32_APB1_TIM2_CLKIN +#elif defined(CONFIG_STM32_TIM3_SDADC3) +# define SDADC3_HAVE_TIMER 1 +# define SDADC3_TIMER_BASE STM32_TIM3_BASE +# define SDADC3_TIMER_PCLK_FREQUENCY STM32_APB1_TIM3_CLKIN +#elif defined(CONFIG_STM32_TIM4_SDADC3) +# define SDADC3_HAVE_TIMER 1 +# define SDADC3_TIMER_BASE STM32_TIM4_BASE +# define SDADC3_TIMER_PCLK_FREQUENCY STM32_APB1_TIM4_CLKIN +#elif defined(CONFIG_STM32_TIM12_SDADC3) +# define SDADC3_HAVE_TIMER 1 +# define SDADC3_TIMER_BASE STM32_TIM12_BASE +# define SDADC3_TIMER_PCLK_FREQUENCY STM32_APB1_TIM12_CLKIN +#elif defined(CONFIG_STM32_TIM16_SDADC3) +# define SDADC3_HAVE_TIMER 1 +# define SDADC3_TIMER_BASE STM32_TIM16_BASE +# define SDADC3_TIMER_PCLK_FREQUENCY STM32_APB2_TIM16_CLKIN +#elif defined(CONFIG_STM32_TIM19_SDADC3) +# define SDADC3_HAVE_TIMER 1 +# define SDADC3_TIMER_BASE STM32_TIM19_BASE +# define SDADC3_TIMER_PCLK_FREQUENCY STM32_APB1_TIM19_CLKIN +#else +# undef SDADC3_HAVE_TIMER +#endif + +#ifdef SDADC3_HAVE_TIMER +# ifndef CONFIG_STM32_SDADC3_SAMPLE_FREQUENCY +# error "CONFIG_STM32_SDADC3_SAMPLE_FREQUENCY not defined" +# endif +# ifndef CONFIG_STM32_SDADC3_TIMTRIG +# error "CONFIG_STM32_SDADC3_TIMTRIG not defined" +# warning "Values 0:TIM16_CH1 1:TIM12_CH2 2:TIM2_CH4 3:TIM3_CH3 4:TIM4_CH3 5:TIM19_CH4" +# endif +#endif + +#if defined(SDADC1_HAVE_TIMER) || defined(SDADC2_HAVE_TIMER) || \ + defined(SDADC3_HAVE_TIMER) +# define SDADC_HAVE_TIMER 1 +# if defined(CONFIG_STM32_STM32F37XX) && !defined(CONFIG_STM32_FORCEPOWER) +# warning "CONFIG_STM32_FORCEPOWER must be defined to enable the timer(s)" +# endif +#else +# undef SDADC_HAVE_TIMER +#endif + +/* NOTE: The following assumes that all possible combinations of timers and + * values are support JEXTSEL. That is not so and it varies from one STM32 + * to another. But this (wrong) assumptions keeps the logic as simple as + * possible. If unsupported combination is used, an error will show up + * later during compilation although it may be difficult to track it back + * to this simplification. + * + * STM32L37XX-family has 3 SDADC onboard + */ + +#ifdef CONFIG_STM32_STM32F37XX +# define SDADC1_JEXTSEL_TIM13_CH1 SDADC1_CR2_JEXTSEL_TIM13_CH1 +# define SDADC1_JEXTSEL_TIM14_CH1 SDADC1_CR2_JEXTSEL_TIM14_CH1 +# define SDADC1_JEXTSEL_TIM15_CH2 SDADC1_CR2_JEXTSEL_TIM15_CH2 +# define SDADC1_JEXTSEL_TIM3_CH1 SDADC1_CR2_JEXTSEL_TIM3_CH1 +# define SDADC1_JEXTSEL_TIM4_CH1 SDADC1_CR2_JEXTSEL_TIM4_CH1 +# define SDADC1_JEXTSEL_TIM19_CH2 SDADC1_CR2_JEXTSEL_TIM19_CH2 +# define SDADC1_JEXTSEL_EXTI15 SDADC1_CR2_JEXTSEL_EXTI15 +# define SDADC1_JEXTSEL_EXTI11 SDADC1_CR2_JEXTSEL_EXTI11 +# define SDADC2_JEXTSEL_TIM17_CH1 SDADC2_CR2_JEXTSEL_TIM17_CH1 +# define SDADC2_JEXTSEL_TIM12_CH1 SDADC2_CR2_JEXTSEL_TIM12_CH1 +# define SDADC2_JEXTSEL_TIM2_CH3 SDADC2_CR2_JEXTSEL_TIM2_CH3 +# define SDADC2_JEXTSEL_TIM3_CH2 SDADC2_CR2_JEXTSEL_TIM3_CH2 +# define SDADC2_JEXTSEL_TIM4_CH2 SDADC2_CR2_JEXTSEL_TIM4_CH2 +# define SDADC2_JEXTSEL_TIM19_CH3 SDADC2_CR2_JEXTSEL_TIM19_CH3 +# define SDADC2_JEXTSEL_EXTI15 SDADC2_CR2_JEXTSEL_EXTI15 +# define SDADC2_JEXTSEL_EXTI11 SDADC2_CR2_JEXTSEL_EXTI11 +# define SDADC3_JEXTSEL_TIM16_CH1 SDADC3_CR2_JEXTSEL_TIM16_CH1 +# define SDADC3_JEXTSEL_TIM12_CH1 SDADC3_CR2_JEXTSEL_TIM12_CH1 +# define SDADC3_JEXTSEL_TIM2_CH4 SDADC3_CR2_JEXTSEL_TIM2_CH4 +# define SDADC3_JEXTSEL_TIM3_CH3 SDADC3_CR2_JEXTSEL_TIM3_CH3 +# define SDADC3_JEXTSEL_TIM4_CH3 SDADC3_CR2_JEXTSEL_TIM4_CH3 +# define SDADC3_JEXTSEL_TIM19_CH4 SDADC3_CR2_JEXTSEL_TIM19_CH4 +# define SDADC3_JEXTSEL_EXTI15 SDADC3_CR2_JEXTSEL_EXTI15 +# define SDADC3_JEXTSEL_EXTI11 SDADC3_CR2_JEXTSEL_EXTI11 +#endif + +#if defined(CONFIG_STM32_TIM3_SDADC1) +# define SDADC1_JEXTSEL_VALUE 3 +#elif defined(CONFIG_STM32_TIM4_SDADC1) +# define SDADC1_JEXTSEL_VALUE 4 +#elif defined(CONFIG_STM32_TIM13_SDADC1) +# define SDADC1_JEXTSEL_VALUE 0 +#elif defined(CONFIG_STM32_TIM14_SDADC1) +# define SDADC1_JEXTSEL_VALUE 1 +#elif defined(CONFIG_STM32_TIM15_SDADC1) +# define SDADC1_JEXTSEL_VALUE 2 +#elif defined(CONFIG_STM32_TIM19_SDADC1) +# define SDADC1_JEXTSEL_VALUE 5 +#else +# undef SDADC1_JEXTSEL_VALUE +#endif + +#if defined(CONFIG_STM32_TIM2_SDADC2) +# define SDADC2_JEXTSEL_VALUE 2 +#elif defined(CONFIG_STM32_TIM3_SDADC2) +# define SDADC2_JEXTSEL_VALUE 3 +#elif defined(CONFIG_STM32_TIM4_SDADC2) +# define SDADC2_JEXTSEL_VALUE 4 +#elif defined(CONFIG_STM32_TIM12_SDADC2) +# define SDADC2_JEXTSEL_VALUE 1 +#elif defined(CONFIG_STM32_TIM17_SDADC2) +# define SDADC2_JEXTSEL_VALUE 0 +#elif defined(CONFIG_STM32_TIM19_SDADC2) +# define SDADC2_JEXTSEL_VALUE 5 +#else +# undef SDADC2_JEXTSEL_VALUE +#endif + +#if defined(CONFIG_STM32_TIM2_SDADC3) +# define SDADC3_JEXTSEL_VALUE 2 +#elif defined(CONFIG_STM32_TIM3_SDADC3) +# define SDADC3_JEXTSEL_VALUE 3 +#elif defined(CONFIG_STM32_TIM4_SDADC3) +# define SDADC3_JEXTSEL_VALUE 4 +#elif defined(CONFIG_STM32_TIM12_SDADC3) +# define SDADC3_JEXTSEL_VALUE 1 +#elif defined(CONFIG_STM32_TIM16_SDADC3) +# define SDADC3_JEXTSEL_VALUE 0 +#elif defined(CONFIG_STM32_TIM19_SDADC3) +# define SDADC3_JEXTSEL_VALUE 5 +#else +# undef SDADC3_JEXTSEL_VALUE +#endif + +/* SDADC Configurations ******************************************************** + * Up to 3 configuration profiles may be defined in order to define: + * - calibration method + * - SE/differential mode + * - input gain + * Each of the 9 SDADC channels is assigned to a configuration profile + */ +#ifndef SDADC_CONF0R_DEFAULT +# define SDADC_CONF0R_DEFAULT (SDADC_CONFR_GAIN_1X | SDADC_CONFR_SE_SE_OFFSET | SDADC_CONFR_COMMON_GND) +#endif +#ifndef SDADC_CONF1R_DEFAULT +# define SDADC_CONF1R_DEFAULT (SDADC_CONFR_GAIN_2X | SDADC_CONFR_SE_SE_OFFSET | SDADC_CONFR_COMMON_GND) +#endif +#ifndef SDADC_CONF2R_DEFAULT +# define SDADC_CONF2R_DEFAULT (SDADC_CONFR_GAIN_4X | SDADC_CONFR_SE_SE_OFFSET | SDADC_CONFR_COMMON_GND) +#endif +#ifndef SDADC_CONFCHR1_DEFAULT +# define SDADC_CONFCHR1_DEFAULT ((SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(0)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(1)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(2)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(3)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(4)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(5)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(6)) | \ + (SDADC_CONF0R << SDADC_CONFCHR1_CH_SHIFT(7))) +#endif +#ifndef SDADC_CONFCHR2_DEFAULT +# define SDADC_CONFCHR2_DEFAULT (SDADC_CONF0R << SDADC_CONFCHR2_CH8_SHIFT) +#endif + +/* SDADC Reference voltage selection ************************************************/ + +#ifndef SDADC_REFV_DEFAULT +# define SDADC_REFV_DEFAULT SDADC_CR1_REFV_EXT +#endif +#ifndef SDADC1_REFV +# define SDADC1_REFV SDADC_REFV_DEFAULT +#endif +#ifndef SDADC2_REFV +# define SDADC2_REFV SDADC_REFV_DEFAULT +#endif +#ifndef SDADC3_REFV +# define SDADC3_REFV SDADC_REFV_DEFAULT +#endif + +/************************************************************************************ + * Public Types + ************************************************************************************/ + +/************************************************************************************ + * Public Function Prototypes + ************************************************************************************/ + +#ifndef __ASSEMBLY__ +#ifdef __cplusplus +#define EXTERN extern "C" +extern "C" +{ +#else +#define EXTERN extern +#endif + +/**************************************************************************** + * Name: stm32_sdadcinitialize + * + ****************************************************************************/ + +struct adc_dev_s *stm32_sdadcinitialize(int intf, FAR const uint8_t *chanlist, + int nchannels); + +#undef EXTERN +#ifdef __cplusplus +} +#endif +#endif /* __ASSEMBLY__ */ + +#endif /* CONFIG_STM32_SDADC1 || CONFIG_STM32_SDADC2 || + * CONFIG_STM32_SDADC3 + */ +#endif /* __ARCH_ARM_SRC_STM32_STM32_SDADC_H */ diff --git a/arch/arm/src/stm32/stm32f30xxx_i2c.c b/arch/arm/src/stm32/stm32f30xxx_i2c.c index 141b0deb75c..27b1c924889 100644 --- a/arch/arm/src/stm32/stm32f30xxx_i2c.c +++ b/arch/arm/src/stm32/stm32f30xxx_i2c.c @@ -101,7 +101,7 @@ #if defined(CONFIG_STM32_I2C1) || defined(CONFIG_STM32_I2C2) || defined(CONFIG_STM32_I2C3) /* This implementation is for the STM32 F1, F2, and F4 only */ -#if defined(CONFIG_STM32_STM32F30XX) +#if defined(CONFIG_STM32_STM32F30XX) || defined(CONFIG_STM32_STM32F37XX) /************************************************************************************ * Pre-processor Definitions @@ -1949,7 +1949,7 @@ out: FAR struct i2c_master_s *stm32_i2cbus_initialize(int port) { struct stm32_i2c_priv_s * priv = NULL; /* private data of device with multiple instances */ - irqtate_t flags; + irqstate_t flags; #if STM32_PCLK1_FREQUENCY < 4000000 # warning STM32_I2C_INIT: Peripheral clock must be at least 4 MHz to support 400 kHz operation. diff --git a/arch/arm/src/stm32/stm32f37xxx_rcc.c b/arch/arm/src/stm32/stm32f37xxx_rcc.c index 02fa9fd930d..6b83ee316c9 100644 --- a/arch/arm/src/stm32/stm32f37xxx_rcc.c +++ b/arch/arm/src/stm32/stm32f37xxx_rcc.c @@ -80,7 +80,7 @@ static inline void rcc_reset(void) regval |= RCC_CR_HSION; putreg32(regval, STM32_RCC_CR); - regval = getreg32(STM32_RCC_CFGR); /* Reset SW, HPRE, PPRE1, PPRE2, USBPRE, and MCO bits */ + regval = getreg32(STM32_RCC_CFGR); /* Reset SW, HPRE, PPRE1, PPRE2, ADCPRE, USBPRE, MCO, SDADC bits */ regval &= ~(RCC_CFGR_SW_MASK | RCC_CFGR_HPRE_MASK | RCC_CFGR_PPRE1_MASK | RCC_CFGR_PPRE2_MASK | RCC_CFGR_USBPRE | RCC_CFGR_MCO_MASK); putreg32(regval, STM32_RCC_CFGR); @@ -107,6 +107,7 @@ static inline void rcc_reset(void) putreg32(0, STM32_RCC_CIR); /* Disable all interrupts */ } + /**************************************************************************** * Name: rcc_enableahb * @@ -169,7 +170,7 @@ static inline void rcc_enableapb1(void) #ifdef CONFIG_STM32_USB /* USB clock divider. This bit must be valid before enabling the USB - * clock in the RCC_APB1ENR register. This bit can’t be reset if the USB + * clock in the RCC_APB1ENR register. This bit can't be reset if the USB * clock is enabled. */ @@ -356,6 +357,28 @@ static inline void rcc_enableapb2(void) { uint32_t regval; +#if defined(CONFIG_STM32_SDADC) || defined(CONFIG_STM32_ADC) + /* Adjust clock of selected peripherals */ + + regval = getreg32(STM32_RCC_CFGR); + +#ifdef CONFIG_STM32_ADC + /* ADC clock divider */ + + regval &= ~RCC_CFGR_ADCPRE_MASK; + regval |= STM32_RCC_ADCPRE; +#endif + +#ifdef CONFIG_STM32_SDADC + /* SDADC clock divider */ + + regval &= ~RCC_CFGR_SDPRE_MASK; + regval |= STM32_RCC_SDPRE; +#endif + + putreg32(regval, STM32_RCC_CFGR); +#endif + /* Set the appropriate bits in the APB2ENR register to enabled the * selected APB2 peripherals. */ @@ -368,6 +391,12 @@ static inline void rcc_enableapb2(void) regval |= RCC_APB2ENR_SYSCFGEN; #endif +#ifdef CONFIG_STM32_ADC1 + /* ADC clock enable */ + + regval |= RCC_APB2ENR_ADC1EN; +#endif + #ifdef CONFIG_STM32_SPI1 /* SPI 1 clock enable */ @@ -412,6 +441,24 @@ static inline void rcc_enableapb2(void) #endif #endif +#ifdef CONFIG_STM32_SDADC1 + /* SDCADC1 clock enable */ + + regval |= RCC_APB2ENR_SDADC1EN; +#endif + +#ifdef CONFIG_STM32_SDADC2 + /* SDCADC2 clock enable */ + + regval |= RCC_APB2ENR_SDADC2EN; +#endif + +#ifdef CONFIG_STM32_SDADC3 + /* SDCADC3 clock enable */ + + regval |= RCC_APB2ENR_SDADC3EN; +#endif + putreg32(regval, STM32_RCC_APB2ENR); } @@ -469,13 +516,13 @@ static void stm32_stdclockconfig(void) /* If this is a value-line part and we are using the HSE as the PLL */ -# if (STM32_CFGR_PLLXTPRE >> 17) != (STM32_CFGR2_PREDIV1 & 1) -# error STM32_CFGR_PLLXTPRE must match the LSB of STM32_CFGR2_PREDIV1 +# if (STM32_CFGR_PLLXTPRE >> 17) != (STM32_CFGR2_PREDIV & 1) +# error STM32_CFGR_PLLXTPRE must match the LSB of STM32_CFGR2_PREDIV # endif /* Set the HSE prescaler */ - regval = STM32_CFGR2_PREDIV1; + regval = STM32_CFGR2_PREDIV; putreg32(regval, STM32_RCC_CFGR2); # endif diff --git a/arch/xtensa/include/esp32/irq.h b/arch/xtensa/include/esp32/irq.h index 36fce7d4e58..46b20fb552d 100644 --- a/arch/xtensa/include/esp32/irq.h +++ b/arch/xtensa/include/esp32/irq.h @@ -50,29 +50,6 @@ * Pre-processor Definitions ****************************************************************************/ -/* Exceptions - * - * IRAM Offset Description - * 0x0000 Windows - * 0x0180 Level 2 interrupt - * 0x01c0 Level 3 interrupt - * 0x0200 Level 4 interrupt - * 0x0240 Level 5 interrupt - * 0x0280 Debug exception - * 0x02c0 NMI exception - * 0x0300 Kernel exception - * 0x0340 User exception - * 0x03c0 Double exception - * - * REVISIT: In more architectures supported by NuttX, exception errors - * tie into the normal interrupt handling via special IRQ numbers. I - * is still to be determined what will be done for the ESP32. - */ - -#define XTENSA_IRQ_TIMER0 0 /* INTERRUPT, bit 6 */ -#define XTENSA_IRQ_TIMER1 1 /* INTERRUPT, bit 15 */ -#define XTENSA_IRQ_TIMER2 2 /* INTERRUPT, bit 16 */ - /* Interrupt Matrix * * The Interrupt Matrix embedded in the ESP32 independently allocates @@ -102,94 +79,307 @@ /* PRO_INTR_STATUS_REG_0 / APP_INTR_STATUS_REG_0 */ -#define XTENSA_IRQ_SREG0 3 -#define XTENSA_IRQ_MAC 3 /* INTR_STATUS_REG_0, bit 0 */ -#define XTENSA_IRQ_MAC_NMI 4 /* INTR_STATUS_REG_0, bit 1 */ -#define XTENSA_IRQ_BB 5 /* INTR_STATUS_REG_0, bit 2 */ -#define XTENSA_IRQ_BB_MAC 6 /* INTR_STATUS_REG_0, bit 3 */ -#define XTENSA_IRQ_BT_BB 7 /* INTR_STATUS_REG_0, bit 4 */ -#define XTENSA_IRQ_BT_BB_NMI 8 /* INTR_STATUS_REG_0, bit 5 */ -#define XTENSA_IRQ_RWBT_IRQ 9 /* INTR_STATUS_REG_0, bit 6 */ -#define XTENSA_IRQ_RWBLE_IRQ 10 /* INTR_STATUS_REG_0, bit 7 */ -#define XTENSA_IRQ_RWBT_NMI 11 /* INTR_STATUS_REG_0, bit 8 */ -#define XTENSA_IRQ_RWBLE_NMI 12 /* INTR_STATUS_REG_0, bit 9 */ +#define ESP32_PERIPH_MAC 0 /* INTR_STATUS_REG_0, bit 0 */ +#define ESP32_PERIPH_MAC_NMI 1 /* INTR_STATUS_REG_0, bit 1 */ +#define ESP32_PERIPH_BB 2 /* INTR_STATUS_REG_0, bit 2 */ +#define ESP32_PERIPH_BB_MAC 3 /* INTR_STATUS_REG_0, bit 3 */ +#define ESP32_PERIPH_BT_BB 4 /* INTR_STATUS_REG_0, bit 4 */ +#define ESP32_PERIPH_BT_BB_NMI 5 /* INTR_STATUS_REG_0, bit 5 */ +#define ESP32_PERIPH_RWBT_IRQ 6 /* INTR_STATUS_REG_0, bit 6 */ +#define ESP32_PERIPH_RWBLE_IRQ 7 /* INTR_STATUS_REG_0, bit 7 */ +#define ESP32_PERIPH_RWBT_NMI 8 /* INTR_STATUS_REG_0, bit 8 */ +#define ESP32_PERIPH_RWBLE_NMI 9 /* INTR_STATUS_REG_0, bit 9 */ -#define XTENSA_IRQ_SLC0 13 /* INTR_STATUS_REG_0, bit 10 */ -#define XTENSA_IRQ_SLC1 14 /* INTR_STATUS_REG_0, bit 11 */ -#define XTENSA_IRQ_UHCI0 15 /* INTR_STATUS_REG_0, bit 12 */ -#define XTENSA_IRQ_UHCI1 16 /* INTR_STATUS_REG_0, bit 13 */ -#define XTENSA_IRQ_TG_T0_LEVEL 17 /* INTR_STATUS_REG_0, bit 14 */ -#define XTENSA_IRQ_TG_T1_LEVEL 18 /* INTR_STATUS_REG_0, bit 15 */ -#define XTENSA_IRQ_TG_WDT_LEVEL 19 /* INTR_STATUS_REG_0, bit 16 */ -#define XTENSA_IRQ_TG_LACT_LEVEL 20 /* INTR_STATUS_REG_0, bit 17 */ -#define XTENSA_IRQ_TG1_T0_LEVEL 21 /* INTR_STATUS_REG_0, bit 18 */ -#define XTENSA_IRQ_TG1_T1_LEVEL 22 /* INTR_STATUS_REG_0, bit 19 */ +#define ESP32_PERIPH_SLC0 10 /* INTR_STATUS_REG_0, bit 10 */ +#define ESP32_PERIPH_SLC1 11 /* INTR_STATUS_REG_0, bit 11 */ +#define ESP32_PERIPH_UHCI0 12 /* INTR_STATUS_REG_0, bit 12 */ +#define ESP32_PERIPH_UHCI1 13 /* INTR_STATUS_REG_0, bit 13 */ +#define ESP32_PERIPH_TG_T0_LEVEL 14 /* INTR_STATUS_REG_0, bit 14 */ +#define ESP32_PERIPH_TG_T1_LEVEL 15 /* INTR_STATUS_REG_0, bit 15 */ +#define ESP32_PERIPH_TG_WDT_LEVEL 16 /* INTR_STATUS_REG_0, bit 16 */ +#define ESP32_PERIPH_TG_LACT_LEVEL 17 /* INTR_STATUS_REG_0, bit 17 */ +#define ESP32_PERIPH_TG1_T0_LEVEL 18 /* INTR_STATUS_REG_0, bit 18 */ +#define ESP32_PERIPH_TG1_T1_LEVEL 19 /* INTR_STATUS_REG_0, bit 19 */ -#define XTENSA_IRQ_TG1_WDT_LEVEL 23 /* INTR_STATUS_REG_0, bit 20 */ -#define XTENSA_IRQ_G1_LACT_LEVEL 24 /* INTR_STATUS_REG_0, bit 21 */ -#define XTENSA_IRQ_CPU_GPIO 25 /* INTR_STATUS_REG_0, bit 22 */ -#define XTENSA_IRQ_CPU_NMI 26 /* INTR_STATUS_REG_0, bit 23 */ -#define XTENSA_IRQ_CPU_CPU0 27 /* INTR_STATUS_REG_0, bit 24 */ -#define XTENSA_IRQ_CPU_CPU1 28 /* INTR_STATUS_REG_0, bit 25 */ -#define XTENSA_IRQ_CPU_CPU2 29 /* INTR_STATUS_REG_0, bit 26 */ -#define XTENSA_IRQ_CPU_CPU3 30 /* INTR_STATUS_REG_0, bit 27 */ -#define XTENSA_IRQ_SPI0 31 /* INTR_STATUS_REG_0, bit 28 */ -#define XTENSA_IRQ_SPI1 32 /* INTR_STATUS_REG_0, bit 29 */ +#define ESP32_PERIPH_TG1_WDT_LEVEL 20 /* INTR_STATUS_REG_0, bit 20 */ +#define ESP32_PERIPH_G1_LACT_LEVEL 21 /* INTR_STATUS_REG_0, bit 21 */ +#define ESP32_PERIPH_CPU_GPIO 22 /* INTR_STATUS_REG_0, bit 22 */ +#define ESP32_PERIPH_CPU_NMI 23 /* INTR_STATUS_REG_0, bit 23 */ +#define ESP32_PERIPH_CPU_CPU0 24 /* INTR_STATUS_REG_0, bit 24 */ +#define ESP32_PERIPH_CPU_CPU1 25 /* INTR_STATUS_REG_0, bit 25 */ +#define ESP32_PERIPH_CPU_CPU2 26 /* INTR_STATUS_REG_0, bit 26 */ +#define ESP32_PERIPH_CPU_CPU3 27 /* INTR_STATUS_REG_0, bit 27 */ +#define ESP32_PERIPH_SPI0 28 /* INTR_STATUS_REG_0, bit 28 */ +#define ESP32_PERIPH_SPI1 29 /* INTR_STATUS_REG_0, bit 29 */ -#define XTENSA_IRQ_SPI2 33 /* INTR_STATUS_REG_0, bit 30 */ -#define XTENSA_IRQ_SPI3 34 /* INTR_STATUS_REG_0, bit 31 */ +#define ESP32_PERIPH_SPI2 30 /* INTR_STATUS_REG_0, bit 30 */ +#define ESP32_PERIPH_SPI3 31 /* INTR_STATUS_REG_0, bit 31 */ /* PRO_INTR_STATUS_REG_1 / APP_INTR_STATUS_REG_1 */ -#define XTENSA_IRQ_SREG1 35 -#define XTENSA_IRQ_I2S0 35 /* INTR_STATUS_REG_1, bit 0 */ -#define XTENSA_IRQ_I2S1 36 /* INTR_STATUS_REG_1, bit 1 */ -#define XTENSA_IRQ_UART 37 /* INTR_STATUS_REG_1, bit 2 */ -#define XTENSA_IRQ_UART1 38 /* INTR_STATUS_REG_1, bit 3 */ -#define XTENSA_IRQ_UART2 39 /* INTR_STATUS_REG_1, bit 4 */ -#define XTENSA_IRQ_SDIO_HOST 40 /* INTR_STATUS_REG_1, bit 5 */ -#define XTENSA_IRQ_EMAC 41 /* INTR_STATUS_REG_1, bit 6 */ -#define XTENSA_IRQ_PWM0 42 /* INTR_STATUS_REG_1, bit 7 */ -#define XTENSA_IRQ_PWM1 43 /* INTR_STATUS_REG_1, bit 8 */ -#define XTENSA_IRQ_PWM2 44 /* INTR_STATUS_REG_1, bit 9 */ +#define ESP32_PERIPH_I2S0 32 /* INTR_STATUS_REG_1, bit 0 */ +#define ESP32_PERIPH_I2S1 33 /* INTR_STATUS_REG_1, bit 1 */ +#define ESP32_PERIPH_UART 34 /* INTR_STATUS_REG_1, bit 2 */ +#define ESP32_PERIPH_UART1 35 /* INTR_STATUS_REG_1, bit 3 */ +#define ESP32_PERIPH_UART2 36 /* INTR_STATUS_REG_1, bit 4 */ +#define ESP32_PERIPH_SDIO_HOST 37 /* INTR_STATUS_REG_1, bit 5 */ +#define ESP32_PERIPH_EMAC 38 /* INTR_STATUS_REG_1, bit 6 */ +#define ESP32_PERIPH_PWM0 39 /* INTR_STATUS_REG_1, bit 7 */ +#define ESP32_PERIPH_PWM1 40 /* INTR_STATUS_REG_1, bit 8 */ +#define ESP32_PERIPH_PWM2 41 /* INTR_STATUS_REG_1, bit 9 */ -#define XTENSA_IRQ_PWM3 45 /* INTR_STATUS_REG_1, bit 10 */ -#define XTENSA_IRQ_LEDC 46 /* INTR_STATUS_REG_1, bit 11 */ -#define XTENSA_IRQ_EFUSE 47 /* INTR_STATUS_REG_1, bit 12 */ -#define XTENSA_IRQ_CAN 48 /* INTR_STATUS_REG_1, bit 13 */ -#define XTENSA_IRQ_RTC_CORE 49 /* INTR_STATUS_REG_1, bit 14 */ -#define XTENSA_IRQ_RMT 50 /* INTR_STATUS_REG_1, bit 15 */ -#define XTENSA_IRQ_PCNT 51 /* INTR_STATUS_REG_1, bit 16 */ -#define XTENSA_IRQ_I2C_EXT0 52 /* INTR_STATUS_REG_1, bit 17 */ -#define XTENSA_IRQ_I2C_EXT1 53 /* INTR_STATUS_REG_1, bit 18 */ -#define XTENSA_IRQ_RSA 54 /* INTR_STATUS_REG_1, bit 19 */ +#define ESP32_PERIPH_PWM3 42 /* INTR_STATUS_REG_1, bit 10 */ +#define ESP32_PERIPH_LEDC 43 /* INTR_STATUS_REG_1, bit 11 */ +#define ESP32_PERIPH_EFUSE 44 /* INTR_STATUS_REG_1, bit 12 */ +#define ESP32_PERIPH_CAN 45 /* INTR_STATUS_REG_1, bit 13 */ +#define ESP32_PERIPH_RTC_CORE 46 /* INTR_STATUS_REG_1, bit 14 */ +#define ESP32_PERIPH_RMT 47 /* INTR_STATUS_REG_1, bit 15 */ +#define ESP32_PERIPH_PCNT 48 /* INTR_STATUS_REG_1, bit 16 */ +#define ESP32_PERIPH_I2C_EXT0 49 /* INTR_STATUS_REG_1, bit 17 */ +#define ESP32_PERIPH_I2C_EXT1 50 /* INTR_STATUS_REG_1, bit 18 */ +#define ESP32_PERIPH_RSA 51 /* INTR_STATUS_REG_1, bit 19 */ -#define XTENSA_IRQ_SPI1_DMA 55 /* INTR_STATUS_REG_1, bit 20 */ -#define XTENSA_IRQ_SPI2_DMA 56 /* INTR_STATUS_REG_1, bit 21 */ -#define XTENSA_IRQ_SPI3_DMA 57 /* INTR_STATUS_REG_1, bit 22 */ -#define XTENSA_IRQ_WDG 58 /* INTR_STATUS_REG_1, bit 23 */ -#define XTENSA_IRQ_TIMER1 59 /* INTR_STATUS_REG_1, bit 24 */ -#define XTENSA_IRQ_TIMER2 60 /* INTR_STATUS_REG_1, bit 25 */ -#define XTENSA_IRQ_TG_T0_EDGE 61 /* INTR_STATUS_REG_1, bit 26 */ -#define XTENSA_IRQ_TG_T1_EDGE 62 /* INTR_STATUS_REG_1, bit 27 */ -#define XTENSA_IRQ_TG_WDT_EDGE 63 /* INTR_STATUS_REG_1, bit 28 */ -#define XTENSA_IRQ_TG_LACT_EDGE 64 /* INTR_STATUS_REG_1, bit 29 */ +#define ESP32_PERIPH_SPI1_DMA 52 /* INTR_STATUS_REG_1, bit 20 */ +#define ESP32_PERIPH_SPI2_DMA 53 /* INTR_STATUS_REG_1, bit 21 */ +#define ESP32_PERIPH_SPI3_DMA 54 /* INTR_STATUS_REG_1, bit 22 */ +#define ESP32_PERIPH_WDG 55 /* INTR_STATUS_REG_1, bit 23 */ +#define ESP32_PERIPH_TIMER1 56 /* INTR_STATUS_REG_1, bit 24 */ +#define ESP32_PERIPH_TIMER2 57 /* INTR_STATUS_REG_1, bit 25 */ +#define ESP32_PERIPH_TG_T0_EDGE 58 /* INTR_STATUS_REG_1, bit 26 */ +#define ESP32_PERIPH_TG_T1_EDGE 59 /* INTR_STATUS_REG_1, bit 27 */ +#define ESP32_PERIPH_TG_WDT_EDGE 60 /* INTR_STATUS_REG_1, bit 28 */ +#define ESP32_PERIPH_TG_LACT_EDGE 61 /* INTR_STATUS_REG_1, bit 29 */ -#define XTENSA_IRQ_TG1_T0_EDGE 65 /* INTR_STATUS_REG_1, bit 30 */ -#define XTENSA_IRQ_TG1_T1_EDGE 66 /* INTR_STATUS_REG_1, bit 31 */ +#define ESP32_PERIPH_TG1_T0_EDGE 62 /* INTR_STATUS_REG_1, bit 30 */ +#define ESP32_PERIPH_TG1_T1_EDGE 63 /* INTR_STATUS_REG_1, bit 31 */ /* PRO_INTR_STATUS_REG_2 / APP_INTR_STATUS_REG_2 */ -#define XTENSA_IRQ_SREG2 67 -#define XTENSA_IRQ_TG1_WDT_EDGE 67 /* INTR_STATUS_REG_2, bit 0 */ -#define XTENSA_IRQ_TG1_LACT_EDGE 68 /* INTR_STATUS_REG_2, bit 1 */ -#define XTENSA_IRQ_MMU_IA 69 /* INTR_STATUS_REG_2, bit 2 */ -#define XTENSA_IRQ_MPU_IA 70 /* INTR_STATUS_REG_2, bit 3 */ -#define XTENSA_IRQ_CACHE_IA 71 /* INTR_STATUS_REG_2, bit 4 */ +#define ESP32_PERIPH_TG1_WDT_EDGE 64 /* INTR_STATUS_REG_2, bit 0 */ +#define ESP32_PERIPH_TG1_LACT_EDGE 65 /* INTR_STATUS_REG_2, bit 1 */ +#define ESP32_PERIPH_MMU_IA 66 /* INTR_STATUS_REG_2, bit 2 */ +#define ESP32_PERIPH_MPU_IA 67 /* INTR_STATUS_REG_2, bit 3 */ +#define ESP32_PERIPH_CACHE_IA 68 /* INTR_STATUS_REG_2, bit 4 */ + +/* Total number of peripherals */ + +#define NR_PERIPHERALS 69 + +/* Exceptions + * + * IRAM Offset Description + * 0x0000 Windows + * 0x0180 Level 2 interrupt + * 0x01c0 Level 3 interrupt + * 0x0200 Level 4 interrupt + * 0x0240 Level 5 interrupt + * 0x0280 Debug exception + * 0x02c0 NMI exception + * 0x0300 Kernel exception + * 0x0340 User exception + * 0x03c0 Double exception + * + * REVISIT: In more architectures supported by NuttX, exception errors + * tie into the normal interrupt handling via special IRQ numbers. I + * is still to be determined what will be done for the ESP32. + */ + +/* IRQ numbers for internal interrupts that are dispatched like peripheral + * interrupts + */ + +#define XTENSA_IRQ_TIMER0 0 /* INTERRUPT, bit 6 */ +#define XTENSA_IRQ_TIMER1 1 /* INTERRUPT, bit 15 */ +#define XTENSA_IRQ_TIMER2 2 /* INTERRUPT, bit 16 */ + +#define XTENSA_IRQ_FIRSTPERIPH 3 /* First peripheral IRQ number */ + +/* IRQ numbers for peripheral interrupts coming throught the Interrupt + * Matrix. + */ + +#define ESP32_IRQ2PERIPH(irq) ((irq)-XTENSA_IRQ_FIRSTPERIPH) + +/* PRO_INTR_STATUS_REG_0 / APP_INTR_STATUS_REG_0 */ + +#define ESP32_IRQ_MAC (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_MAC) +#define ESP32_IRQ_MAC_NMI (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_MAC_NMI) +#define ESP32_IRQ_BB (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_BB) +#define ESP32_IRQ_BB_MAC (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_BB_MAC) +#define ESP32_IRQ_BT_BB (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_BT_BB) +#define ESP32_IRQ_BT_BB_NMI (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_BT_BB_NMI) +#define ESP32_IRQ_RWBT_IRQ (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RWBT_IRQ) +#define ESP32_IRQ_RWBLE_IRQ (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RWBLE_IRQ) +#define ESP32_IRQ_RWBT_NMI (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RWBT_NMI) +#define ESP32_IRQ_RWBLE_NMI (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RWBLE_NMI) +#define ESP32_IRQ_SLC0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SLC0) +#define ESP32_IRQ_SLC1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SLC1) +#define ESP32_IRQ_UHCI0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_UHCI0) +#define ESP32_IRQ_UHCI1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_UHCI1) +#define ESP32_IRQ_TG_T0_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_T0_LEVEL) +#define ESP32_IRQ_TG_T1_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_T1_LEVEL) +#define ESP32_IRQ_TG_WDT_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_WDT_LEVEL) +#define ESP32_IRQ_TG_LACT_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_LACT_LEVEL) +#define ESP32_IRQ_TG1_T0_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_T0_LEVEL) +#define ESP32_IRQ_TG1_T1_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_T1_LEVEL) +#define ESP32_IRQ_TG1_WDT_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_WDT_LEVEL) +#define ESP32_IRQ_G1_LACT_LEVEL (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_G1_LACT_LEVEL) +#define ESP32_IRQ_CPU_GPIO (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CPU_GPIO) +#define ESP32_IRQ_CPU_NMI (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CPU_NMI) +#define ESP32_IRQ_CPU_CPU0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CPU_CPU0) +#define ESP32_IRQ_CPU_CPU1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CPU_CPU1) +#define ESP32_IRQ_CPU_CPU2 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CPU_CPU2) +#define ESP32_IRQ_CPU_CPU3 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CPU_CPU3) +#define ESP32_IRQ_SPI0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI0) +#define ESP32_IRQ_SPI1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI1 +#define ESP32_IRQ_SPI2 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI2) +#define ESP32_IRQ_SPI3 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI3 + +#define ESP32_IRQ_SREG0 ESP32_IRQ_MAC +#define ESP32_NIRQS_SREG0 32 + +/* PRO_INTR_STATUS_REG_1 / APP_INTR_STATUS_REG_1 */ + +#define ESP32_IRQ_I2S0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_I2S0) +#define ESP32_IRQ_I2S1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_I2S1) +#define ESP32_IRQ_UART (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_UART) +#define ESP32_IRQ_UART1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_UART1) +#define ESP32_IRQ_UART2 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_UART2) +#define ESP32_IRQ_SDIO_HOST (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SDIO_HOST) +#define ESP32_IRQ_EMAC (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_EMAC) +#define ESP32_IRQ_PWM0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_PWM0) +#define ESP32_IRQ_PWM1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_PWM1) +#define ESP32_IRQ_PWM2 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_PWM2) +#define ESP32_IRQ_PWM3 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_PWM3) +#define ESP32_IRQ_LEDC (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_LEDC) +#define ESP32_IRQ_EFUSE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_EFUSE) +#define ESP32_IRQ_CAN (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CAN) +#define ESP32_IRQ_RTC_CORE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RTC_CORE) +#define ESP32_IRQ_RMT (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RMT) +#define ESP32_IRQ_PCNT (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_PCNT) +#define ESP32_IRQ_I2C_EXT0 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_I2C_EXT0) +#define ESP32_IRQ_I2C_EXT1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_I2C_EXT1) +#define ESP32_IRQ_RSA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_RSA) +#define ESP32_IRQ_SPI1_DMA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI1_DMA) +#define ESP32_IRQ_SPI2_DMA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI2_DMA) +#define ESP32_IRQ_SPI3_DMA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_SPI3_DMA) +#define ESP32_IRQ_WDG (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_WDG) +#define ESP32_IRQ_TIMER1 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TIMER1) +#define ESP32_IRQ_TIMER2 (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TIMER2) +#define ESP32_IRQ_TG_T0_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_T0_EDGE) +#define ESP32_IRQ_TG_T1_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_T1_EDGE) +#define ESP32_IRQ_TG_WDT_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_WDT_EDGE) +#define ESP32_IRQ_TG_LACT_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG_LACT_EDGE) +#define ESP32_IRQ_TG1_T0_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_T0_EDGE) +#define ESP32_IRQ_TG1_T1_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_T1_EDGE) + +#define ESP32_IRQ_SREG1 ESP32_IRQ_I2S0 +#define ESP32_NIRQS_SREG1 32 + +/* PRO_INTR_STATUS_REG_2 / APP_INTR_STATUS_REG_2 */ + +#define ESP32_IRQ_TG1_WDT_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_WDT_EDGE) +#define ESP32_IRQ_TG1_LACT_EDGE (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_TG1_LACT_EDGE) +#define ESP32_IRQ_MMU_IA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_MMU_IA) +#define ESP32_IRQ_MPU_IA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_MPU_IA) +#define ESP32_IRQ_CACHE_IA (XTENSA_IRQ_FIRSTPERIPH+ESP32_PERIPH_CACHE_IA) + +#define ESP32_IRQ_SREG2 ESP32_IRQ_TG1_WDT_EDGE +#define ESP32_NIRQS_SREG2 5 /* Total number of interrupts */ -#define NR_IRQS 72 +#define NR_IRQS (ESP32_IRQ_CACHE_IA+1) + +/* CPU Interrupts. + * + * Each of the two CPUs (PRO and APP) have 32 interrupts each, of which + * 26 can be mapped to peripheral interrupts: + * + * Level triggered peripherals (21 total): + * 0-5, 8-9, 12-13, 17-18 - Priority 1 + * 19-21 - Priority 2 + * 23, 27 - Priority 3 + * 24-25 - Priority 4 + * 26, 31 - Priority 5 + * Edge triggered peripherals (4 total): + * 10 - Priority 1 + * 22 - Priority 3 + * 28, 30 - Priority 4 + * NMI (1 total): + * 14 - NMI + * + * CPU peripheral interrupts can be a assigned to a CPU interrupt using the + * PRO_*_MAP_REG or APP_*_MAP_REG. There are a pair of these registers for + * each peripheral source. Multiple peripheral interrupt sources can be + * mapped to the same. + * + * The remaining, five, internal CPU interrupts are: + * + * 6 Timer0 - Priority 1 + * 7 Software - Priority 1 + * 11 Profiling - Priority 3 + * 15 Timer1 - Priority 3 + * 16 Timer2 - Priority 5 + * 29 Software - Priority 3 + * + * A peripheral interrupt can be disabled + */ + +#define ESP32_CPUINT_LEVELPERIPH_0 0 +#define ESP32_CPUINT_LEVELPERIPH_1 1 +#define ESP32_CPUINT_LEVELPERIPH_2 2 +#define ESP32_CPUINT_LEVELPERIPH_3 3 +#define ESP32_CPUINT_LEVELPERIPH_4 4 +#define ESP32_CPUINT_LEVELPERIPH_5 5 +#define ESP32_CPUINT_LEVELPERIPH_6 8 +#define ESP32_CPUINT_LEVELPERIPH_7 9 +#define ESP32_CPUINT_LEVELPERIPH_8 12 +#define ESP32_CPUINT_LEVELPERIPH_9 13 +#define ESP32_CPUINT_LEVELPERIPH_10 17 +#define ESP32_CPUINT_LEVELPERIPH_11 18 +#define ESP32_CPUINT_LEVELPERIPH_12 19 +#define ESP32_CPUINT_LEVELPERIPH_13 20 +#define ESP32_CPUINT_LEVELPERIPH_14 21 +#define ESP32_CPUINT_LEVELPERIPH_15 23 +#define ESP32_CPUINT_LEVELPERIPH_16 24 +#define ESP32_CPUINT_LEVELPERIPH_17 25 +#define ESP32_CPUINT_LEVELPERIPH_18 26 +#define ESP32_CPUINT_LEVELPERIPH_19 27 +#define ESP32_CPUINT_LEVELPERIPH_20 31 +#define ESP32_CPUINT_NLEVELPERIPHS 21 + +#define ESP32_CPUINT_EDGEPERIPH_0 10 +#define ESP32_CPUINT_EDGEPERIPH_1 22 +#define ESP32_CPUINT_EDGEPERIPH_2 28 +#define ESP32_CPUINT_EDGEPERIPH_3 30 +#define ESP32_CPUINT_NEDGEPERIPHS 4 + +#define ESP32_CPUINT_TIMER0 6 +#define ESP32_CPUINT_SOFTWARE0 7 +#define ESP32_CPUINT_TIMER1 15 +#define ESP32_CPUINT_TIMER2 16 +#define ESP32_CPUINT_SOFTWARE1 29 +#define ESP32_CPUINT_NINTERNAL 5 + +#define ESP32_CPUINT_MAX 31 +#define EPS32_CPUINT_PERIPHSET 0xdffe7f3f +#define EPS32_CPUINT_INTERNALSET 0x200180c0 + +/* Priority 1: 0-10, 12-13, 17-18 (15) + * Priority 2: 19-21 (3) + * Priority 3: 11, 15, 22-23, 27, 29 (6) + * Priority 4: 24-25, 28, 30 (4) + * Priority 5: 16, 26, 31 (3) + * Priority NMI: 14 (1) + */ + +#define ESP32_INTPRI1_MASK 0x000637ff +#define ESP32_INTPRI2_MASK 0x00380000 +#define ESP32_INTPRI3_MASK 0x28c08800 +#define ESP32_INTPRI4_MASK 0x53000000 +#define ESP32_INTPRI5_MASK 0x84010000 +#define ESP32_INTNMI_MASK 0x00004000 /**************************************************************************** * Public Types diff --git a/arch/xtensa/src/common/xtensa.h b/arch/xtensa/src/common/xtensa.h index fb13a8150a8..bde2eaba5f8 100644 --- a/arch/xtensa/src/common/xtensa.h +++ b/arch/xtensa/src/common/xtensa.h @@ -156,13 +156,6 @@ extern volatile uint32_t *g_current_regs[1]; #endif -/* This is the beginning of heap as provided from *_head.S. This is the - * first address in DRAM after the loaded program+bss+idle stack. The end - * of the heap is CONFIG_RAM_END - */ - -extern uint32_t g_idle_topstack; - /* Address of the saved user stack pointer */ #if CONFIG_ARCH_INTERRUPTSTACK > 3 @@ -243,6 +236,8 @@ void xtensa_dumpstate(void); uint32_t *xtensa_int_decode(uint32_t *regs); uint32_t *xtensa_irq_dispatch(int irq, uint32_t *regs); +uint32_t xtensa_enable_cpuint(uint32_t *shadow, uint32_t intmask); +uint32_t xtensa_disable_cpuint(uint32_t *shadow, uint32_t intmask); /* Software interrupt handler */ diff --git a/arch/xtensa/src/common/xtensa_cpuint.S b/arch/xtensa/src/common/xtensa_cpuint.S new file mode 100644 index 00000000000..6ea46d71d41 --- /dev/null +++ b/arch/xtensa/src/common/xtensa_cpuint.S @@ -0,0 +1,126 @@ +/**************************************************************************** + * arch/xtensa/src/common/xtensa_cpuint.S + * + * Adapted from use in NuttX by: + * + * Copyright (C) 2016 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt + * + * Derives from logic originally provided by Cadence Design Systems Inc. + * + * Copyright (c) 2006-2015 Cadence Design Systems Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining + * a copy of this software and associated documentation files (the + * "Software"), to deal in the Software without restriction, including + * without limitation the rights to use, copy, modify, merge, publish, + * distribute, sublicense, and/or sell copies of the Software, and to + * permit persons to whom the Software is furnished to do so, subject to + * the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY + * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, + * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE + * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + ****************************************************************************/ + + .file "xtensa_cpuint.S" + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include +#include + +#if XCHAL_HAVE_INTERRUPTS + +/**************************************************************************** + * Public Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: xtensa_enable_cpuint + * + * C Prototype: + * uint32_t xtensa_enable_cpuint(uint32_t *shadow, unsigned int intmask) + * + * Description: + * Enables a set of interrupts. Does not simply set INTENABLE directly, + * but operates on a shadow copy of the CPU INTENABLE register then + * writes that value to the hardware INTENABLE register. Can be called + * from interrupt handlers. + * + * NOTE: It is possible only to enable interrupts on the current CPU + * because there is an INTENABLE register implemented in each CPU. + * + ****************************************************************************/ + + .text + .global xtensa_enable_cpuint + .type xtensa_enable_cpuint, @function + .align 4 + +xtensa_enable_cpuint: + + movi a4, 0 + xsr a4, INTENABLE /* Disables all interrupts */ + rsync + + l32i a4, a2, 0 /* a4 = value of INTENABLE shadow */ + or a5, a4, a3 /* a5 = shadow | mask */ + s32i a5, a2, 0 /* shadow |= mask */ + + wsr a5, INTENABLE /* Set CPU INTENABLE to shadow */ + mov a3, a4 /* Return previous shadow content */ + ret + + .size xtensa_enable_cpuint, . - xtensa_enable_cpuint + +/**************************************************************************** + * Name: xtensa_disable_cpuint + * + * C Prototype: + * uint32_t xtensa_disable_cpuint(uint32_t *shadow, unsigned int intmask) + * + * Description: + * Disables a set of interrupts. Does not simply set INTENABLE directly, + * but operates on a shadow copy of the CPU INTENABLE register then + * writes that value to the hardware INTENABLE register. Can be called + * from interrupt handlers. + * + * NOTE: It is possible only to enable interrupts on the current CPU + * because there is an INTENABLE register implemented in each CPU. + * + ****************************************************************************/ + + .text + .global xtensa_disable_cpuint + .type xtensa_disable_cpuint, @function + .align 4 + +xtensa_disable_cpuint: + + movi a4, 0 + xsr a4, INTENABLE /* Disables all interrupts */ + rsync + + l32i a4, a2, 0 /* a4 = value of INTENABLE shadow */ + or a5, a4, a3 /* a5 = shadow | mask */ + xor a5, a5, a3 /* a5 = shadow & ~mask */ + s32i a5, a2, 0 /* shadow &= ~mask */ + + wsr a5, INTENABLE /* Set CPU INTENABLE to shadow */ + mov a3, a4 /* Return previous shadow content */ + ret + + .size xtensa_disable_cpuint, . - xtensa_disable_cpuint + +#endif /* XCHAL_HAVE_INTERRUPTS */ diff --git a/arch/xtensa/src/common/xtensa_dumpstate.c b/arch/xtensa/src/common/xtensa_dumpstate.c index 74de6d74a55..f99f3d905cd 100644 --- a/arch/xtensa/src/common/xtensa_dumpstate.c +++ b/arch/xtensa/src/common/xtensa_dumpstate.c @@ -150,12 +150,24 @@ void xtensa_dumpstate(void) uint32_t istacksize; #endif +#ifdef CONFIG_SMP + /* Show the CPU number */ + + _alert("CPU%d:\n", up_cpu_index()); +#endif + /* Get the limits on the user stack memory */ if (rtcb->pid == 0) { +#warning REVISIT: Need top of IDLE stack +#if 0 ustackbase = g_idle_topstack - 4; ustacksize = CONFIG_IDLETHREAD_STACKSIZE; +#else + ustackbase = sp + 128; + ustacksize = 128; +#endif } else { diff --git a/arch/xtensa/src/common/xtensa_inthandlers.S b/arch/xtensa/src/common/xtensa_inthandlers.S index af4e068728d..b716c9f1f23 100644 --- a/arch/xtensa/src/common/xtensa_inthandlers.S +++ b/arch/xtensa/src/common/xtensa_inthandlers.S @@ -62,9 +62,9 @@ #include #include #include -#include #include "xtensa_macros.h" +#include "chip_macros.h" #include "xtensa_timer.h" /**************************************************************************** diff --git a/arch/xtensa/src/common/xtensa_nmihandler.S b/arch/xtensa/src/common/xtensa_nmihandler.S index 0720b1fe71f..7f10b2ae6a5 100644 --- a/arch/xtensa/src/common/xtensa_nmihandler.S +++ b/arch/xtensa/src/common/xtensa_nmihandler.S @@ -61,8 +61,8 @@ #include #include -#include +#include "chip_macros.h" #include "xtensa_macros.h" /**************************************************************************** diff --git a/arch/xtensa/src/esp32/Make.defs b/arch/xtensa/src/esp32/Make.defs index 993965dac87..5952d793776 100644 --- a/arch/xtensa/src/esp32/Make.defs +++ b/arch/xtensa/src/esp32/Make.defs @@ -40,18 +40,18 @@ HEAD_CSRC = esp32_start.c # Common XTENSA files (arch/xtensa/src/common) -CMN_ASRCS = xtensa_context.S xtensa_vectors.S xtensa_inthandlers.S -CMN_ASRCS += xtensa_nmihandler.S +CMN_ASRCS = xtensa_context.S xtensa_cpuint.S xtensa_vectors.S +CMN_ASRCS += xtensa_inthandlers.S xtensa_nmihandler.S CMN_CSRCS = xtensa_assert.c xtensa_blocktask.c xtensa_copystate.c -CMN_CSRCS += xtensa_createstack.c xtensa_exit.c xtensa_idle.c -CMN_CSRCS += xtensa_initialize.c xtensa_initialstate.c -CMN_CSRCS += xtensa_interruptcontext.c xtensa_irqdispatch.c xtensa_lowputs.c -CMN_CSRCS += xtensa_mdelay.c xtensa_modifyreg8.c xtensa_modifyreg16.c -CMN_CSRCS += xtensa_modifyreg32.c xtensa_puts.c xtensa_releasepending.c -CMN_CSRCS += xtensa_releasestack.c xtensa_reprioritizertr.c -CMN_CSRCS += xtensa_schedsigaction.c xtensa_sigdeliver.c xtensa_stackframe.c -CMN_CSRCS += xtensa_udelay.c xtensa_unblocktask.c xtensa_usestack.c +CMN_CSRCS += xtensa_createstack.c xtensa_exit.c xtensa_idle.c +CMN_CSRCS += xtensa_initialize.c xtensa_initialstate.c xtensa_interruptcontext.c +CMN_CSRCS += xtensa_irqdispatch.c xtensa_lowputs.c xtensa_mdelay.c +CMN_CSRCS += xtensa_modifyreg8.c xtensa_modifyreg16.c xtensa_modifyreg32.c +CMN_CSRCS += xtensa_puts.c xtensa_releasepending.c xtensa_releasestack.c +CMN_CSRCS += xtensa_reprioritizertr.c xtensa_schedsigaction.c +CMN_CSRCS += xtensa_sigdeliver.c xtensa_stackframe.c xtensa_udelay.c +CMN_CSRCS += xtensa_unblocktask.c xtensa_usestack.c # Configuration-dependent common XTENSA files @@ -77,8 +77,9 @@ endif # Required ESP32 files (arch/xtensa/src/lx6) CHIP_ASRCS = -CHIP_CSRCS = esp32_allocateheap.c esp32_intdecode.c esp32_irq.c -CHIP_CSRCS += esp32_region.c esp32_start.c esp32_timerisr.c +CHIP_CSRCS = esp32_allocateheap.c esp32_clockconfig.c esp32_cpuint.c +CHIP_CSRCS += esp32_intdecode.c esp32_irq.c esp32_region.c esp32_start.c +CHIP_CSRCS += esp32_timerisr.c # Configuration-dependent ESP32 files diff --git a/arch/xtensa/src/esp32/chip/esp32_uart.h b/arch/xtensa/src/esp32/chip/esp32_uart.h new file mode 100644 index 00000000000..f13a5c234c8 --- /dev/null +++ b/arch/xtensa/src/esp32/chip/esp32_uart.h @@ -0,0 +1,1668 @@ +/**************************************************************************** + * arch/xtensa/src/esp32/chip/esp32_uart.h + * + * Adapted from use in NuttX by: + * + * Copyright (C) 2016 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt + * + * Derives from logic originally provided by Espressif Systems: + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + ****************************************************************************/ + +#ifndef __ARCH_XTENSA_SRC_ESP32_CHIP_ESP32_UART_H +#define __ARCH_XTENSA_SRC_ESP32_CHIP_ESP32_UART_H + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include "chip/esp32_soc.h" + +/**************************************************************************** + * Pre-processor Macros + ****************************************************************************/ + +#define REG_UART_BASE(i) (DR_REG_UART_BASE + (i) * 0x10000 + (i > 1 ? 0xe000 : 0)) + +#define UART_FIFO_REG(i) (REG_UART_BASE(i) + 0x0) + +/* UART_RXFIFO_RD_BYTE : RO ;bitpos:[7:0] ;default: 8'b0 ; */ +/* Description: This register stores one byte data read by rx fifo.*/ + +#define UART_RXFIFO_RD_BYTE 0x000000FF +#define UART_RXFIFO_RD_BYTE_M ((UART_RXFIFO_RD_BYTE_V)<<(UART_RXFIFO_RD_BYTE_S)) +#define UART_RXFIFO_RD_BYTE_V 0xFF +#define UART_RXFIFO_RD_BYTE_S 0 + +#define UART_INT_RAW_REG(i) (REG_UART_BASE(i) + 0x4) + +/* UART_AT_CMD_CHAR_DET_INT_RAW : RO ;bitpos:[18] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects the configured at_cmd chars. + */ + +#define UART_AT_CMD_CHAR_DET_INT_RAW (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_RAW_M (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_RAW_V 0x1 +#define UART_AT_CMD_CHAR_DET_INT_RAW_S 18 + +/* UART_RS485_CLASH_INT_RAW : RO ;bitpos:[17] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when rs485 detects + * the clash between transmitter and receiver. + */ + +#define UART_RS485_CLASH_INT_RAW (BIT(17)) +#define UART_RS485_CLASH_INT_RAW_M (BIT(17)) +#define UART_RS485_CLASH_INT_RAW_V 0x1 +#define UART_RS485_CLASH_INT_RAW_S 17 + +/* UART_RS485_FRM_ERR_INT_RAW : RO ;bitpos:[16] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when rs485 detects + * the data frame error. + */ + +#define UART_RS485_FRM_ERR_INT_RAW (BIT(16)) +#define UART_RS485_FRM_ERR_INT_RAW_M (BIT(16)) +#define UART_RS485_FRM_ERR_INT_RAW_V 0x1 +#define UART_RS485_FRM_ERR_INT_RAW_S 16 + +/* UART_RS485_PARITY_ERR_INT_RAW : RO ;bitpos:[15] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when rs485 + * detects the parity error. + */ + +#define UART_RS485_PARITY_ERR_INT_RAW (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_RAW_M (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_RAW_V 0x1 +#define UART_RS485_PARITY_ERR_INT_RAW_S 15 + +/* UART_TX_DONE_INT_RAW : RO ;bitpos:[14] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when transmitter + * has send all the data in fifo. + */ + +#define UART_TX_DONE_INT_RAW (BIT(14)) +#define UART_TX_DONE_INT_RAW_M (BIT(14)) +#define UART_TX_DONE_INT_RAW_V 0x1 +#define UART_TX_DONE_INT_RAW_S 14 + +/* UART_TX_BRK_IDLE_DONE_INT_RAW : RO ;bitpos:[13] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when transmitter + * has kept the shortest duration after the last data has been send. + */ + +#define UART_TX_BRK_IDLE_DONE_INT_RAW (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_RAW_M (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_RAW_V 0x1 +#define UART_TX_BRK_IDLE_DONE_INT_RAW_S 13 + +/* UART_TX_BRK_DONE_INT_RAW : RO ;bitpos:[12] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when transmitter + * completes sending 0 after all the datas in transmitter's fifo are send. + */ + +#define UART_TX_BRK_DONE_INT_RAW (BIT(12)) +#define UART_TX_BRK_DONE_INT_RAW_M (BIT(12)) +#define UART_TX_BRK_DONE_INT_RAW_V 0x1 +#define UART_TX_BRK_DONE_INT_RAW_S 12 + +/* UART_GLITCH_DET_INT_RAW : RO ;bitpos:[11] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects the start bit. + */ + +#define UART_GLITCH_DET_INT_RAW (BIT(11)) +#define UART_GLITCH_DET_INT_RAW_M (BIT(11)) +#define UART_GLITCH_DET_INT_RAW_V 0x1 +#define UART_GLITCH_DET_INT_RAW_S 11 + +/* UART_SW_XOFF_INT_RAW : RO ;bitpos:[10] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * receives xon char with uart_sw_flow_con_en is set to 1. + */ + +#define UART_SW_XOFF_INT_RAW (BIT(10)) +#define UART_SW_XOFF_INT_RAW_M (BIT(10)) +#define UART_SW_XOFF_INT_RAW_V 0x1 +#define UART_SW_XOFF_INT_RAW_S 10 + +/* UART_SW_XON_INT_RAW : RO ;bitpos:[9] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * receives xoff char with uart_sw_flow_con_en is set to 1. + */ + +#define UART_SW_XON_INT_RAW (BIT(9)) +#define UART_SW_XON_INT_RAW_M (BIT(9)) +#define UART_SW_XON_INT_RAW_V 0x1 +#define UART_SW_XON_INT_RAW_S 9 + +/* UART_RXFIFO_TOUT_INT_RAW : RO ;bitpos:[8] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * takes more time than rx_tout_thrhd to receive a byte. + */ + +#define UART_RXFIFO_TOUT_INT_RAW (BIT(8)) +#define UART_RXFIFO_TOUT_INT_RAW_M (BIT(8)) +#define UART_RXFIFO_TOUT_INT_RAW_V 0x1 +#define UART_RXFIFO_TOUT_INT_RAW_S 8 + +/* UART_BRK_DET_INT_RAW : RO ;bitpos:[7] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects the 0 after the stop bit. + */ + +#define UART_BRK_DET_INT_RAW (BIT(7)) +#define UART_BRK_DET_INT_RAW_M (BIT(7)) +#define UART_BRK_DET_INT_RAW_V 0x1 +#define UART_BRK_DET_INT_RAW_S 7 + +/* UART_CTS_CHG_INT_RAW : RO ;bitpos:[6] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects the edge change of ctsn signal. + */ + +#define UART_CTS_CHG_INT_RAW (BIT(6)) +#define UART_CTS_CHG_INT_RAW_M (BIT(6)) +#define UART_CTS_CHG_INT_RAW_V 0x1 +#define UART_CTS_CHG_INT_RAW_S 6 + +/* UART_DSR_CHG_INT_RAW : RO ;bitpos:[5] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects the edge change of dsrn signal. + */ + +#define UART_DSR_CHG_INT_RAW (BIT(5)) +#define UART_DSR_CHG_INT_RAW_M (BIT(5)) +#define UART_DSR_CHG_INT_RAW_V 0x1 +#define UART_DSR_CHG_INT_RAW_S 5 + +/* UART_RXFIFO_OVF_INT_RAW : RO ;bitpos:[4] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * receives more data than the fifo can store. + */ + +#define UART_RXFIFO_OVF_INT_RAW (BIT(4)) +#define UART_RXFIFO_OVF_INT_RAW_M (BIT(4)) +#define UART_RXFIFO_OVF_INT_RAW_V 0x1 +#define UART_RXFIFO_OVF_INT_RAW_S 4 + +/* UART_FRM_ERR_INT_RAW : RO ;bitpos:[3] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects data's frame error. + */ + +#define UART_FRM_ERR_INT_RAW (BIT(3)) +#define UART_FRM_ERR_INT_RAW_M (BIT(3)) +#define UART_FRM_ERR_INT_RAW_V 0x1 +#define UART_FRM_ERR_INT_RAW_S 3 + +/* UART_PARITY_ERR_INT_RAW : RO ;bitpos:[2] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * detects the parity error of data. + */ + +#define UART_PARITY_ERR_INT_RAW (BIT(2)) +#define UART_PARITY_ERR_INT_RAW_M (BIT(2)) +#define UART_PARITY_ERR_INT_RAW_V 0x1 +#define UART_PARITY_ERR_INT_RAW_S 2 + +/* UART_TXFIFO_EMPTY_INT_RAW : RO ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when the amount + * of data in transmitter's fifo is less than ((tx_mem_cnttxfifo_cnt). + */ + +#define UART_TXFIFO_EMPTY_INT_RAW (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_RAW_M (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_RAW_V 0x1 +#define UART_TXFIFO_EMPTY_INT_RAW_S 1 + +/* UART_RXFIFO_FULL_INT_RAW : RO ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: This interrupt raw bit turns to high level when receiver + * receives more data than (rx_flow_thrhd_h3 rx_flow_thrhd). + */ + +#define UART_RXFIFO_FULL_INT_RAW (BIT(0)) +#define UART_RXFIFO_FULL_INT_RAW_M (BIT(0)) +#define UART_RXFIFO_FULL_INT_RAW_V 0x1 +#define UART_RXFIFO_FULL_INT_RAW_S 0 + +#define UART_INT_ST_REG(i) (REG_UART_BASE(i) + 0x8) + +/* UART_AT_CMD_CHAR_DET_INT_ST : RO ;bitpos:[18] ;default: 1'b0 ; */ +/* Description: This is the status bit for at_cmd_det_int_raw when + * at_cmd_char_det_int_ena is set to 1. + */ + +#define UART_AT_CMD_CHAR_DET_INT_ST (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_ST_M (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_ST_V 0x1 +#define UART_AT_CMD_CHAR_DET_INT_ST_S 18 + +/* UART_RS485_CLASH_INT_ST : RO ;bitpos:[17] ;default: 1'b0 ; */ +/* Description: This is the status bit for rs485_clash_int_raw when + * rs485_clash_int_ena is set to 1. + */ + +#define UART_RS485_CLASH_INT_ST (BIT(17)) +#define UART_RS485_CLASH_INT_ST_M (BIT(17)) +#define UART_RS485_CLASH_INT_ST_V 0x1 +#define UART_RS485_CLASH_INT_ST_S 17 + +/* UART_RS485_FRM_ERR_INT_ST : RO ;bitpos:[16] ;default: 1'b0 ; */ +/* Description: This is the status bit for rs485_fm_err_int_raw when + * rs485_fm_err_int_ena is set to 1. + */ + +#define UART_RS485_FRM_ERR_INT_ST (BIT(16)) +#define UART_RS485_FRM_ERR_INT_ST_M (BIT(16)) +#define UART_RS485_FRM_ERR_INT_ST_V 0x1 +#define UART_RS485_FRM_ERR_INT_ST_S 16 + +/* UART_RS485_PARITY_ERR_INT_ST : RO ;bitpos:[15] ;default: 1'b0 ; */ +/* Description: This is the status bit for rs485_parity_err_int_raw when + * rs485_parity_int_ena is set to 1. + */ + +#define UART_RS485_PARITY_ERR_INT_ST (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_ST_M (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_ST_V 0x1 +#define UART_RS485_PARITY_ERR_INT_ST_S 15 + +/* UART_TX_DONE_INT_ST : RO ;bitpos:[14] ;default: 1'b0 ; */ +/* Description: This is the status bit for tx_done_int_raw when + * tx_done_int_ena is set to 1. + */ + +#define UART_TX_DONE_INT_ST (BIT(14)) +#define UART_TX_DONE_INT_ST_M (BIT(14)) +#define UART_TX_DONE_INT_ST_V 0x1 +#define UART_TX_DONE_INT_ST_S 14 + +/* UART_TX_BRK_IDLE_DONE_INT_ST : RO ;bitpos:[13] ;default: 1'b0 ; */ +/* Description: This is the stauts bit for tx_brk_idle_done_int_raw when + * tx_brk_idle_done_int_ena is set to 1. + */ + +#define UART_TX_BRK_IDLE_DONE_INT_ST (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_ST_M (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_ST_V 0x1 +#define UART_TX_BRK_IDLE_DONE_INT_ST_S 13 + +/* UART_TX_BRK_DONE_INT_ST : RO ;bitpos:[12] ;default: 1'b0 ; */ +/* Description: This is the status bit for tx_brk_done_int_raw when + * tx_brk_done_int_ena is set to 1. + */ + +#define UART_TX_BRK_DONE_INT_ST (BIT(12)) +#define UART_TX_BRK_DONE_INT_ST_M (BIT(12)) +#define UART_TX_BRK_DONE_INT_ST_V 0x1 +#define UART_TX_BRK_DONE_INT_ST_S 12 + +/* UART_GLITCH_DET_INT_ST : RO ;bitpos:[11] ;default: 1'b0 ; */ +/* Description: This is the status bit for glitch_det_int_raw when + * glitch_det_int_ena is set to 1. + */ + +#define UART_GLITCH_DET_INT_ST (BIT(11)) +#define UART_GLITCH_DET_INT_ST_M (BIT(11)) +#define UART_GLITCH_DET_INT_ST_V 0x1 +#define UART_GLITCH_DET_INT_ST_S 11 + +/* UART_SW_XOFF_INT_ST : RO ;bitpos:[10] ;default: 1'b0 ; */ +/* Description: This is the status bit for sw_xoff_int_raw when + * sw_xoff_int_ena is set to 1. + */ + +#define UART_SW_XOFF_INT_ST (BIT(10)) +#define UART_SW_XOFF_INT_ST_M (BIT(10)) +#define UART_SW_XOFF_INT_ST_V 0x1 +#define UART_SW_XOFF_INT_ST_S 10 + +/* UART_SW_XON_INT_ST : RO ;bitpos:[9] ;default: 1'b0 ; */ +/* Description: This is the status bit for sw_xon_int_raw when + * sw_xon_int_ena is set to 1. + */ + +#define UART_SW_XON_INT_ST (BIT(9)) +#define UART_SW_XON_INT_ST_M (BIT(9)) +#define UART_SW_XON_INT_ST_V 0x1 +#define UART_SW_XON_INT_ST_S 9 + +/* UART_RXFIFO_TOUT_INT_ST : RO ;bitpos:[8] ;default: 1'b0 ; */ +/* Description: This is the status bit for rxfifo_tout_int_raw when + * rxfifo_tout_int_ena is set to 1. + */ + +#define UART_RXFIFO_TOUT_INT_ST (BIT(8)) +#define UART_RXFIFO_TOUT_INT_ST_M (BIT(8)) +#define UART_RXFIFO_TOUT_INT_ST_V 0x1 +#define UART_RXFIFO_TOUT_INT_ST_S 8 + +/* UART_BRK_DET_INT_ST : RO ;bitpos:[7] ;default: 1'b0 ; */ +/* Description: This is the status bit for brk_det_int_raw when + * brk_det_int_ena is set to 1. + */ + +#define UART_BRK_DET_INT_ST (BIT(7)) +#define UART_BRK_DET_INT_ST_M (BIT(7)) +#define UART_BRK_DET_INT_ST_V 0x1 +#define UART_BRK_DET_INT_ST_S 7 + +/* UART_CTS_CHG_INT_ST : RO ;bitpos:[6] ;default: 1'b0 ; */ +/* Description: This is the status bit for cts_chg_int_raw when + * cts_chg_int_ena is set to 1. + */ + +#define UART_CTS_CHG_INT_ST (BIT(6)) +#define UART_CTS_CHG_INT_ST_M (BIT(6)) +#define UART_CTS_CHG_INT_ST_V 0x1 +#define UART_CTS_CHG_INT_ST_S 6 + +/* UART_DSR_CHG_INT_ST : RO ;bitpos:[5] ;default: 1'b0 ; */ +/* Description: This is the status bit for dsr_chg_int_raw when + * dsr_chg_int_ena is set to 1. + */ + +#define UART_DSR_CHG_INT_ST (BIT(5)) +#define UART_DSR_CHG_INT_ST_M (BIT(5)) +#define UART_DSR_CHG_INT_ST_V 0x1 +#define UART_DSR_CHG_INT_ST_S 5 + +/* UART_RXFIFO_OVF_INT_ST : RO ;bitpos:[4] ;default: 1'b0 ; */ +/* Description: This is the status bit for rxfifo_ovf_int_raw when + * rxfifo_ovf_int_ena is set to 1. + */ + +#define UART_RXFIFO_OVF_INT_ST (BIT(4)) +#define UART_RXFIFO_OVF_INT_ST_M (BIT(4)) +#define UART_RXFIFO_OVF_INT_ST_V 0x1 +#define UART_RXFIFO_OVF_INT_ST_S 4 + +/* UART_FRM_ERR_INT_ST : RO ;bitpos:[3] ;default: 1'b0 ; */ +/* Description: This is the status bit for frm_err_int_raw when + * fm_err_int_ena is set to 1. + */ + +#define UART_FRM_ERR_INT_ST (BIT(3)) +#define UART_FRM_ERR_INT_ST_M (BIT(3)) +#define UART_FRM_ERR_INT_ST_V 0x1 +#define UART_FRM_ERR_INT_ST_S 3 + +/* UART_PARITY_ERR_INT_ST : RO ;bitpos:[2] ;default: 1'b0 ; */ +/* Description: This is the status bit for parity_err_int_raw when + * parity_err_int_ena is set to 1. + */ + +#define UART_PARITY_ERR_INT_ST (BIT(2)) +#define UART_PARITY_ERR_INT_ST_M (BIT(2)) +#define UART_PARITY_ERR_INT_ST_V 0x1 +#define UART_PARITY_ERR_INT_ST_S 2 + +/* UART_TXFIFO_EMPTY_INT_ST : RO ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: This is the status bit for txfifo_empty_int_raw when + * txfifo_empty_int_ena is set to 1. + */ + +#define UART_TXFIFO_EMPTY_INT_ST (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_ST_M (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_ST_V 0x1 +#define UART_TXFIFO_EMPTY_INT_ST_S 1 + +/* UART_RXFIFO_FULL_INT_ST : RO ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: This is the status bit for rxfifo_full_int_raw when + * rxfifo_full_int_ena is set to 1.*/ + +#define UART_RXFIFO_FULL_INT_ST (BIT(0)) +#define UART_RXFIFO_FULL_INT_ST_M (BIT(0)) +#define UART_RXFIFO_FULL_INT_ST_V 0x1 +#define UART_RXFIFO_FULL_INT_ST_S 0 + +#define UART_INT_ENA_REG(i) (REG_UART_BASE(i) + 0xC) + +/* UART_AT_CMD_CHAR_DET_INT_ENA : R/W ;bitpos:[18] ;default: 1'b0 ; */ +/* Description: This is the enable bit for at_cmd_char_det_int_st register.*/ + +#define UART_AT_CMD_CHAR_DET_INT_ENA (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_ENA_M (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_ENA_V 0x1 +#define UART_AT_CMD_CHAR_DET_INT_ENA_S 18 + +/* UART_RS485_CLASH_INT_ENA : R/W ;bitpos:[17] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rs485_clash_int_st register.*/ + +#define UART_RS485_CLASH_INT_ENA (BIT(17)) +#define UART_RS485_CLASH_INT_ENA_M (BIT(17)) +#define UART_RS485_CLASH_INT_ENA_V 0x1 +#define UART_RS485_CLASH_INT_ENA_S 17 + +/* UART_RS485_FRM_ERR_INT_ENA : R/W ;bitpos:[16] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rs485_parity_err_int_st register.*/ + +#define UART_RS485_FRM_ERR_INT_ENA (BIT(16)) +#define UART_RS485_FRM_ERR_INT_ENA_M (BIT(16)) +#define UART_RS485_FRM_ERR_INT_ENA_V 0x1 +#define UART_RS485_FRM_ERR_INT_ENA_S 16 + +/* UART_RS485_PARITY_ERR_INT_ENA : R/W ;bitpos:[15] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rs485_parity_err_int_st register.*/ + +#define UART_RS485_PARITY_ERR_INT_ENA (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_ENA_M (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_ENA_V 0x1 +#define UART_RS485_PARITY_ERR_INT_ENA_S 15 + +/* UART_TX_DONE_INT_ENA : R/W ;bitpos:[14] ;default: 1'b0 ; */ +/* Description: This is the enable bit for tx_done_int_st register.*/ + +#define UART_TX_DONE_INT_ENA (BIT(14)) +#define UART_TX_DONE_INT_ENA_M (BIT(14)) +#define UART_TX_DONE_INT_ENA_V 0x1 +#define UART_TX_DONE_INT_ENA_S 14 + +/* UART_TX_BRK_IDLE_DONE_INT_ENA : R/W ;bitpos:[13] ;default: 1'b0 ; */ +/* Description: This is the enable bit for tx_brk_idle_done_int_st register.*/ + +#define UART_TX_BRK_IDLE_DONE_INT_ENA (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_ENA_M (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_ENA_V 0x1 +#define UART_TX_BRK_IDLE_DONE_INT_ENA_S 13 + +/* UART_TX_BRK_DONE_INT_ENA : R/W ;bitpos:[12] ;default: 1'b0 ; */ +/* Description: This is the enable bit for tx_brk_done_int_st register.*/ + +#define UART_TX_BRK_DONE_INT_ENA (BIT(12)) +#define UART_TX_BRK_DONE_INT_ENA_M (BIT(12)) +#define UART_TX_BRK_DONE_INT_ENA_V 0x1 +#define UART_TX_BRK_DONE_INT_ENA_S 12 + +/* UART_GLITCH_DET_INT_ENA : R/W ;bitpos:[11] ;default: 1'b0 ; */ +/* Description: This is the enable bit for glitch_det_int_st register.*/ + +#define UART_GLITCH_DET_INT_ENA (BIT(11)) +#define UART_GLITCH_DET_INT_ENA_M (BIT(11)) +#define UART_GLITCH_DET_INT_ENA_V 0x1 +#define UART_GLITCH_DET_INT_ENA_S 11 + +/* UART_SW_XOFF_INT_ENA : R/W ;bitpos:[10] ;default: 1'b0 ; */ +/* Description: This is the enable bit for sw_xoff_int_st register.*/ + +#define UART_SW_XOFF_INT_ENA (BIT(10)) +#define UART_SW_XOFF_INT_ENA_M (BIT(10)) +#define UART_SW_XOFF_INT_ENA_V 0x1 +#define UART_SW_XOFF_INT_ENA_S 10 + +/* UART_SW_XON_INT_ENA : R/W ;bitpos:[9] ;default: 1'b0 ; */ +/* Description: This is the enable bit for sw_xon_int_st register.*/ + +#define UART_SW_XON_INT_ENA (BIT(9)) +#define UART_SW_XON_INT_ENA_M (BIT(9)) +#define UART_SW_XON_INT_ENA_V 0x1 +#define UART_SW_XON_INT_ENA_S 9 + +/* UART_RXFIFO_TOUT_INT_ENA : R/W ;bitpos:[8] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rxfifo_tout_int_st register.*/ + +#define UART_RXFIFO_TOUT_INT_ENA (BIT(8)) +#define UART_RXFIFO_TOUT_INT_ENA_M (BIT(8)) +#define UART_RXFIFO_TOUT_INT_ENA_V 0x1 +#define UART_RXFIFO_TOUT_INT_ENA_S 8 + +/* UART_BRK_DET_INT_ENA : R/W ;bitpos:[7] ;default: 1'b0 ; */ +/* Description: This is the enable bit for brk_det_int_st register.*/ + +#define UART_BRK_DET_INT_ENA (BIT(7)) +#define UART_BRK_DET_INT_ENA_M (BIT(7)) +#define UART_BRK_DET_INT_ENA_V 0x1 +#define UART_BRK_DET_INT_ENA_S 7 + +/* UART_CTS_CHG_INT_ENA : R/W ;bitpos:[6] ;default: 1'b0 ; */ +/* Description: This is the enable bit for cts_chg_int_st register.*/ + +#define UART_CTS_CHG_INT_ENA (BIT(6)) +#define UART_CTS_CHG_INT_ENA_M (BIT(6)) +#define UART_CTS_CHG_INT_ENA_V 0x1 +#define UART_CTS_CHG_INT_ENA_S 6 + +/* UART_DSR_CHG_INT_ENA : R/W ;bitpos:[5] ;default: 1'b0 ; */ +/* Description: This is the enable bit for dsr_chg_int_st register.*/ + +#define UART_DSR_CHG_INT_ENA (BIT(5)) +#define UART_DSR_CHG_INT_ENA_M (BIT(5)) +#define UART_DSR_CHG_INT_ENA_V 0x1 +#define UART_DSR_CHG_INT_ENA_S 5 + +/* UART_RXFIFO_OVF_INT_ENA : R/W ;bitpos:[4] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rxfifo_ovf_int_st register.*/ + +#define UART_RXFIFO_OVF_INT_ENA (BIT(4)) +#define UART_RXFIFO_OVF_INT_ENA_M (BIT(4)) +#define UART_RXFIFO_OVF_INT_ENA_V 0x1 +#define UART_RXFIFO_OVF_INT_ENA_S 4 + +/* UART_FRM_ERR_INT_ENA : R/W ;bitpos:[3] ;default: 1'b0 ; */ +/* Description: This is the enable bit for frm_err_int_st register.*/ + +#define UART_FRM_ERR_INT_ENA (BIT(3)) +#define UART_FRM_ERR_INT_ENA_M (BIT(3)) +#define UART_FRM_ERR_INT_ENA_V 0x1 +#define UART_FRM_ERR_INT_ENA_S 3 + +/* UART_PARITY_ERR_INT_ENA : R/W ;bitpos:[2] ;default: 1'b0 ; */ +/* Description: This is the enable bit for parity_err_int_st register.*/ + +#define UART_PARITY_ERR_INT_ENA (BIT(2)) +#define UART_PARITY_ERR_INT_ENA_M (BIT(2)) +#define UART_PARITY_ERR_INT_ENA_V 0x1 +#define UART_PARITY_ERR_INT_ENA_S 2 + +/* UART_TXFIFO_EMPTY_INT_ENA : R/W ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rxfifo_full_int_st register.*/ + +#define UART_TXFIFO_EMPTY_INT_ENA (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_ENA_M (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_ENA_V 0x1 +#define UART_TXFIFO_EMPTY_INT_ENA_S 1 + +/* UART_RXFIFO_FULL_INT_ENA : R/W ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: This is the enable bit for rxfifo_full_int_st register.*/ + +#define UART_RXFIFO_FULL_INT_ENA (BIT(0)) +#define UART_RXFIFO_FULL_INT_ENA_M (BIT(0)) +#define UART_RXFIFO_FULL_INT_ENA_V 0x1 +#define UART_RXFIFO_FULL_INT_ENA_S 0 + +#define UART_INT_CLR_REG(i) (REG_UART_BASE(i) + 0x10) + +/* UART_AT_CMD_CHAR_DET_INT_CLR : WO ;bitpos:[18] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the at_cmd_char_det_int_raw interrupt.*/ + +#define UART_AT_CMD_CHAR_DET_INT_CLR (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_CLR_M (BIT(18)) +#define UART_AT_CMD_CHAR_DET_INT_CLR_V 0x1 +#define UART_AT_CMD_CHAR_DET_INT_CLR_S 18 + +/* UART_RS485_CLASH_INT_CLR : WO ;bitpos:[17] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the rs485_clash_int_raw interrupt.*/ + +#define UART_RS485_CLASH_INT_CLR (BIT(17)) +#define UART_RS485_CLASH_INT_CLR_M (BIT(17)) +#define UART_RS485_CLASH_INT_CLR_V 0x1 +#define UART_RS485_CLASH_INT_CLR_S 17 + +/* UART_RS485_FRM_ERR_INT_CLR : WO ;bitpos:[16] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the rs485_frm_err_int_raw interrupt.*/ + +#define UART_RS485_FRM_ERR_INT_CLR (BIT(16)) +#define UART_RS485_FRM_ERR_INT_CLR_M (BIT(16)) +#define UART_RS485_FRM_ERR_INT_CLR_V 0x1 +#define UART_RS485_FRM_ERR_INT_CLR_S 16 + +/* UART_RS485_PARITY_ERR_INT_CLR : WO ;bitpos:[15] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the rs485_parity_err_int_raw + * interrupt. + */ + +#define UART_RS485_PARITY_ERR_INT_CLR (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_CLR_M (BIT(15)) +#define UART_RS485_PARITY_ERR_INT_CLR_V 0x1 +#define UART_RS485_PARITY_ERR_INT_CLR_S 15 + +/* UART_TX_DONE_INT_CLR : WO ;bitpos:[14] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the tx_done_int_raw interrupt.*/ + +#define UART_TX_DONE_INT_CLR (BIT(14)) +#define UART_TX_DONE_INT_CLR_M (BIT(14)) +#define UART_TX_DONE_INT_CLR_V 0x1 +#define UART_TX_DONE_INT_CLR_S 14 + +/* UART_TX_BRK_IDLE_DONE_INT_CLR : WO ;bitpos:[13] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the tx_brk_idle_done_int_raw + * interrupt. + */ + +#define UART_TX_BRK_IDLE_DONE_INT_CLR (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_CLR_M (BIT(13)) +#define UART_TX_BRK_IDLE_DONE_INT_CLR_V 0x1 +#define UART_TX_BRK_IDLE_DONE_INT_CLR_S 13 + +/* UART_TX_BRK_DONE_INT_CLR : WO ;bitpos:[12] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the tx_brk_done_int_raw interrupt. */ + +#define UART_TX_BRK_DONE_INT_CLR (BIT(12)) +#define UART_TX_BRK_DONE_INT_CLR_M (BIT(12)) +#define UART_TX_BRK_DONE_INT_CLR_V 0x1 +#define UART_TX_BRK_DONE_INT_CLR_S 12 + +/* UART_GLITCH_DET_INT_CLR : WO ;bitpos:[11] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the glitch_det_int_raw interrupt.*/ + +#define UART_GLITCH_DET_INT_CLR (BIT(11)) +#define UART_GLITCH_DET_INT_CLR_M (BIT(11)) +#define UART_GLITCH_DET_INT_CLR_V 0x1 +#define UART_GLITCH_DET_INT_CLR_S 11 + +/* UART_SW_XOFF_INT_CLR : WO ;bitpos:[10] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the sw_xon_int_raw interrupt.*/ + +#define UART_SW_XOFF_INT_CLR (BIT(10)) +#define UART_SW_XOFF_INT_CLR_M (BIT(10)) +#define UART_SW_XOFF_INT_CLR_V 0x1 +#define UART_SW_XOFF_INT_CLR_S 10 + +/* UART_SW_XON_INT_CLR : WO ;bitpos:[9] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the sw_xon_int_raw interrupt.*/ + +#define UART_SW_XON_INT_CLR (BIT(9)) +#define UART_SW_XON_INT_CLR_M (BIT(9)) +#define UART_SW_XON_INT_CLR_V 0x1 +#define UART_SW_XON_INT_CLR_S 9 + +/* UART_RXFIFO_TOUT_INT_CLR : WO ;bitpos:[8] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the rxfifo_tout_int_raw interrupt.*/ + +#define UART_RXFIFO_TOUT_INT_CLR (BIT(8)) +#define UART_RXFIFO_TOUT_INT_CLR_M (BIT(8)) +#define UART_RXFIFO_TOUT_INT_CLR_V 0x1 +#define UART_RXFIFO_TOUT_INT_CLR_S 8 + +/* UART_BRK_DET_INT_CLR : WO ;bitpos:[7] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the brk_det_int_raw interrupt.*/ + +#define UART_BRK_DET_INT_CLR (BIT(7)) +#define UART_BRK_DET_INT_CLR_M (BIT(7)) +#define UART_BRK_DET_INT_CLR_V 0x1 +#define UART_BRK_DET_INT_CLR_S 7 + +/* UART_CTS_CHG_INT_CLR : WO ;bitpos:[6] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the cts_chg_int_raw interrupt.*/ + +#define UART_CTS_CHG_INT_CLR (BIT(6)) +#define UART_CTS_CHG_INT_CLR_M (BIT(6)) +#define UART_CTS_CHG_INT_CLR_V 0x1 +#define UART_CTS_CHG_INT_CLR_S 6 + +/* UART_DSR_CHG_INT_CLR : WO ;bitpos:[5] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the dsr_chg_int_raw interrupt.*/ + +#define UART_DSR_CHG_INT_CLR (BIT(5)) +#define UART_DSR_CHG_INT_CLR_M (BIT(5)) +#define UART_DSR_CHG_INT_CLR_V 0x1 +#define UART_DSR_CHG_INT_CLR_S 5 + +/* UART_RXFIFO_OVF_INT_CLR : WO ;bitpos:[4] ;default: 1'b0 ; */ +/* Description: Set this bit to clear rxfifo_ovf_int_raw interrupt.*/ + +#define UART_RXFIFO_OVF_INT_CLR (BIT(4)) +#define UART_RXFIFO_OVF_INT_CLR_M (BIT(4)) +#define UART_RXFIFO_OVF_INT_CLR_V 0x1 +#define UART_RXFIFO_OVF_INT_CLR_S 4 + +/* UART_FRM_ERR_INT_CLR : WO ;bitpos:[3] ;default: 1'b0 ; */ +/* Description: Set this bit to clear frm_err_int_raw interrupt.*/ + +#define UART_FRM_ERR_INT_CLR (BIT(3)) +#define UART_FRM_ERR_INT_CLR_M (BIT(3)) +#define UART_FRM_ERR_INT_CLR_V 0x1 +#define UART_FRM_ERR_INT_CLR_S 3 + +/* UART_PARITY_ERR_INT_CLR : WO ;bitpos:[2] ;default: 1'b0 ; */ +/* Description: Set this bit to clear parity_err_int_raw interrupt.*/ + +#define UART_PARITY_ERR_INT_CLR (BIT(2)) +#define UART_PARITY_ERR_INT_CLR_M (BIT(2)) +#define UART_PARITY_ERR_INT_CLR_V 0x1 +#define UART_PARITY_ERR_INT_CLR_S 2 + +/* UART_TXFIFO_EMPTY_INT_CLR : WO ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: Set this bit to clear txfifo_empty_int_raw interrupt.*/ + +#define UART_TXFIFO_EMPTY_INT_CLR (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_CLR_M (BIT(1)) +#define UART_TXFIFO_EMPTY_INT_CLR_V 0x1 +#define UART_TXFIFO_EMPTY_INT_CLR_S 1 + +/* UART_RXFIFO_FULL_INT_CLR : WO ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: Set this bit to clear the rxfifo_full_int_raw interrupt.*/ + +#define UART_RXFIFO_FULL_INT_CLR (BIT(0)) +#define UART_RXFIFO_FULL_INT_CLR_M (BIT(0)) +#define UART_RXFIFO_FULL_INT_CLR_V 0x1 +#define UART_RXFIFO_FULL_INT_CLR_S 0 + +#define UART_CLKDIV_REG(i) (REG_UART_BASE(i) + 0x14) + +/* UART_CLKDIV_FRAG : R/W ;bitpos:[23:20] ;default: 4'h0 ; */ +/* Description: The register value is the decimal part of the frequency + * divider's factor. + */ + +#define UART_CLKDIV_FRAG 0x0000000F +#define UART_CLKDIV_FRAG_M ((UART_CLKDIV_FRAG_V)<<(UART_CLKDIV_FRAG_S)) +#define UART_CLKDIV_FRAG_V 0xF +#define UART_CLKDIV_FRAG_S 20 + +/* UART_CLKDIV : R/W ;bitpos:[19:0] ;default: 20'h2B6 ; */ +/* Description: The register value is the integer part of the frequency + * divider's factor. + */ + +#define UART_CLKDIV 0x000FFFFF +#define UART_CLKDIV_M ((UART_CLKDIV_V)<<(UART_CLKDIV_S)) +#define UART_CLKDIV_V 0xFFFFF +#define UART_CLKDIV_S 0 + +#define UART_AUTOBAUD_REG(i) (REG_UART_BASE(i) + 0x18) + +/* UART_GLITCH_FILT : R/W ;bitpos:[15:8] ;default: 8'h10 ; */ +/* Description: when input pulse width is lower then this value igore this + * pulse. This register is used in autobaud detect process. + */ + +#define UART_GLITCH_FILT 0x000000FF +#define UART_GLITCH_FILT_M ((UART_GLITCH_FILT_V)<<(UART_GLITCH_FILT_S)) +#define UART_GLITCH_FILT_V 0xFF +#define UART_GLITCH_FILT_S 8 + +/* UART_AUTOBAUD_EN : R/W ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: This is the enable bit for detecting baudrate.*/ + +#define UART_AUTOBAUD_EN (BIT(0)) +#define UART_AUTOBAUD_EN_M (BIT(0)) +#define UART_AUTOBAUD_EN_V 0x1 +#define UART_AUTOBAUD_EN_S 0 + +#define UART_STATUS_REG(i) (REG_UART_BASE(i) + 0x1C) + +/* UART_TXD : RO ;bitpos:[31] ;default: 8'h0 ; */ +/* Description: This register represent the level value of the internal + * uart rxd signal. + */ + +#define UART_TXD (BIT(31)) +#define UART_TXD_M (BIT(31)) +#define UART_TXD_V 0x1 +#define UART_TXD_S 31 + +/* UART_RTSN : RO ;bitpos:[30] ;default: 1'b0 ; */ +/* Description: This register represent the level value of the internal uart + * cts signal. + */ + +#define UART_RTSN (BIT(30)) +#define UART_RTSN_M (BIT(30)) +#define UART_RTSN_V 0x1 +#define UART_RTSN_S 30 + +/* UART_DTRN : RO ;bitpos:[29] ;default: 1'b0 ; */ +/* Description: The register represent the level value of the internal uart + * dsr signal. + */ + +#define UART_DTRN (BIT(29)) +#define UART_DTRN_M (BIT(29)) +#define UART_DTRN_V 0x1 +#define UART_DTRN_S 29 + +/* UART_ST_UTX_OUT : RO ;bitpos:[27:24] ;default: 4'b0 ; */ +/* Description: This register stores the value of transmitter's finite state + * machine. 0:TX_IDLE 1:TX_STRT 2:TX_DAT0 3:TX_DAT1 4:TX_DAT2 + * 5:TX_DAT3 6:TX_DAT4 7:TX_DAT5 8:TX_DAT6 9:TX_DAT7 10:TX_PRTY + * 11:TX_STP1 12:TX_STP2 13:TX_DL0 14:TX_DL1 + */ + +#define UART_ST_UTX_OUT 0x0000000F +#define UART_ST_UTX_OUT_M ((UART_ST_UTX_OUT_V)<<(UART_ST_UTX_OUT_S)) +#define UART_ST_UTX_OUT_V 0xF +#define UART_ST_UTX_OUT_S 24 + +/* UART_TXFIFO_CNT : RO ;bitpos:[23:16] ;default: 8'b0 ; */ +/* Description: (tx_mem_cnt txfifo_cnt) stores the byte num of valid datas + * in transmitter's fifo. tx_mem_cnt stores the 3 most significant bits + * txfifo_cnt stores the 8 least significant bits. + */ + +#define UART_TXFIFO_CNT 0x000000FF +#define UART_TXFIFO_CNT_M ((UART_TXFIFO_CNT_V)<<(UART_TXFIFO_CNT_S)) +#define UART_TXFIFO_CNT_V 0xFF +#define UART_TXFIFO_CNT_S 16 + +/* UART_RXD : RO ;bitpos:[15] ;default: 1'b0 ; */ +/* Description: This register stores the level value of the internal uart + * rxd signal. + */ + +#define UART_RXD (BIT(15)) +#define UART_RXD_M (BIT(15)) +#define UART_RXD_V 0x1 +#define UART_RXD_S 15 + +/* UART_CTSN : RO ;bitpos:[14] ;default: 1'b0 ; */ +/* Description: This register stores the level value of the internal uart + * cts signal. + */ + +#define UART_CTSN (BIT(14)) +#define UART_CTSN_M (BIT(14)) +#define UART_CTSN_V 0x1 +#define UART_CTSN_S 14 + +/* UART_DSRN : RO ;bitpos:[13] ;default: 1'b0 ; */ +/* Description: This register stores the level value of the internal uart + * dsr signal. + */ + +#define UART_DSRN (BIT(13)) +#define UART_DSRN_M (BIT(13)) +#define UART_DSRN_V 0x1 +#define UART_DSRN_S 13 + +/* UART_ST_URX_OUT : RO ;bitpos:[11:8] ;default: 4'b0 ; */ +/* Description: This register stores the value of receiver's finite state + * machine. + * 0:RX_IDLE 1:RX_STRT 2:RX_DAT0 3:RX_DAT1 4:RX_DAT2 5:RX_DAT3 + * 6:RX_DAT4 7:RX_DAT5 8:RX_DAT6 9:RX_DAT7 10:RX_PRTY 11:RX_STP1 + * 12:RX_STP2 13:RX_DL1 + */ + +#define UART_ST_URX_OUT 0x0000000F +#define UART_ST_URX_OUT_M ((UART_ST_URX_OUT_V)<<(UART_ST_URX_OUT_S)) +#define UART_ST_URX_OUT_V 0xF +#define UART_ST_URX_OUT_S 8 + +/* UART_RXFIFO_CNT : RO ;bitpos:[7:0] ;default: 8'b0 ; */ +/* Description: (rx_mem_cnt rxfifo_cnt) stores the byte num of valid datas + * in receiver's fifo. rx_mem_cnt register stores the 3 most significant + * bits rxfifo_cnt stores the 8 least significant bits. + */ + +#define UART_RXFIFO_CNT 0x000000FF +#define UART_RXFIFO_CNT_M ((UART_RXFIFO_CNT_V)<<(UART_RXFIFO_CNT_S)) +#define UART_RXFIFO_CNT_V 0xFF +#define UART_RXFIFO_CNT_S 0 + +#define UART_CONF0_REG(i) (REG_UART_BASE(i) + 0x20) + +/* UART_TICK_REF_ALWAYS_ON : R/W ;bitpos:[27] ;default: 1'b1 ; */ +/* Description: This register is used to select the clock.1.apb clock + * 0:ref_tick + */ + +#define UART_TICK_REF_ALWAYS_ON (BIT(27)) +#define UART_TICK_REF_ALWAYS_ON_M (BIT(27)) +#define UART_TICK_REF_ALWAYS_ON_V 0x1 +#define UART_TICK_REF_ALWAYS_ON_S 27 + +/* UART_ERR_WR_MASK : R/W ;bitpos:[26] ;default: 1'b0 ; */ +/* Description: 1.receiver stops storing data int fifo when data is wrong. + * 0.receiver stores the data even if the received data is wrong.*/ + +#define UART_ERR_WR_MASK (BIT(26)) +#define UART_ERR_WR_MASK_M (BIT(26)) +#define UART_ERR_WR_MASK_V 0x1 +#define UART_ERR_WR_MASK_S 26 + +/* UART_CLK_EN : R/W ;bitpos:[25] ;default: 1'h0 ; */ +/* Description: 1.force clock on for registers.support clock only when write + * registers + */ + +#define UART_CLK_EN (BIT(25)) +#define UART_CLK_EN_M (BIT(25)) +#define UART_CLK_EN_V 0x1 +#define UART_CLK_EN_S 25 + +/* UART_DTR_INV : R/W ;bitpos:[24] ;default: 1'h0 ; */ +/* Description: Set this bit to inverse the level value of uart dtr signal.*/ + +#define UART_DTR_INV (BIT(24)) +#define UART_DTR_INV_M (BIT(24)) +#define UART_DTR_INV_V 0x1 +#define UART_DTR_INV_S 24 + +/* UART_RTS_INV : R/W ;bitpos:[23] ;default: 1'h0 ; */ +/* Description: Set this bit to inverse the level value of uart rts signal.*/ + +#define UART_RTS_INV (BIT(23)) +#define UART_RTS_INV_M (BIT(23)) +#define UART_RTS_INV_V 0x1 +#define UART_RTS_INV_S 23 + +/* UART_TXD_INV : R/W ;bitpos:[22] ;default: 1'h0 ; */ +/* Description: Set this bit to inverse the level value of uart txd signal.*/ + +#define UART_TXD_INV (BIT(22)) +#define UART_TXD_INV_M (BIT(22)) +#define UART_TXD_INV_V 0x1 +#define UART_TXD_INV_S 22 + +/* UART_DSR_INV : R/W ;bitpos:[21] ;default: 1'h0 ; */ +/* Description: Set this bit to inverse the level value of uart dsr signal.*/ + +#define UART_DSR_INV (BIT(21)) +#define UART_DSR_INV_M (BIT(21)) +#define UART_DSR_INV_V 0x1 +#define UART_DSR_INV_S 21 + +/* UART_CTS_INV : R/W ;bitpos:[20] ;default: 1'h0 ; */ +/* Description: Set this bit to inverse the level value of uart cts signal.*/ + +#define UART_CTS_INV (BIT(20)) +#define UART_CTS_INV_M (BIT(20)) +#define UART_CTS_INV_V 0x1 +#define UART_CTS_INV_S 20 + +/* UART_RXD_INV : R/W ;bitpos:[19] ;default: 1'h0 ; */ +/* Description: Set this bit to inverse the level value of uart rxd signal.*/ + +#define UART_RXD_INV (BIT(19)) +#define UART_RXD_INV_M (BIT(19)) +#define UART_RXD_INV_V 0x1 +#define UART_RXD_INV_S 19 + +/* UART_TXFIFO_RST : R/W ;bitpos:[18] ;default: 1'h0 ; */ +/* Description: Set this bit to reset uart transmitter's fifo.*/ + +#define UART_TXFIFO_RST (BIT(18)) +#define UART_TXFIFO_RST_M (BIT(18)) +#define UART_TXFIFO_RST_V 0x1 +#define UART_TXFIFO_RST_S 18 + +/* UART_RXFIFO_RST : R/W ;bitpos:[17] ;default: 1'h0 ; */ +/* Description: Set this bit to reset uart receiver's fifo.*/ + +#define UART_RXFIFO_RST (BIT(17)) +#define UART_RXFIFO_RST_M (BIT(17)) +#define UART_RXFIFO_RST_V 0x1 +#define UART_RXFIFO_RST_S 17 + +/* UART_IRDA_EN : R/W ;bitpos:[16] ;default: 1'h0 ; */ +/* Description: Set this bit to enable irda protocol.*/ + +#define UART_IRDA_EN (BIT(16)) +#define UART_IRDA_EN_M (BIT(16)) +#define UART_IRDA_EN_V 0x1 +#define UART_IRDA_EN_S 16 + +/* UART_TX_FLOW_EN : R/W ;bitpos:[15] ;default: 1'b0 ; */ +/* Description: Set this bit to enable transmitter's flow control function.*/ + +#define UART_TX_FLOW_EN (BIT(15)) +#define UART_TX_FLOW_EN_M (BIT(15)) +#define UART_TX_FLOW_EN_V 0x1 +#define UART_TX_FLOW_EN_S 15 + +/* UART_LOOPBACK : R/W ;bitpos:[14] ;default: 1'b0 ; */ +/* Description: Set this bit to enable uart loopback test mode.*/ + +#define UART_LOOPBACK (BIT(14)) +#define UART_LOOPBACK_M (BIT(14)) +#define UART_LOOPBACK_V 0x1 +#define UART_LOOPBACK_S 14 + +/* UART_IRDA_RX_INV : R/W ;bitpos:[13] ;default: 1'b0 ; */ +/* Description: Set this bit to inverse the level value of irda receiver's + * level. + */ + +#define UART_IRDA_RX_INV (BIT(13)) +#define UART_IRDA_RX_INV_M (BIT(13)) +#define UART_IRDA_RX_INV_V 0x1 +#define UART_IRDA_RX_INV_S 13 + +/* UART_IRDA_TX_INV : R/W ;bitpos:[12] ;default: 1'b0 ; */ +/* Description: Set this bit to inverse the level value of irda + * transmitter's level. + */ + +#define UART_IRDA_TX_INV (BIT(12)) +#define UART_IRDA_TX_INV_M (BIT(12)) +#define UART_IRDA_TX_INV_V 0x1 +#define UART_IRDA_TX_INV_S 12 + +/* UART_IRDA_WCTL : R/W ;bitpos:[11] ;default: 1'b0 ; */ +/* Description: 1.the irda transmitter's 11th bit is the same to the 10th + * bit. 0.set irda transmitter's 11th bit to 0.*/ + +#define UART_IRDA_WCTL (BIT(11)) +#define UART_IRDA_WCTL_M (BIT(11)) +#define UART_IRDA_WCTL_V 0x1 +#define UART_IRDA_WCTL_S 11 + +/* UART_IRDA_TX_EN : R/W ;bitpos:[10] ;default: 1'b0 ; */ +/* Description: This is the start enable bit for irda transmitter.*/ + +#define UART_IRDA_TX_EN (BIT(10)) +#define UART_IRDA_TX_EN_M (BIT(10)) +#define UART_IRDA_TX_EN_V 0x1 +#define UART_IRDA_TX_EN_S 10 + +/* UART_IRDA_DPLX : R/W ;bitpos:[9] ;default: 1'b0 ; */ +/* Description: Set this bit to enable irda loopback mode.*/ + +#define UART_IRDA_DPLX (BIT(9)) +#define UART_IRDA_DPLX_M (BIT(9)) +#define UART_IRDA_DPLX_V 0x1 +#define UART_IRDA_DPLX_S 9 + +/* UART_TXD_BRK : R/W ;bitpos:[8] ;default: 1'b0 ; */ +/* Description: Set this bit to enbale transmitter to send 0 when the + * process of sending data is done. + */ + +#define UART_TXD_BRK (BIT(8)) +#define UART_TXD_BRK_M (BIT(8)) +#define UART_TXD_BRK_V 0x1 +#define UART_TXD_BRK_S 8 + +/* UART_SW_DTR : R/W ;bitpos:[7] ;default: 1'b0 ; */ +/* Description: This register is used to configure the software dtr signal + * which is used in software flow control. + */ + +#define UART_SW_DTR (BIT(7)) +#define UART_SW_DTR_M (BIT(7)) +#define UART_SW_DTR_V 0x1 +#define UART_SW_DTR_S 7 + +/* UART_SW_RTS : R/W ;bitpos:[6] ;default: 1'b0 ; */ +/* Description: This register is used to configure the software rts signal + * which is used in software flow control. + */ + +#define UART_SW_RTS (BIT(6)) +#define UART_SW_RTS_M (BIT(6)) +#define UART_SW_RTS_V 0x1 +#define UART_SW_RTS_S 6 + +/* UART_STOP_BIT_NUM : R/W ;bitpos:[5:4] ;default: 2'd1 ; */ +/* Description: This register is used to set the length of stop bit. + * 1:1bit 2:1.5bits 3:2bits + */ + +#define UART_STOP_BIT_NUM 0x00000003 +#define UART_STOP_BIT_NUM_M ((UART_STOP_BIT_NUM_V)<<(UART_STOP_BIT_NUM_S)) +#define UART_STOP_BIT_NUM_V 0x3 +#define UART_STOP_BIT_NUM_S 4 + +/* UART_BIT_NUM : R/W ;bitpos:[3:2] ;default: 2'd3 ; */ +/* Description: This registe is used to set the length of data: + * 0:5bits 1:6bits 2:7bits 3:8bits + */ + +#define UART_BIT_NUM 0x00000003 +#define UART_BIT_NUM_M ((UART_BIT_NUM_V)<<(UART_BIT_NUM_S)) +#define UART_BIT_NUM_V 0x3 +#define UART_BIT_NUM_S 2 + +/* UART_PARITY_EN : R/W ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: Set this bit to enable uart parity check.*/ + +#define UART_PARITY_EN (BIT(1)) +#define UART_PARITY_EN_M (BIT(1)) +#define UART_PARITY_EN_V 0x1 +#define UART_PARITY_EN_S 1 + +/* UART_PARITY : R/W ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: This register is used to configure the parity check mode. + * 0:even 1:odd + */ + +#define UART_PARITY (BIT(0)) +#define UART_PARITY_M (BIT(0)) +#define UART_PARITY_V 0x1 +#define UART_PARITY_S 0 + +#define UART_CONF1_REG(i) (REG_UART_BASE(i) + 0x24) + +/* UART_RX_TOUT_EN : R/W ;bitpos:[31] ;default: 1'b0 ; */ +/* Description: This is the enble bit for uart receiver's timeout function.*/ + +#define UART_RX_TOUT_EN (BIT(31)) +#define UART_RX_TOUT_EN_M (BIT(31)) +#define UART_RX_TOUT_EN_V 0x1 +#define UART_RX_TOUT_EN_S 31 + +/* UART_RX_TOUT_THRHD : R/W ;bitpos:[30:24] ;default: 7'b0 ; */ +/* Description: This register is used to configure the timeout value for + * uart receiver receiving a byte. + */ + +#define UART_RX_TOUT_THRHD 0x0000007F +#define UART_RX_TOUT_THRHD_M ((UART_RX_TOUT_THRHD_V)<<(UART_RX_TOUT_THRHD_S)) +#define UART_RX_TOUT_THRHD_V 0x7F +#define UART_RX_TOUT_THRHD_S 24 + +/* UART_RX_FLOW_EN : R/W ;bitpos:[23] ;default: 1'b0 ; */ +/* Description: This is the flow enable bit for uart receiver. 1:choose + * software flow control with configuring sw_rts signal + */ + +#define UART_RX_FLOW_EN (BIT(23)) +#define UART_RX_FLOW_EN_M (BIT(23)) +#define UART_RX_FLOW_EN_V 0x1 +#define UART_RX_FLOW_EN_S 23 + +/* UART_RX_FLOW_THRHD : R/W ;bitpos:[22:16] ;default: 7'h0 ; */ +/* Description: when receiver receives more data than its threshold value. + * receiver produce signal to tell the transmitter stop transferring data. + * the threshold value is (rx_flow_thrhd_h3 rx_flow_thrhd). + */ + +#define UART_RX_FLOW_THRHD 0x0000007F +#define UART_RX_FLOW_THRHD_M ((UART_RX_FLOW_THRHD_V)<<(UART_RX_FLOW_THRHD_S)) +#define UART_RX_FLOW_THRHD_V 0x7F +#define UART_RX_FLOW_THRHD_S 16 + +/* UART_TXFIFO_EMPTY_THRHD : R/W ;bitpos:[14:8] ;default: 7'h60 ; */ +/* Description: when the data amount in transmitter fifo is less than its + * threshold value. it will produce txfifo_empty_int_raw interrupt. the + * threshold value is (tx_mem_empty_thrhd txfifo_empty_thrhd) + */ + +#define UART_TXFIFO_EMPTY_THRHD 0x0000007F +#define UART_TXFIFO_EMPTY_THRHD_M ((UART_TXFIFO_EMPTY_THRHD_V)<<(UART_TXFIFO_EMPTY_THRHD_S)) +#define UART_TXFIFO_EMPTY_THRHD_V 0x7F +#define UART_TXFIFO_EMPTY_THRHD_S 8 + +/* UART_RXFIFO_FULL_THRHD : R/W ;bitpos:[6:0] ;default: 7'h60 ; */ +/* Description: When receiver receives more data than its threshold + * value.receiver will produce rxfifo_full_int_raw interrupt.the threshold + * value is (rx_flow_thrhd_h3 rxfifo_full_thrhd). + */ + +#define UART_RXFIFO_FULL_THRHD 0x0000007F +#define UART_RXFIFO_FULL_THRHD_M ((UART_RXFIFO_FULL_THRHD_V)<<(UART_RXFIFO_FULL_THRHD_S)) +#define UART_RXFIFO_FULL_THRHD_V 0x7F +#define UART_RXFIFO_FULL_THRHD_S 0 + +#define UART_LOWPULSE_REG(i) (REG_UART_BASE(i) + 0x28) + +/* UART_LOWPULSE_MIN_CNT : RO ;bitpos:[19:0] ;default: 20'hFFFFF ; */ +/* Description: This register stores the value of the minimum duration time + * for the low level pulse. it is used in baudrate-detect process. + */ + +#define UART_LOWPULSE_MIN_CNT 0x000FFFFF +#define UART_LOWPULSE_MIN_CNT_M ((UART_LOWPULSE_MIN_CNT_V)<<(UART_LOWPULSE_MIN_CNT_S)) +#define UART_LOWPULSE_MIN_CNT_V 0xFFFFF +#define UART_LOWPULSE_MIN_CNT_S 0 + +#define UART_HIGHPULSE_REG(i) (REG_UART_BASE(i) + 0x2C) + +/* UART_HIGHPULSE_MIN_CNT : RO ;bitpos:[19:0] ;default: 20'hFFFFF ; */ +/* Description: This register stores the value of the maxinum duration time + * for the high level pulse. it is used in baudrate-detect process. + */ + +#define UART_HIGHPULSE_MIN_CNT 0x000FFFFF +#define UART_HIGHPULSE_MIN_CNT_M ((UART_HIGHPULSE_MIN_CNT_V)<<(UART_HIGHPULSE_MIN_CNT_S)) +#define UART_HIGHPULSE_MIN_CNT_V 0xFFFFF +#define UART_HIGHPULSE_MIN_CNT_S 0 + +#define UART_RXD_CNT_REG(i) (REG_UART_BASE(i) + 0x30) + +/* UART_RXD_EDGE_CNT : RO ;bitpos:[9:0] ;default: 10'h0 ; */ +/* Description: This register stores the count of rxd edge change. it is + * used in baudrate-detect process. + */ + +#define UART_RXD_EDGE_CNT 0x000003FF +#define UART_RXD_EDGE_CNT_M ((UART_RXD_EDGE_CNT_V)<<(UART_RXD_EDGE_CNT_S)) +#define UART_RXD_EDGE_CNT_V 0x3FF +#define UART_RXD_EDGE_CNT_S 0 + +#define UART_FLOW_CONF_REG(i) (REG_UART_BASE(i) + 0x34) + +/* UART_SEND_XOFF : R/W ;bitpos:[5] ;default: 1'b0 ; */ +/* Description: Set this bit to send xoff char. it is cleared by hardware + * automatically. + */ + +#define UART_SEND_XOFF (BIT(5)) +#define UART_SEND_XOFF_M (BIT(5)) +#define UART_SEND_XOFF_V 0x1 +#define UART_SEND_XOFF_S 5 + +/* UART_SEND_XON : R/W ;bitpos:[4] ;default: 1'b0 ; */ +/* Description: Set this bit to send xon char. it is cleared by hardware + * automatically. + */ + +#define UART_SEND_XON (BIT(4)) +#define UART_SEND_XON_M (BIT(4)) +#define UART_SEND_XON_V 0x1 +#define UART_SEND_XON_S 4 + +/* UART_FORCE_XOFF : R/W ;bitpos:[3] ;default: 1'b0 ; */ +/* Description: Set this bit to set ctsn to enable the transmitter to go on + * sending data. + */ + +#define UART_FORCE_XOFF (BIT(3)) +#define UART_FORCE_XOFF_M (BIT(3)) +#define UART_FORCE_XOFF_V 0x1 +#define UART_FORCE_XOFF_S 3 + +/* UART_FORCE_XON : R/W ;bitpos:[2] ;default: 1'b0 ; */ +/* Description: Set this bit to clear ctsn to stop the transmitter from + * sending data. + */ + +#define UART_FORCE_XON (BIT(2)) +#define UART_FORCE_XON_M (BIT(2)) +#define UART_FORCE_XON_V 0x1 +#define UART_FORCE_XON_S 2 + +/* UART_XONOFF_DEL : R/W ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: Set this bit to remove flow control char from the received + * data. + */ + +#define UART_XONOFF_DEL (BIT(1)) +#define UART_XONOFF_DEL_M (BIT(1)) +#define UART_XONOFF_DEL_V 0x1 +#define UART_XONOFF_DEL_S 1 + +/* UART_SW_FLOW_CON_EN : R/W ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: Set this bit to enable software flow control. it is used + * with register sw_xon or sw_xoff. + */ + +#define UART_SW_FLOW_CON_EN (BIT(0)) +#define UART_SW_FLOW_CON_EN_M (BIT(0)) +#define UART_SW_FLOW_CON_EN_V 0x1 +#define UART_SW_FLOW_CON_EN_S 0 + +#define UART_SLEEP_CONF_REG(i) (REG_UART_BASE(i) + 0x38) + +/* UART_ACTIVE_THRESHOLD : R/W ;bitpos:[9:0] ;default: 10'hf0 ; */ +/* Description: When the input rxd edge changes more than this register + * value. the uart is active from light sleeping mode. + */ + +#define UART_ACTIVE_THRESHOLD 0x000003FF +#define UART_ACTIVE_THRESHOLD_M ((UART_ACTIVE_THRESHOLD_V)<<(UART_ACTIVE_THRESHOLD_S)) +#define UART_ACTIVE_THRESHOLD_V 0x3FF +#define UART_ACTIVE_THRESHOLD_S 0 + +#define UART_SWFC_CONF_REG(i) (REG_UART_BASE(i) + 0x3C) + +/* UART_XOFF_CHAR : R/W ;bitpos:[31:24] ;default: 8'h13 ; */ +/* Description: This register stores the xoff flow control char.*/ + +#define UART_XOFF_CHAR 0x000000FF +#define UART_XOFF_CHAR_M ((UART_XOFF_CHAR_V)<<(UART_XOFF_CHAR_S)) +#define UART_XOFF_CHAR_V 0xFF +#define UART_XOFF_CHAR_S 24 + +/* UART_XON_CHAR : R/W ;bitpos:[23:16] ;default: 8'h11 ; */ +/* Description: This register stores the xon flow control char.*/ + +#define UART_XON_CHAR 0x000000FF +#define UART_XON_CHAR_M ((UART_XON_CHAR_V)<<(UART_XON_CHAR_S)) +#define UART_XON_CHAR_V 0xFF +#define UART_XON_CHAR_S 16 + +/* UART_XOFF_THRESHOLD : R/W ;bitpos:[15:8] ;default: 8'he0 ; */ +/* Description: When the data amount in receiver's fifo is less than this + * register value. it will send a xon char with uart_sw_flow_con_en set to + * 1. + */ + +#define UART_XOFF_THRESHOLD 0x000000FF +#define UART_XOFF_THRESHOLD_M ((UART_XOFF_THRESHOLD_V)<<(UART_XOFF_THRESHOLD_S)) +#define UART_XOFF_THRESHOLD_V 0xFF +#define UART_XOFF_THRESHOLD_S 8 + +/* UART_XON_THRESHOLD : R/W ;bitpos:[7:0] ;default: 8'h0 ; */ +/* Description: when the data amount in receiver's fifo is more than this + * register value. it will send a xoff char with uart_sw_flow_con_en set to + * 1. + */ + +#define UART_XON_THRESHOLD 0x000000FF +#define UART_XON_THRESHOLD_M ((UART_XON_THRESHOLD_V)<<(UART_XON_THRESHOLD_S)) +#define UART_XON_THRESHOLD_V 0xFF +#define UART_XON_THRESHOLD_S 0 + +#define UART_IDLE_CONF_REG(i) (REG_UART_BASE(i) + 0x40) + +/* UART_TX_BRK_NUM : R/W ;bitpos:[27:20] ;default: 8'ha ; */ +/* Description: This register is used to configure the num of 0 send after + * the process of sending data is done. it is active when txd_brk is set to + * 1. + */ + +#define UART_TX_BRK_NUM 0x000000FF +#define UART_TX_BRK_NUM_M ((UART_TX_BRK_NUM_V)<<(UART_TX_BRK_NUM_S)) +#define UART_TX_BRK_NUM_V 0xFF +#define UART_TX_BRK_NUM_S 20 + +/* UART_TX_IDLE_NUM : R/W ;bitpos:[19:10] ;default: 10'h100 ; */ +/* Description: This register is used to configure the duration time + * between transfers. + */ + +#define UART_TX_IDLE_NUM 0x000003FF +#define UART_TX_IDLE_NUM_M ((UART_TX_IDLE_NUM_V)<<(UART_TX_IDLE_NUM_S)) +#define UART_TX_IDLE_NUM_V 0x3FF +#define UART_TX_IDLE_NUM_S 10 + +/* UART_RX_IDLE_THRHD : R/W ;bitpos:[9:0] ;default: 10'h100 ; */ +/* Description: when receiver takes more time than this register value to + * receive a byte data. it will produce frame end signal for uhci to stop + * receiving data. + */ + +#define UART_RX_IDLE_THRHD 0x000003FF +#define UART_RX_IDLE_THRHD_M ((UART_RX_IDLE_THRHD_V)<<(UART_RX_IDLE_THRHD_S)) +#define UART_RX_IDLE_THRHD_V 0x3FF +#define UART_RX_IDLE_THRHD_S 0 + +#define UART_RS485_CONF_REG(i) (REG_UART_BASE(i) + 0x44) + +/* UART_RS485_TX_DLY_NUM : R/W ;bitpos:[9:6] ;default: 4'b0 ; */ +/* Description: This register is used to delay the transmitter's internal + * data signal. + */ + +#define UART_RS485_TX_DLY_NUM 0x0000000F +#define UART_RS485_TX_DLY_NUM_M ((UART_RS485_TX_DLY_NUM_V)<<(UART_RS485_TX_DLY_NUM_S)) +#define UART_RS485_TX_DLY_NUM_V 0xF +#define UART_RS485_TX_DLY_NUM_S 6 + +/* UART_RS485_RX_DLY_NUM : R/W ;bitpos:[5] ;default: 1'b0 ; */ +/* Description: This register is used to delay the receiver's internal data + * signal. + */ + +#define UART_RS485_RX_DLY_NUM (BIT(5)) +#define UART_RS485_RX_DLY_NUM_M (BIT(5)) +#define UART_RS485_RX_DLY_NUM_V 0x1 +#define UART_RS485_RX_DLY_NUM_S 5 + +/* UART_RS485RXBY_TX_EN : R/W ;bitpos:[4] ;default: 1'b0 ; */ +/* Description: 1: enable rs485's transmitter to send data when rs485's + * receiver is busy. 0:rs485's transmitter should not send data when its + * receiver is busy. + */ + +#define UART_RS485RXBY_TX_EN (BIT(4)) +#define UART_RS485RXBY_TX_EN_M (BIT(4)) +#define UART_RS485RXBY_TX_EN_V 0x1 +#define UART_RS485RXBY_TX_EN_S 4 + +/* UART_RS485TX_RX_EN : R/W ;bitpos:[3] ;default: 1'b0 ; */ +/* Description: Set this bit to enable loopback transmitter's output data + * signal to receiver's input data signal. + */ + +#define UART_RS485TX_RX_EN (BIT(3)) +#define UART_RS485TX_RX_EN_M (BIT(3)) +#define UART_RS485TX_RX_EN_V 0x1 +#define UART_RS485TX_RX_EN_S 3 + +/* UART_DL1_EN : R/W ;bitpos:[2] ;default: 1'b0 ; */ +/* Description: Set this bit to delay the stop bit by 1 bit.*/ + +#define UART_DL1_EN (BIT(2)) +#define UART_DL1_EN_M (BIT(2)) +#define UART_DL1_EN_V 0x1 +#define UART_DL1_EN_S 2 + +/* UART_DL0_EN : R/W ;bitpos:[1] ;default: 1'b0 ; */ +/* Description: Set this bit to delay the stop bit by 1 bit.*/ + +#define UART_DL0_EN (BIT(1)) +#define UART_DL0_EN_M (BIT(1)) +#define UART_DL0_EN_V 0x1 +#define UART_DL0_EN_S 1 + +/* UART_RS485_EN : R/W ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: Set this bit to choose rs485 mode.*/ + +#define UART_RS485_EN (BIT(0)) +#define UART_RS485_EN_M (BIT(0)) +#define UART_RS485_EN_V 0x1 +#define UART_RS485_EN_S 0 + +#define UART_AT_CMD_PRECNT_REG(i) (REG_UART_BASE(i) + 0x48) + +/* UART_PRE_IDLE_NUM : R/W ;bitpos:[23:0] ;default: 24'h186a00 ; */ +/* Description: This register is used to configure the idle duration time + * before the first at_cmd is received by receiver. when the the duration + * is less than this register value it will not take the next data received + * as at_cmd char. + */ + +#define UART_PRE_IDLE_NUM 0x00FFFFFF +#define UART_PRE_IDLE_NUM_M ((UART_PRE_IDLE_NUM_V)<<(UART_PRE_IDLE_NUM_S)) +#define UART_PRE_IDLE_NUM_V 0xFFFFFF +#define UART_PRE_IDLE_NUM_S 0 + +#define UART_AT_CMD_POSTCNT_REG(i) (REG_UART_BASE(i) + 0x4c) + +/* UART_POST_IDLE_NUM : R/W ;bitpos:[23:0] ;default: 24'h186a00 ; */ +/* Description: This register is used to configure the duration time between + * the last at_cmd and the next data. when the duration is less than this + * register value it will not take the previous data as at_cmd char. + */ + +#define UART_POST_IDLE_NUM 0x00FFFFFF +#define UART_POST_IDLE_NUM_M ((UART_POST_IDLE_NUM_V)<<(UART_POST_IDLE_NUM_S)) +#define UART_POST_IDLE_NUM_V 0xFFFFFF +#define UART_POST_IDLE_NUM_S 0 + +#define UART_AT_CMD_GAPTOUT_REG(i) (REG_UART_BASE(i) + 0x50) + +/* UART_RX_GAP_TOUT : R/W ;bitpos:[23:0] ;default: 24'h1e00 ; */ +/* Description: This register is used to configure the duration time between + * the at_cmd chars. when the duration time is less than this register + * value it will not take the datas as continous at_cmd chars. + */ + +#define UART_RX_GAP_TOUT 0x00FFFFFF +#define UART_RX_GAP_TOUT_M ((UART_RX_GAP_TOUT_V)<<(UART_RX_GAP_TOUT_S)) +#define UART_RX_GAP_TOUT_V 0xFFFFFF +#define UART_RX_GAP_TOUT_S 0 + +#define UART_AT_CMD_CHAR_REG(i) (REG_UART_BASE(i) + 0x54) + +/* UART_CHAR_NUM : R/W ;bitpos:[15:8] ;default: 8'h3 ; */ +/* Description: This register is used to configure the num of continous + * at_cmd chars received by receiver. + */ + +#define UART_CHAR_NUM 0x000000FF +#define UART_CHAR_NUM_M ((UART_CHAR_NUM_V)<<(UART_CHAR_NUM_S)) +#define UART_CHAR_NUM_V 0xFF +#define UART_CHAR_NUM_S 8 + +/* UART_AT_CMD_CHAR : R/W ;bitpos:[7:0] ;default: 8'h2b ; */ +/* Description: This register is used to configure the content of at_cmd + * char. + */ + +#define UART_AT_CMD_CHAR 0x000000FF +#define UART_AT_CMD_CHAR_M ((UART_AT_CMD_CHAR_V)<<(UART_AT_CMD_CHAR_S)) +#define UART_AT_CMD_CHAR_V 0xFF +#define UART_AT_CMD_CHAR_S 0 + +#define UART_MEM_CONF_REG(i) (REG_UART_BASE(i) + 0x58) + +/* UART_TX_MEM_EMPTY_THRHD : R/W ;bitpos:[30:28] ;default: 3'h0 ; */ +/* Description: refer to txfifo_empty_thrhd 's describtion.*/ + +#define UART_TX_MEM_EMPTY_THRHD 0x00000007 +#define UART_TX_MEM_EMPTY_THRHD_M ((UART_TX_MEM_EMPTY_THRHD_V)<<(UART_TX_MEM_EMPTY_THRHD_S)) +#define UART_TX_MEM_EMPTY_THRHD_V 0x7 +#define UART_TX_MEM_EMPTY_THRHD_S 28 + +/* UART_RX_MEM_FULL_THRHD : R/W ;bitpos:[27:25] ;default: 3'h0 ; */ +/* Description: refer to the rxfifo_full_thrhd's describtion.*/ + +#define UART_RX_MEM_FULL_THRHD 0x00000007 +#define UART_RX_MEM_FULL_THRHD_M ((UART_RX_MEM_FULL_THRHD_V)<<(UART_RX_MEM_FULL_THRHD_S)) +#define UART_RX_MEM_FULL_THRHD_V 0x7 +#define UART_RX_MEM_FULL_THRHD_S 25 + +/* UART_XOFF_THRESHOLD_H2 : R/W ;bitpos:[24:23] ;default: 2'h0 ; */ +/* Description: refer to the uart_xoff_threshold's describtion.*/ + +#define UART_XOFF_THRESHOLD_H2 0x00000003 +#define UART_XOFF_THRESHOLD_H2_M ((UART_XOFF_THRESHOLD_H2_V)<<(UART_XOFF_THRESHOLD_H2_S)) +#define UART_XOFF_THRESHOLD_H2_V 0x3 +#define UART_XOFF_THRESHOLD_H2_S 23 + +/* UART_XON_THRESHOLD_H2 : R/W ;bitpos:[22:21] ;default: 2'h0 ; */ +/* Description: refer to the uart_xon_threshold's describtion.*/ + +#define UART_XON_THRESHOLD_H2 0x00000003 +#define UART_XON_THRESHOLD_H2_M ((UART_XON_THRESHOLD_H2_V)<<(UART_XON_THRESHOLD_H2_S)) +#define UART_XON_THRESHOLD_H2_V 0x3 +#define UART_XON_THRESHOLD_H2_S 21 + +/* UART_RX_TOUT_THRHD_H3 : R/W ;bitpos:[20:18] ;default: 3'h0 ; */ +/* Description: refer to the rx_tout_thrhd's describtion.*/ + +#define UART_RX_TOUT_THRHD_H3 0x00000007 +#define UART_RX_TOUT_THRHD_H3_M ((UART_RX_TOUT_THRHD_H3_V)<<(UART_RX_TOUT_THRHD_H3_S)) +#define UART_RX_TOUT_THRHD_H3_V 0x7 +#define UART_RX_TOUT_THRHD_H3_S 18 + +/* UART_RX_FLOW_THRHD_H3 : R/W ;bitpos:[17:15] ;default: 3'h0 ; */ +/* Description: refer to the rx_flow_thrhd's describtion.*/ + +#define UART_RX_FLOW_THRHD_H3 0x00000007 +#define UART_RX_FLOW_THRHD_H3_M ((UART_RX_FLOW_THRHD_H3_V)<<(UART_RX_FLOW_THRHD_H3_S)) +#define UART_RX_FLOW_THRHD_H3_V 0x7 +#define UART_RX_FLOW_THRHD_H3_S 15 + +/* UART_TX_SIZE : R/W ;bitpos:[10:7] ;default: 4'h1 ; */ +/* Description: This register is used to configure the amount of mem + * allocated to transmitter's fifo.the default byte num is 128. + */ + +#define UART_TX_SIZE 0x0000000F +#define UART_TX_SIZE_M ((UART_TX_SIZE_V)<<(UART_TX_SIZE_S)) +#define UART_TX_SIZE_V 0xF +#define UART_TX_SIZE_S 7 + +/* UART_RX_SIZE : R/W ;bitpos:[6:3] ;default: 4'h1 ; */ +/* Description: This register is used to configure the amount of mem + * allocated to receiver's fifo. the default byte num is 128. + */ + +#define UART_RX_SIZE 0x0000000F +#define UART_RX_SIZE_M ((UART_RX_SIZE_V)<<(UART_RX_SIZE_S)) +#define UART_RX_SIZE_V 0xF +#define UART_RX_SIZE_S 3 + +/* UART_MEM_PD : R/W ;bitpos:[0] ;default: 1'b0 ; */ +/* Description: Set this bit to power down mem.when reg_mem_pd registers in + * the 3 uarts are all set to 1 mem will enter low power mode. + */ + +#define UART_MEM_PD (BIT(0)) +#define UART_MEM_PD_M (BIT(0)) +#define UART_MEM_PD_V 0x1 +#define UART_MEM_PD_S 0 + +#define UART_MEM_TX_STATUS_REG(i) (REG_UART_BASE(i) + 0x5c) + +/* UART_MEM_TX_STATUS : RO ;bitpos:[23:0] ;default: 24'h0 ; */ +/* Description: */ + +#define UART_MEM_TX_STATUS 0x00FFFFFF +#define UART_MEM_TX_STATUS_M ((UART_MEM_TX_STATUS_V)<<(UART_MEM_TX_STATUS_S)) +#define UART_MEM_TX_STATUS_V 0xFFFFFF +#define UART_MEM_TX_STATUS_S 0 + +#define UART_MEM_RX_STATUS_REG(i) (REG_UART_BASE(i) + 0x60) + +/* UART_MEM_RX_STATUS : RO ;bitpos:[23:0] ;default: 24'h0 ; */ +/* Description: */ + +#define UART_MEM_RX_STATUS 0x00FFFFFF +#define UART_MEM_RX_STATUS_M ((UART_MEM_RX_STATUS_V)<<(UART_MEM_RX_STATUS_S)) +#define UART_MEM_RX_STATUS_V 0xFFFFFF +#define UART_MEM_RX_STATUS_S 0 + +#define UART_MEM_CNT_STATUS_REG(i) (REG_UART_BASE(i) + 0x64) + +/* UART_TX_MEM_CNT : RO ;bitpos:[5:3] ;default: 3'b0 ; */ +/* Description: refer to the txfifo_cnt's describtion.*/ + +#define UART_TX_MEM_CNT 0x00000007 +#define UART_TX_MEM_CNT_M ((UART_TX_MEM_CNT_V)<<(UART_TX_MEM_CNT_S)) +#define UART_TX_MEM_CNT_V 0x7 +#define UART_TX_MEM_CNT_S 3 + +/* UART_RX_MEM_CNT : RO ;bitpos:[2:0] ;default: 3'b0 ; */ +/* Description: refer to the rxfifo_cnt's describtion.*/ + +#define UART_RX_MEM_CNT 0x00000007 +#define UART_RX_MEM_CNT_M ((UART_RX_MEM_CNT_V)<<(UART_RX_MEM_CNT_S)) +#define UART_RX_MEM_CNT_V 0x7 +#define UART_RX_MEM_CNT_S 0 + +#define UART_POSPULSE_REG(i) (REG_UART_BASE(i) + 0x68) + +/* UART_POSEDGE_MIN_CNT : RO ;bitpos:[19:0] ;default: 20'hFFFFF ; */ +/* Description: This register stores the count of rxd posedge edge. it is + * used in boudrate-detect process. + */ + +#define UART_POSEDGE_MIN_CNT 0x000FFFFF +#define UART_POSEDGE_MIN_CNT_M ((UART_POSEDGE_MIN_CNT_V)<<(UART_POSEDGE_MIN_CNT_S)) +#define UART_POSEDGE_MIN_CNT_V 0xFFFFF +#define UART_POSEDGE_MIN_CNT_S 0 + +#define UART_NEGPULSE_REG(i) (REG_UART_BASE(i) + 0x6c) + +/* UART_NEGEDGE_MIN_CNT : RO ;bitpos:[19:0] ;default: 20'hFFFFF ; */ +/* Description: This register stores the count of rxd negedge edge. it is + * used in boudrate-detect process. + */ + +#define UART_NEGEDGE_MIN_CNT 0x000FFFFF +#define UART_NEGEDGE_MIN_CNT_M ((UART_NEGEDGE_MIN_CNT_V)<<(UART_NEGEDGE_MIN_CNT_S)) +#define UART_NEGEDGE_MIN_CNT_V 0xFFFFF +#define UART_NEGEDGE_MIN_CNT_S 0 + +#define UART_DATE_REG(i) (REG_UART_BASE(i) + 0x78) + +/* UART_DATE : R/W ;bitpos:[31:0] ;default: 32'h15122500 ; */ +/* Description: */ + +#define UART_DATE 0xFFFFFFFF +#define UART_DATE_M ((UART_DATE_V)<<(UART_DATE_S)) +#define UART_DATE_V 0xFFFFFFFF +#define UART_DATE_S 0 + +#define UART_ID_REG(i) (REG_UART_BASE(i) + 0x7C) + +/* UART_ID : R/W ;bitpos:[31:0] ;default: 32'h0500 ; */ +/* Description: */ + +#define UART_ID 0xFFFFFFFF +#define UART_ID_M ((UART_ID_V)<<(UART_ID_S)) +#define UART_ID_V 0xFFFFFFFF +#define UART_ID_S 0 + +#endif /*__ARCH_XTENSA_SRC_ESP32_CHIP_ESP32_UART_H */ diff --git a/arch/xtensa/src/esp32/esp32_clockconfig.c b/arch/xtensa/src/esp32/esp32_clockconfig.c index 2da4e0b4dec..7ccc12090e0 100644 --- a/arch/xtensa/src/esp32/esp32_clockconfig.c +++ b/arch/xtensa/src/esp32/esp32_clockconfig.c @@ -13,7 +13,7 @@ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at - + * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software @@ -26,21 +26,24 @@ /**************************************************************************** * Included Files - **************************************************************************** + ****************************************************************************/ #include #include "xtensa.h" +#ifndef CONFIG_SUPPRESS_CLOCK_CONFIG #warning REVISIT ... function prototypes void phy_get_romfunc_addr(void); void rtc_init_lite(void); void rtc_set_cpu_freq(xtal_freq_t xtal_freq, enum xtal_freq_e cpu_freq); +#endif /**************************************************************************** * Private Types - **************************************************************************** + ****************************************************************************/ +#ifndef CONFIG_SUPPRESS_CLOCK_CONFIG enum xtal_freq_e { XTAL_40M = 40, @@ -55,10 +58,11 @@ enum xtal_freq_e CPU_160M = 2, CPU_240M = 3, }; +#endif /**************************************************************************** * Public Functions - **************************************************************************** + ****************************************************************************/ /**************************************************************************** * Name: esp32_clockconfig diff --git a/arch/xtensa/src/esp32/esp32_cpuint.c b/arch/xtensa/src/esp32/esp32_cpuint.c new file mode 100644 index 00000000000..6a6aec7fe5a --- /dev/null +++ b/arch/xtensa/src/esp32/esp32_cpuint.c @@ -0,0 +1,510 @@ +/**************************************************************************** + * arch/xtensa/src/esp32/esp32_irq.c + * + * Copyright (C) 2016 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************/ + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include + +#include +#include +#include +#include + +#include +#include +#include + +#include "xtensa.h" + +/**************************************************************************** + * Pre-processor Definitions + ****************************************************************************/ + +#define ESP32_INTSET(n) ((1 << (n)) - 1) +#define ESP32_LEVEL_SET ESP32_INTSET(ESP32_CPUINT_NLEVELPERIPHS) +#define ESP32_EDGE_SET ESP32_INTSET(ESP32_CPUINT_NEDGEPERIPHS) + +/* Mapping Peripheral IDs to map register addresses + * + * PERIPHERAL ID DPORT REGISTER OFFSET + * MNEMONIC VAL PRO CPU APP CPU + * -------------------------- --- ------- ------- + * ESP32_PERIPH_MAC 0 0x104 0x218 + * ESP32_PERIPH_MAC_NMI 1 0x108 0x21c + * ESP32_PERIPH_BB 2 0x10c 0x220 + * ESP32_PERIPH_BB_MAC 3 0x110 0x224 + * ESP32_PERIPH_BT_BB 4 0x114 0x228 + * ESP32_PERIPH_BT_BB_NMI 5 0x118 0x22c + * ESP32_PERIPH_RWBT_IRQ 6 0x11c 0x230 + * ESP32_PERIPH_RWBLE_IRQ 7 0x120 0x234 + * ESP32_PERIPH_RWBT_NMI 8 0x124 0x238 + * ESP32_PERIPH_RWBLE_NMI 9 0x128 0x23c + * ESP32_PERIPH_SLC0 10 0x12c 0x240 + * ESP32_PERIPH_SLC1 11 0x130 0x244 + * ESP32_PERIPH_UHCI0 12 0x134 0x248 + * ESP32_PERIPH_UHCI1 13 0x138 0x24c + * ESP32_PERIPH_TG_T0_LEVEL 14 0x13c 0x250 + * ESP32_PERIPH_TG_T1_LEVEL 15 0x140 0x254 + * ESP32_PERIPH_TG_WDT_LEVEL 16 0x144 0x258 + * ESP32_PERIPH_TG_LACT_LEVEL 17 0x148 0x25c + * ESP32_PERIPH_TG1_T0_LEVEL 18 0x14c 0x260 + * ESP32_PERIPH_TG1_T1_LEVEL 19 0x150 0x264 + * ESP32_PERIPH_TG1_WDT_LEVEL 20 0x154 0x268 + * ESP32_PERIPH_G1_LACT_LEVEL 21 0x158 0x26c + * ESP32_PERIPH_CPU_GPIO 22 0x15c 0x270 + * ESP32_PERIPH_CPU_NMI 23 0x160 0x274 + * ESP32_PERIPH_CPU_CPU0 24 0x164 0x278 + * ESP32_PERIPH_CPU_CPU1 25 0x168 0x27c + * ESP32_PERIPH_CPU_CPU2 26 0x16c 0x280 + * ESP32_PERIPH_CPU_CPU3 27 0x170 0x284 + * ESP32_PERIPH_SPI0 28 0x174 0x288 + * ESP32_PERIPH_SPI1 29 0x178 0x28c + * ESP32_PERIPH_SPI2 30 0x17c 0x290 + * ESP32_PERIPH_SPI3 31 0x180 0x294 + * ESP32_PERIPH_I2S0 32 0x184 0x298 + * ESP32_PERIPH_I2S1 33 0x188 0x29c + * ESP32_PERIPH_UART 34 0x18c 0x2a0 + * ESP32_PERIPH_UART1 35 0x190 0x2a4 + * ESP32_PERIPH_UART2 36 0x194 0x2a8 + * ESP32_PERIPH_SDIO_HOST 37 0x198 0x2ac + * ESP32_PERIPH_EMAC 38 0x19c 0x2b0 + * ESP32_PERIPH_PWM0 39 0x1a0 0x2b4 + * ESP32_PERIPH_PWM1 40 0x1a4 0x2b8 + * ESP32_PERIPH_PWM2 41 0x1a8 0x2bc + * ESP32_PERIPH_PWM3 42 0x1ac 0x2c0 + * ESP32_PERIPH_LEDC 43 0x1b0 0x2c4 + * ESP32_PERIPH_EFUSE 44 0x1b4 0x2c8 + * ESP32_PERIPH_CAN 45 0x1b8 0x2cc + * ESP32_PERIPH_RTC_CORE 46 0x1bc 0x2d0 + * ESP32_PERIPH_RMT 47 0x1c0 0x2d4 + * ESP32_PERIPH_PCNT 48 0x1c4 0x2d8 + * ESP32_PERIPH_I2C_EXT0 49 0x1c8 0x2dc + * ESP32_PERIPH_I2C_EXT1 50 0x1cc 0x2e0 + * ESP32_PERIPH_RSA 51 0x1d0 0x2e4 + * ESP32_PERIPH_SPI1_DMA 52 0x1d4 0x2e8 + * ESP32_PERIPH_SPI2_DMA 53 0x1d8 0x2ec + * ESP32_PERIPH_SPI3_DMA 54 0x1dc 0x2f0 + * ESP32_PERIPH_WDG 55 0x1e0 0x2f4 + * ESP32_PERIPH_TIMER1 56 0x1e4 0x2f8 + * ESP32_PERIPH_TIMER2 57 0x1e8 0x2fc + * ESP32_PERIPH_TG_T0_EDGE 58 0x1ec 0x300 + * ESP32_PERIPH_TG_T1_EDGE 59 0x1f0 0x304 + * ESP32_PERIPH_TG_WDT_EDGE 60 0x1F4 0x308 + * ESP32_PERIPH_TG_LACT_EDGE 61 0x1F8 0x30c + * ESP32_PERIPH_TG1_T0_EDGE 62 0x1fc 0x310 + * ESP32_PERIPH_TG1_T1_EDGE 63 0x200 0x314 + * ESP32_PERIPH_TG1_WDT_EDGE 64 0x204 0x318 + * ESP32_PERIPH_TG1_LACT_EDGE 65 0x208 0x31c + * ESP32_PERIPH_MMU_IA 66 0x20c 0x320 + * ESP32_PERIPH_MPU_IA 67 0x210 0x324 + * ESP32_PERIPH_CACHE_IA 68 0x214 0x328 + */ + +#define DPORT_PRO_MAP_REGADDR(n) (DR_REG_DPORT_BASE + 0x104 + ((n) << 2)) +#define DPORT_APP_MAP_REGADDR(n) (DR_REG_DPORT_BASE + 0x218 + ((n) << 2)) + +/* CPU interrupts can be detached from any peripheral source by setting the + * map register to an internal CPU interrupt (6, 7, 11, 15, 16, or 29). + */ + +#define NO_CPUINT ESP32_CPUINT_TIMER0 + +/* Priority range is 1-5 */ + +#define ESP32_MIN_PRIORITY 1 +#define ESP32_MAX_PRIORITY 5 +#define ESP32_PRIO_INDEX(p) ((p) - ESP32_MIN_PRIORITY) + +/**************************************************************************** + * Private Data + ****************************************************************************/ + +/* g_intenable[] is a shadow copy of the per-CPU INTENABLE register + * content. + */ + +#ifdef CONFIG_SMP + +static uint32_t g_intenable[CONFIG_SMP_NCPUS]; + +#else + +static uint32_t g_intenable[1]; + +#endif + +/* Bitsets for free, unallocated CPU interrupts */ + +static uint32_t g_level_ints = ESP32_LEVEL_SET; +static uint32_t g_edge_ints = ESP32_EDGE_SET; + +/* Bitsets for each interrupt priority 1-5 */ + +static uint32_t g_priority[5] = +{ + ESP32_INTPRI1_MASK, + ESP32_INTPRI2_MASK, + ESP32_INTPRI3_MASK, + ESP32_INTPRI4_MASK, + ESP32_INTPRI5_MASK +}; + +/**************************************************************************** + * Private Functions + ****************************************************************************/ + +/**************************************************************************** + * Public Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: up_disable_irq + * + * Description: + * Disable the CPU interrupt specified by 'cpuint' + * + ****************************************************************************/ + +void up_disable_irq(int cpuint) +{ +#ifdef CONFIG_SMP + int cpu; +#endif + + DEBUGASSERT(cpuint >= 0 && cpuint <= ESP32_CPUINT_MAX); + +#ifdef CONFIG_SMP + cpu = up_cpu_index(); + (void)xtensa_disable_cpuint(&g_intenable[cpu], (1ul << cpuint)); +#else + (void)xtensa_disable_cpuint(&g_intenable[0], (1ul << cpuint)); +#endif +} + +/**************************************************************************** + * Name: up_enable_irq + * + * Description: + * Ensable the CPU interrupt specified by 'cpuint' + * + ****************************************************************************/ + +void up_enable_irq(int cpuint) +{ +#ifdef CONFIG_SMP + int cpu; +#endif + + DEBUGASSERT(cpuint >= 0 && cpuint <= ESP32_CPUINT_MAX); + +#ifdef CONFIG_SMP + cpu = up_cpu_index(); + (void)xtensa_enable_cpuint(&g_intenable[cpu], (1ul << cpuint)); +#else + (void)xtensa_enable_cpuint(&g_intenable[0], (1ul << cpuint)); +#endif +} + +/**************************************************************************** + * Name: esp32_alloc_levelint + * + * Description: + * Allocate a level CPU interrupt + * + * Input Parameters: + * priority - Priority of the CPU interrupt (1-5) + * + * Returned Value: + * On success, the allocated level-sensitive, CPU interrupt numbr is + * returned. A negated errno is returned on failure. The only possible + * failure is that all level-sensitive CPU interrupts have already been + * allocated. + * + ****************************************************************************/ + +int esp32_alloc_levelint(int priority) +{ + irqstate_t flags; + uint32_t mask; + uint32_t intset; + int cpuint; + int ret = -ENOMEM; + + DEBUGASSERT(priority >= ESP32_MIN_PRIORITY && priority <= ESP32_MAX_PRIORITY) + + /* Check if there are any level CPU interrupts available */ + + flags = enter_critical_section(); + + intset = g_level_ints & g_priority[ESP32_PRIO_INDEX(priority)] & ESP32_LEVEL_SET; + if (intset != 0) + { + /* Skip over initial zeroes as quickly in groups of 8 bits. */ + + for (cpuint = 0, mask = 0xff; + cpuint <= ESP32_CPUINT_MAX && (intset & mask) == 0; + cpuint += 8, mask <<= 8); + + /* Search for an unallocated CPU interrupt number in the remaining intset. */ + + for (; cpuint <= ESP32_CPUINT_MAX && intset != 0; cpuint++) + { + /* If the bit corresponding to the CPU interrupt is '1', then + * that CPU interrupt is available. + */ + + mask = (1ul << cpuint); + if ((intset & mask) != 0) + { + /* Got it! */ + + g_level_ints &= ~mask; + ret = cpuint; + break; + } + + /* Clear the bit in intset so that we may exit the loop sooner */ + + intset &= ~mask; + } + } + + leave_critical_section(flags); + return ret; +} + +/**************************************************************************** + * Name: esp32_free_levelint + * + * Description: + * Free a previoulsy allocated level CPU interrupt + * + * Input Parameters: + * The CPU interrupt number to be freed + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_free_levelint(int cpuint) +{ + irqstate_t flags; + uint32_t mask; + + DEBUGASSERT(cpuint >= 0 && cpuint < ESP32_CPUINT_NLEVELPERIPHS); + + /* Mark the CPU interrupt as available */ + + mask = (1ul << cpuint); + flags = enter_critical_section(); + DEBUGASSERT((g_level_ints & mask) == 0); + g_level_ints |= mask; + leave_critical_section(flags); +} + +/**************************************************************************** + * Name: esp32_alloc_edgeint + * + * Description: + * Allocate an edge CPU interrupt + * + * Input Parameters: + * priority - Priority of the CPU interrupt (1-5) + * + * Returned Value: + * On success, the allocated edge-sensitive, CPU interrupt numbr is + * returned. A negated errno is returned on failure. The only possible + * failure is that all edge-sensitive CPU interrupts have already been + * allocated. + * + ****************************************************************************/ + +int esp32_alloc_edgeint(int priority) +{ + irqstate_t flags; + uint32_t mask; + uint32_t intset; + int cpuint; + int ret = -ENOMEM; + + DEBUGASSERT(priority >= ESP32_MIN_PRIORITY && priority <= ESP32_MAX_PRIORITY) + + /* Check if there are any level CPU interrupts available */ + + flags = enter_critical_section(); + + intset = g_edge_ints & g_priority[ESP32_PRIO_INDEX(priority)] & ESP32_EDGE_SET; + if (intset != 0) + { + /* Skip over initial zeroes as quickly in groups of 8 bits. */ + + for (cpuint = 0, mask = 0xff; + cpuint <= ESP32_CPUINT_MAX && (intset & mask) == 0; + cpuint += 8, mask <<= 8); + + /* Search for an unallocated CPU interrupt number in the remaining intset. */ + + for (; cpuint <= ESP32_CPUINT_MAX && intset != 0; cpuint++) + { + /* If the bit corresponding to the CPU interrupt is '1', then + * that CPU interrupt is available. + */ + + mask = (1ul << cpuint); + if ((intset & mask) != 0) + { + /* Got it! */ + + g_edge_ints &= ~mask; + ret = cpuint; + break; + } + + /* Clear the bit in intset so that we may exit the loop sooner */ + + intset &= ~mask; + } + } + + leave_critical_section(flags); + return ret; +} + +/**************************************************************************** + * Name: esp32_free_edgeint + * + * Description: + * Free a previoulsy allocated edge CPU interrupt + * + * Input Parameters: + * The CPU interrupt number to be freed + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_free_edgeint(int cpuint) +{ + irqstate_t flags; + uint32_t mask; + + DEBUGASSERT(cpuint >= 0 && cpuint < ESP32_CPUINT_NEDGEPERIPHS); + + /* Mark the CPU interrupt as available */ + + mask = (1ul << cpuint); + flags = enter_critical_section(); + DEBUGASSERT((g_edge_ints & mask) == 0); + g_edge_ints |= mask; + leave_critical_section(flags); +} + +/**************************************************************************** + * Name: esp32_attach_peripheral + * + * Description: + * Attach a peripheral interupt to a CPU interrupt. + * + * Input Parameters: + * cpu - The CPU to receive the interrupt 0=PRO CPU 1=APP CPU + * periphid - The peripheral number from ira.h to be assigned. + * cpuint - The CPU interrupt to receive the peripheral interrupt + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_attach_peripheral(int cpu, int periphid, int cpuint) +{ + uintptr_t regaddr; + + DEBUGASSERT(periphid >= 0 && periphid < NR_PERIPHERALS); + DEBUGASSERT(cpuint >= 0 && cpuint <= ESP32_CPUINT_MAX); +#ifdef CONFIG_SMP + DEBUGASSERT(cpu >= 0 && cpu < CONFIG_SMP_NCPUS); + + if (cpu != 0) + { + regaddr = DPORT_APP_MAP_REGADDR(periphid); + } + else +#endif + { + regaddr = DPORT_PRO_MAP_REGADDR(periphid); + } + + putreg(cpuint, regaddr); +} + +/**************************************************************************** + * Name: esp32_detach_peripheral + * + * Description: + * Detach a peripheral interupt from a CPU interrupt. + * + * Input Parameters: + * cpu - The CPU to receive the interrupt 0=PRO CPU 1=APP CPU + * periphid - The peripheral number from ira.h to be assigned. + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_detach_peripheral(int cpu, int periphid) +{ + uintptr_t regaddr; + + DEBUGASSERT(periphid >= 0 && periphid < NR_PERIPHERALS); +#ifdef CONFIG_SMP + DEBUGASSERT(cpu >= 0 && cpu < CONFIG_SMP_NCPUS); + + if (cpu != 0) + { + regaddr = DPORT_APP_MAP_REGADDR(periphid); + } + else +#endif + { + regaddr = DPORT_PRO_MAP_REGADDR(periphid); + } + + putreg(NO_CPUINT, regaddr); +} diff --git a/arch/xtensa/src/esp32/esp32_cpuint.h b/arch/xtensa/src/esp32/esp32_cpuint.h new file mode 100644 index 00000000000..746248456de --- /dev/null +++ b/arch/xtensa/src/esp32/esp32_cpuint.h @@ -0,0 +1,154 @@ +/**************************************************************************** + * arch/xtensa/src/esp32/esp32_cpuint.h + * + * Copyright (C) 2016 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************/ + +#ifndef __ARCH_XTENSA_SRC_ESP32_ESP32_CPUINT_H +#define __ARCH_XTENSA_SRC_ESP32_ESP32_CPUINT_H 1 + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include + +/**************************************************************************** + * Public Function Prototypes + ****************************************************************************/ + +/**************************************************************************** + * Name: esp32_alloc_levelint + * + * Description: + * Allocate a level CPU interrupt + * + * Input Parameters: + * priority - Priority of the CPU interrupt (1-5) + * + * Returned Value: + * On success, the allocated level-sensitive, CPU interrupt numbr is + * returned. A negated errno is returned on failure. The only possible + * failure is that all level-sensitive CPU interrupts have already been + * allocated. + * + ****************************************************************************/ + +int esp32_alloc_levelint(int priority); + +/**************************************************************************** + * Name: esp32_free_levelint + * + * Description: + * Free a previoulsy allocated level CPU interrupt + * + * Input Parameters: + * cpuint - The CPU interrupt number to be freed + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_free_levelint(int cpuint); + +/**************************************************************************** + * Name: esp32_alloc_edgeint + * + * Description: + * Allocate an edge CPU interrupt + * + * Input Parameters: + * priority - Priority of the CPU interrupt (1-5) + * + * Returned Value: + * On success, the allocated edge-sensitive, CPU interrupt numbr is + * returned. A negated errno is returned on failure. The only possible + * failure is that all edge-sensitive CPU interrupts have already been + * allocated. + * + ****************************************************************************/ + +int esp32_alloc_edgeint(int priority); + +/**************************************************************************** + * Name: esp32_free_edgeint + * + * Description: + * Free a previoulsy allocated edge CPU interrupt + * + * Input Parameters: + * cpuint - The CPU interrupt number to be freed + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_free_edgeint(int cpuint, int priority); + +/**************************************************************************** + * Name: esp32_attach_peripheral + * + * Description: + * Attach a peripheral interupt to a CPU interrupt. + * + * Input Parameters: + * cpu - The CPU to receive the interrupt 0=PRO CPU 1=APP CPU + * periphid - The peripheral number from ira.h to be attached. + * cpuint - The CPU interrupt to receive the peripheral interrupt + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_attach_peripheral(int cpu, int periphid, int cpuint); + +/**************************************************************************** + * Name: esp32_detach_peripheral + * + * Description: + * Detach a peripheral interupt from a CPU interrupt. + * + * Input Parameters: + * cpu - The CPU to receive the interrupt 0=PRO CPU 1=APP CPU + * periphid - The peripheral number from ira.h to be detached. + * + * Returned Value: + * None + * + ****************************************************************************/ + +void esp32_detach_peripheral(int cpu, int periphid); + +#endif /* __ARCH_XTENSA_SRC_ESP32_ESP32_CPUINT_H */ diff --git a/arch/xtensa/src/esp32/esp32_cpustart.c b/arch/xtensa/src/esp32/esp32_cpustart.c index 038a2851c2a..ec5d0c7d063 100644 --- a/arch/xtensa/src/esp32/esp32_cpustart.c +++ b/arch/xtensa/src/esp32/esp32_cpustart.c @@ -83,6 +83,20 @@ static inline void xtensa_registerdump(FAR struct tcb_s *tcb) # define xtensa_registerdump(tcb) #endif +/**************************************************************************** + * Name: xtensa_disable_all + ****************************************************************************/ + +static inline void xtensa_disable_all(void) +{ + __asm__ __volatile__ + ( + "movi a2, 0\n" + "xsr a2, INTENABLE\n" + : : : "a2" + ); +} + /**************************************************************************** * Public Functions ****************************************************************************/ @@ -106,6 +120,7 @@ static inline void xtensa_registerdump(FAR struct tcb_s *tcb) int xtensa_start_handler(int irq, FAR void *context) { FAR struct tcb_s *tcb; + int i; sinfo("CPU%d Started\n", up_cpu_index()); @@ -127,6 +142,17 @@ int xtensa_start_handler(int irq, FAR void *context) esp32_region_protection(); + /* Disable all PRO CPU interrupts */ + + xtensa_disable_all(); + + /* Detach all peripheral sources APP CPU interrupts */ + + for (i = 0; i < NR_PERIPHERALS) + { + esp32_detach_peripheral(1, i);; + } + /* Dump registers so that we can see what is going to happen on return */ xtensa_registerdump(tcb); diff --git a/arch/xtensa/src/esp32/esp32_intdecode.c b/arch/xtensa/src/esp32/esp32_intdecode.c index 5490e614e36..d75cf08914c 100644 --- a/arch/xtensa/src/esp32/esp32_intdecode.c +++ b/arch/xtensa/src/esp32/esp32_intdecode.c @@ -44,6 +44,24 @@ #include "chip/esp32_dport.h" #include "xtensa.h" +/**************************************************************************** + * Private Data + ****************************************************************************/ + +static const uint8_t g_baseirq[3] = +{ + ESP32_IRQ_SREG0, + ESP32_IRQ_SREG1, + ESP32_IRQ_SREG2 +}; + +static const uint8_t g_nirqs[3] = +{ + ESP32_NIRQS_SREG0, + ESP32_NIRQS_SREG1, + ESP32_NIRQS_SREG2 +}; + /**************************************************************************** * Public Functions ****************************************************************************/ @@ -73,6 +91,7 @@ uint32_t *xtensa_int_decode(uint32_t *regs) int regndx; int bit; int baseirq; + int nirqs; #ifdef CONFIG_SMP int cpu; @@ -94,19 +113,23 @@ uint32_t *xtensa_int_decode(uint32_t *regs) * registers. */ - for (regndx = 0, baseirq = XTENSA_IRQ_SREG0; - regndx < 3; - regndx++, baseirq += 32, regaddr += sizeof(uint32_t)) + for (regndx = 0; regndx < 3; regndx++) { /* Fetch the next register status register */ - regval = getreg32(regaddr); + regval = getreg32(regaddr); + regaddr += sizeof(uint32_t); + + /* Set up the search */ + + baseirq = g_baseirq[regndx]; + nirqs = g_nirqs[regndx]; /* Decode and dispatch each pending bit in the interrupt status * register. */ - for (bit = 0; regval != 0 && bit < 32; bit++) + for (bit = 0; regval != 0 && bit < nirqs; bit++) { /* Check if this interrupt is pending */ diff --git a/arch/xtensa/src/esp32/esp32_irq.c b/arch/xtensa/src/esp32/esp32_irq.c index d5cf4b552a4..010f05eb99d 100644 --- a/arch/xtensa/src/esp32/esp32_irq.c +++ b/arch/xtensa/src/esp32/esp32_irq.c @@ -48,10 +48,6 @@ #include "xtensa.h" -/**************************************************************************** - * Pre-processor Definitions - ****************************************************************************/ - /**************************************************************************** * Public Data ****************************************************************************/ @@ -62,8 +58,19 @@ * CURRENT_REGS for portability. */ +#ifdef CONFIG_SMP +/* For the case of architectures with multiple CPUs, then there must be one + * such value for each processor that can receive an interrupt. + */ + +volatile uint32_t *g_current_regs[CONFIG_SMP_NCPUS]; + +#else + volatile uint32_t *g_current_regs[1]; +#endif + /**************************************************************************** * Private Functions ****************************************************************************/ @@ -89,6 +96,20 @@ static void esp32_irq_dump(const char *msg, int irq) # define esp32_irq_dump(msg, irq) #endif +/**************************************************************************** + * Name: xtensa_disable_all + ****************************************************************************/ + +static inline void xtensa_disable_all(void) +{ + __asm__ __volatile__ + ( + "movi a2, 0\n" + "xsr a2, INTENABLE\n" + : : : "a2" + ); +} + /**************************************************************************** * Public Functions ****************************************************************************/ @@ -99,8 +120,18 @@ static void esp32_irq_dump(const char *msg, int irq) void xtensa_irq_initialize(void) { - /* Disable all interrupts */ -#warning Missing logic + int i; + + /* Disable all PRO CPU interrupts */ + + xtensa_disable_all(); + + /* Detach all peripheral sources PRO CPU interrupts */ + + for (i = 0; i < NR_PERIPHERALS) + { + esp32_detach_peripheral(0, i);; + } #if defined(CONFIG_STACK_COLORATION) && CONFIG_ARCH_INTERRUPTSTACK > 3 /* Colorize the interrupt stack for debug purposes */ @@ -108,75 +139,14 @@ void xtensa_irq_initialize(void) #warning Missing logic #endif - /* Set all interrupts (and exceptions) to the default priority */ -#warning Missing logic - - /* Attach all other processor exceptions (except reset and sys tick) */ + /* Attach all processor exceptions */ #warning Missing logic esp32_irq_dump("initial", NR_IRQS); #ifndef CONFIG_SUPPRESS_INTERRUPTS - /* And finally, enable interrupts */ up_irq_enable(); #endif } - -/**************************************************************************** - * Name: up_disable_irq - * - * Description: - * Disable the IRQ specified by 'irq' - * - ****************************************************************************/ - -void up_disable_irq(int irq) -{ -#warning Missing logic -} - -/**************************************************************************** - * Name: up_enable_irq - * - * Description: - * Enable the IRQ specified by 'irq' - * - ****************************************************************************/ - -void up_enable_irq(int irq) -{ -#warning Missing logic -} - -/**************************************************************************** - * Name: up_ack_irq - * - * Description: - * Acknowledge the IRQ - * - ****************************************************************************/ - -void up_ack_irq(int irq) -{ -} - -/**************************************************************************** - * Name: up_prioritize_irq - * - * Description: - * Set the priority of an IRQ. - * - * Since this API is not supported on all architectures, it should be - * avoided in common implementations where possible. - * - ****************************************************************************/ - -#ifdef CONFIG_ARCH_IRQPRIO -int up_prioritize_irq(int irq, int priority) -{ -#warning Missing logic - return OK; -} -#endif diff --git a/arch/xtensa/src/esp32/esp32_timerisr.c b/arch/xtensa/src/esp32/esp32_timerisr.c index b5a7871ae49..3d031dc776c 100644 --- a/arch/xtensa/src/esp32/esp32_timerisr.c +++ b/arch/xtensa/src/esp32/esp32_timerisr.c @@ -62,8 +62,7 @@ static uint32_t g_tick_divisor; ****************************************************************************/ /**************************************************************************** - * Function: xtensa_getcount, xtensa_getcompare, xtensa_setcompare, and - * xtensa_enable_timer + * Function: xtensa_getcount, xtensa_getcompare, and xtensa_setcompare * * Description: * Lower level operations on Xtensa special registers. @@ -108,22 +107,6 @@ static inline void xtensa_setcompare(uint32_t compare) ); } -/* Enable the timer interrupt. NOTE: This is non-atomic but safe in this - * context because this occurs early in the initialization sequence. - */ - -static inline void xtensa_enable_timer(void) -{ - __asm__ __volatile__ - ( - "movi a3, %0\n" - "rsr a2, INTENABLE\n" - "or a2, a2, a3\n" - "wsr a2, INTENABLE\n" - : : "I"(XT_TIMER_INTEN) : "a2", "a3" - ); -} - /**************************************************************************** * Function: esp32_timerisr * @@ -208,13 +191,15 @@ void xtensa_timer_initialize(void) count = xtensa_getcount(); xtensa_setcompare(count + divisor); + /* NOTE: Timer 0 is an internal interrupt source so we do not need to + * attach any peripheral ID to the dedicated CPU interrupt. + */ + /* Attach the timer interrupt vector */ (void)irq_attach(XTENSA_IRQ_TIMER0, (xcpt_t)esp32_timerisr); - /* Enable the timer interrupt at the device level. NOTE: It is un-necessary - * to call up_enable_irq() for timers. - */ + /* Enable the timer 0 CPU interrupt. */ - xtensa_enable_timer(); + up_enable_irq(ESP32_CPUINT_TIMER0); } diff --git a/configs/nucleo-f303re/src/Makefile b/configs/nucleo-f303re/src/Makefile index 7d81b2cbe1b..a4906030e79 100644 --- a/configs/nucleo-f303re/src/Makefile +++ b/configs/nucleo-f303re/src/Makefile @@ -62,6 +62,10 @@ ifeq ($(CONFIG_CAN),y) CSRCS += stm32_can.c endif +ifeq ($(CONFIG_DAC),y) +CSRCS += stm32_dac.c +endif + ifeq ($(CONFIG_PWM),y) CSRCS += stm32_pwm.c endif diff --git a/configs/nucleo-f303re/src/nucleo-f303re.h b/configs/nucleo-f303re/src/nucleo-f303re.h index 526bc7ee9a5..8d9d21d2273 100644 --- a/configs/nucleo-f303re/src/nucleo-f303re.h +++ b/configs/nucleo-f303re/src/nucleo-f303re.h @@ -69,6 +69,8 @@ #define GPIO_LED1 (GPIO_OUTPUT|GPIO_PUSHPULL|GPIO_SPEED_50MHz|\ GPIO_OUTPUT_CLEAR|GPIO_PORTA|GPIO_PIN5) +#define LED_DRIVER_PATH "/dev/userleds" + /* Button definitions *******************************************************/ /* The Nucleo F303RE supports two buttons; only one button is controllable * by software: @@ -153,4 +155,16 @@ void weak_function stm32_spidev_initialize(void); int stm32_timer_driver_setup(FAR const char *devpath, int timer); #endif +/**************************************************************************** + * Name: stm32_dac_setup + * + * Description: + * Configure DAC peripheral for the board. + * + ****************************************************************************/ + +#ifdef CONFIG_DAC +int stm32_dac_setup(void); +#endif + #endif /* __CONFIGS_NUCLEO_F303RE_SRC_NUCLEO_F303RE_H */ diff --git a/configs/nucleo-f303re/src/stm32_adc.c b/configs/nucleo-f303re/src/stm32_adc.c index 10871a82da6..2c2e0bed280 100644 --- a/configs/nucleo-f303re/src/stm32_adc.c +++ b/configs/nucleo-f303re/src/stm32_adc.c @@ -58,37 +58,66 @@ * Pre-processor Definitions ****************************************************************************/ +#if (defined(CONFIG_STM32_ADC1) && defined(CONFIG_STM32_ADC2)) || \ + (defined(CONFIG_STM32_ADC3) && defined(CONFIG_STM32_ADC4)) +# error "will not work with this combination of ADCs" +#endif + /* Configuration ************************************************************/ -#if defined(CONFIG_STM32_ADC1) && !defined(CONFIG_STM32_ADC2) && \ - !defined(CONFIG_STM32_ADC3) && !defined(CONFIG_STM32_ADC4) -# define ADC_PORT 1 -#elif defined(CONFIG_STM32_ADC2) && !defined(CONFIG_STM32_ADC1) && \ - !defined(CONFIG_STM32_ADC3) && !defined(CONFIG_STM32_ADC4) -# define ADC_PORT 2 -#elif defined(CONFIG_STM32_ADC3) && !defined(CONFIG_STM32_ADC1) && \ - !defined(CONFIG_STM32_ADC2) && !defined(CONFIG_STM32_ADC4) -# define ADC_PORT 3 -#elif defined(CONFIG_STM32_ADC4) && !defined(CONFIG_STM32_ADC1) && \ - !defined(CONFIG_STM32_ADC2) && !defined(CONFIG_STM32_ADC3) -# define ADC_PORT 4 -#else -# error "Choose only one of ADC1, ADC2, ADC3, ADC4" +/* 1 or 2 ADC devices (DEV1, DEV2) */ + +#if defined(CONFIG_STM32_ADC1) +# define DEV1_PORT 1 +#endif + +#if defined(CONFIG_STM32_ADC2) +# if defined(DEV1_PORT) +# define DEV2_PORT 2 +# else +# define DEV1_PORT 2 +# endif +#endif + +#if defined(CONFIG_STM32_ADC3) +# if defined(DEV2_PORT) +# error "Choose maximum two of ADC1, ADC2, ADC3, ADC4" +# else +# if defined(DEV1_PORT) +# define DEV2_PORT 3 +# else +# define DEV1_PORT 3 +# endif +# endif +#endif + +#if defined(CONFIG_STM32_ADC4) +# if defined(DEV2_PORT) +# error "Choose maximum two of ADC1, ADC2, ADC3, ADC4" +# else +# if defined(DEV1_PORT) +# define DEV2_PORT 4 +# else +# define DEV1_PORT 4 +# endif +# endif #endif /* The number of ADC channels in the conversion list */ +/* TODO DMA */ -#if defined(CONFIG_STM32_ADC1) && defined(ADC1_HAVE_DMA) -# define ADC_NCHANNELS 4 -#elif defined(CONFIG_STM32_ADC2) && defined(ADC2_HAVE_DMA) -# define ADC_NCHANNELS 3 -#elif defined(CONFIG_STM32_ADC3) && defined(ADC3_HAVE_DMA) -# define ADC_NCHANNELS 1 -#elif defined(CONFIG_STM32_ADC4) && defined(ADC4_HAVE_DMA) -# define ADC_NCHANNELS 1 +#if defined(ADC1_HAVE_DMA) +# error "ADC1 with DMA support is not fully implemented" #else -# define ADC_NCHANNELS 1 +# define ADC1_NCHANNELS 4 #endif +#if defined(ADC2_HAVE_DMA) +# error "ADC2 with DMA support is not fully implemented" +#else +# define ADC2_NCHANNELS 3 +#endif +#define ADC3_NCHANNELS 3 +#define ADC4_NCHANNELS 1 /**************************************************************************** * Private Function Prototypes @@ -98,88 +127,187 @@ * Private Data ****************************************************************************/ -#if defined(CONFIG_STM32_ADC1) +/* DEV 1 */ -/* Identifying number of each ADC channel */ +#if DEV1_PORT == 1 -static const uint8_t g_chanlist[ADC_NCHANNELS] = +#define DEV1_NCHANNELS ADC1_NCHANNELS + +/* Identifying number of each ADC channel (even if NCHANNELS is less ) */ + +static const uint8_t g_chanlist1[4] = { 1, -#ifdef ADC1_HAVE_DMA 2, 6, 7, -#endif }; /* Configurations of pins used by each ADC channel */ -static const uint32_t g_pinlist[ADC_NCHANNELS] = +static const uint32_t g_pinlist1[4] = { GPIO_ADC1_IN1, -#ifdef ADC1_HAVE_DMA GPIO_ADC1_IN2, GPIO_ADC1_IN6, - GPIO_ADC1_IN7, -#endif + GPIO_ADC1_IN7 }; -#elif defined(CONFIG_STM32_ADC2) +#elif DEV1_PORT == 2 + +#define DEV1_NCHANNELS ADC2_NCHANNELS /* Identifying number of each ADC channel */ -static const uint8_t g_chanlist[ADC_NCHANNELS] = +static const uint8_t g_chanlist1[3] = { 1, -#ifdef ADC2_HAVE_DMA - 6, - 7, -#endif + 3, + 4 }; /* Configurations of pins used by each ADC channel */ -static const uint32_t g_pinlist[ADC_NCHANNELS] = +static const uint32_t g_pinlist1[3] = { GPIO_ADC2_IN1, -#ifdef ADC2_HAVE_DMA - GPIO_ADC2_IN6, - GPIO_ADC2_IN7, + GPIO_ADC2_IN3, + GPIO_ADC2_IN4 +}; + +#elif DEV1_PORT == 3 + +#define DEV1_NCHANNELS ADC3_NCHANNELS + +/* Identifying number of each ADC channel */ + +static const uint8_t g_chanlist1[3] = +{ + 1, + 5, + 12 +}; + +/* Configurations of pins used by each ADC channel */ + +static const uint32_t g_pinlist1[3] = +{ + GPIO_ADC3_IN1, + GPIO_ADC3_IN5, + GPIO_ADC3_IN12 +}; + +#elif DEV1_PORT == 4 + +#define DEV1_NCHANNELS ADC4_NCHANNELS + +/* Identifying number of each ADC channel */ + +static const uint8_t g_chanlist1[1] = +{ + 3 +}; + +/* Configurations of pins used by each ADC channel */ + +static const uint32_t g_pinlist1[1] = +{ + GPIO_ADC4_IN3 +}; + #endif -}; -#elif defined(CONFIG_STM32_ADC3) +#ifdef DEV2_PORT -/* Identifying number of each ADC channel */ +/* DEV 2 */ -static const uint8_t g_chanlist[ADC_NCHANNELS] = +#if DEV2_PORT == 1 + +#define DEV2_NCHANNELS ADC1_NCHANNELS + +/* Identifying number of each ADC channel (even if NCHANNELS is less ) */ + +static const uint8_t g_chanlist2[4] = { - 12, + 1, + 2, + 6, + 7 }; /* Configurations of pins used by each ADC channel */ -static const uint32_t g_pinlist[ADC_NCHANNELS] = +static const uint32_t g_pinlist2[4] = { - GPIO_ADC3_IN12, + GPIO_ADC1_IN1, + GPIO_ADC1_IN2, + GPIO_ADC1_IN6, + GPIO_ADC1_IN7 }; -#elif defined(CONFIG_STM32_ADC4) +#elif DEV2_PORT == 2 + +#define DEV2_NCHANNELS ADC2_NCHANNELS /* Identifying number of each ADC channel */ -static const uint8_t g_chanlist[ADC_NCHANNELS] = +static const uint8_t g_chanlist2[3] = { + 1, 3, + 4 }; /* Configurations of pins used by each ADC channel */ -static const uint32_t g_pinlist[ADC_NCHANNELS] = +static const uint32_t g_pinlist2[3] = { - GPIO_ADC4_IN3, + GPIO_ADC2_IN1, + GPIO_ADC2_IN3, + GPIO_ADC2_IN4 }; +#elif DEV2_PORT == 3 + +#define DEV2_NCHANNELS ADC3_NCHANNELS + +/* Identifying number of each ADC channel */ + +static const uint8_t g_chanlist2[3] = +{ + 1, + 5, + 12 +}; + +/* Configurations of pins used by each ADC channel */ + +static const uint32_t g_pinlist2[3] = +{ + GPIO_ADC3_IN1, + GPIO_ADC3_IN5, + GPIO_ADC3_IN12 +}; + +#elif DEV2_PORT == 4 + +#define DEV2_NCHANNELS ADC4_NCHANNELS + +/* Identifying number of each ADC channel */ + +static const uint8_t g_chanlist2[1] = +{ + 3 +}; + +/* Configurations of pins used by each ADC channel */ + +static const uint32_t g_pinlist2[1] = +{ + GPIO_ADC4_IN3 +}; + +#endif #endif /**************************************************************************** @@ -208,21 +336,22 @@ int board_adc_setup(void) /* Check if we have already initialized */ - if (!initialized) - { + if (!initialized) { + + /* DEV1 */ /* Configure the pins as analog inputs for the selected channels */ - for (i = 0; i < ADC_NCHANNELS; i++) + for (i = 0; i < DEV1_NCHANNELS; i++) { - stm32_configgpio(g_pinlist[i]); + stm32_configgpio(g_pinlist1[i]); } /* Call stm32_adcinitialize() to get an instance of the ADC interface */ - adc = stm32_adcinitialize(ADC_PORT, g_chanlist, ADC_NCHANNELS); + adc = stm32_adcinitialize(DEV1_PORT, g_chanlist1, DEV1_NCHANNELS); if (adc == NULL) { - aerr("ERROR: Failed to get ADC interface\n"); + aerr("ERROR: Failed to get ADC interface 1\n"); return -ENODEV; } @@ -231,10 +360,39 @@ int board_adc_setup(void) ret = adc_register("/dev/adc0", adc); if (ret < 0) { - aerr("ERROR: adc_register failed: %d\n", ret); + aerr("ERROR: adc_register /dev/adc0 failed: %d\n", ret); return ret; } +#ifdef DEV2_PORT + + /* DEV2 */ + /* Configure the pins as analog inputs for the selected channels */ + + for (i = 0; i < DEV2_NCHANNELS; i++) + { + stm32_configgpio(g_pinlist2[i]); + } + + /* Call stm32_adcinitialize() to get an instance of the ADC interface */ + + adc = stm32_adcinitialize(DEV2_PORT, g_chanlist2, DEV2_NCHANNELS); + if (adc == NULL) + { + aerr("ERROR: Failed to get ADC interface 2\n"); + return -ENODEV; + } + + /* Register the ADC driver at "/dev/adc1" */ + + ret = adc_register("/dev/adc1", adc); + if (ret < 0) + { + aerr("ERROR: adc_register /dev/adc1 failed: %d\n", ret); + return ret; + } +#endif + /* Now we are initialized */ initialized = true; diff --git a/configs/nucleo-f303re/src/stm32_appinitialize.c b/configs/nucleo-f303re/src/stm32_appinitialize.c index d79c7d50412..3ce7e293bd0 100644 --- a/configs/nucleo-f303re/src/stm32_appinitialize.c +++ b/configs/nucleo-f303re/src/stm32_appinitialize.c @@ -42,8 +42,12 @@ #include #include +#include #include +#include + +#include "nucleo-f303re.h" /**************************************************************************** * Pre-processor Definitions @@ -80,5 +84,31 @@ int board_app_initialize(uintptr_t arg) { + int ret; + +#if !defined(CONFIG_ARCH_LEDS) && defined(CONFIG_USERLED_LOWER) + /* Register the LED driver */ + + ret = userled_lower_initialize(LED_DRIVER_PATH); + if (ret < 0) + { + syslog(LOG_ERR, "ERROR: userled_lower_initialize() failed: %d\n", ret); + return ret; + } +#endif + + /* Contrairement à l'ADC, il n'y a pas de BOARDIOC_DAC_SETUP spécifique. Il + * faut le faire ici + */ + +#if defined(CONFIG_DAC) + ret = board_dac_setup(); + if (ret < 0) + { + syslog(LOG_ERR, "ERROR: board_dac_setup() failed: %d\n", ret); + return ret; + } +#endif + return OK; } diff --git a/configs/stm32f103-minimum/include/board.h b/configs/stm32f103-minimum/include/board.h index 8e983ae3516..1dc84378c78 100644 --- a/configs/stm32f103-minimum/include/board.h +++ b/configs/stm32f103-minimum/include/board.h @@ -114,12 +114,12 @@ * Note: TIM1,8 are on APB2, others on APB1 */ #define BOARD_TIM1_FREQUENCY STM32_HCLK_FREQUENCY -#define BOARD_TIM2_FREQUENCY STM32_HCLK_FREQUENCY -#define BOARD_TIM3_FREQUENCY STM32_HCLK_FREQUENCY -#define BOARD_TIM4_FREQUENCY STM32_HCLK_FREQUENCY -#define BOARD_TIM5_FREQUENCY STM32_HCLK_FREQUENCY -#define BOARD_TIM6_FREQUENCY STM32_HCLK_FREQUENCY -#define BOARD_TIM7_FREQUENCY STM32_HCLK_FREQUENCY +#define BOARD_TIM2_FREQUENCY STM32_PCLK1_FREQUENCY +#define BOARD_TIM3_FREQUENCY STM32_PCLK1_FREQUENCY +#define BOARD_TIM4_FREQUENCY STM32_PCLK1_FREQUENCY +#define BOARD_TIM5_FREQUENCY STM32_PCLK1_FREQUENCY +#define BOARD_TIM6_FREQUENCY STM32_PCLK1_FREQUENCY +#define BOARD_TIM7_FREQUENCY STM32_PCLK1_FREQUENCY #define BOARD_TIM8_FREQUENCY STM32_HCLK_FREQUENCY /* SDIO dividers. Note that slower clocking is required when DMA is disabled