From 794ecbfd8625906b6a83bc3e3fa830f29b0ce89f Mon Sep 17 00:00:00 2001 From: Oleg Evseev Date: Mon, 19 Jun 2017 19:45:35 +0300 Subject: [PATCH 1/8] Use struct instead of pointer to the struct as sizeof argument in memset in usbmsc.c Otherwise it leads to error: argument to 'sizeof' in 'memset' call is the same pointer type 'struct usbmsc_lun_s *' as the destination --- drivers/usbdev/usbmsc.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/usbdev/usbmsc.c b/drivers/usbdev/usbmsc.c index b3eb1d1c9a..f7e1e58a4c 100644 --- a/drivers/usbdev/usbmsc.c +++ b/drivers/usbdev/usbmsc.c @@ -906,7 +906,7 @@ static void usbmsc_lununinitialize(struct usbmsc_lun_s *lun) (void)close_blockdriver(lun->inode); } - memset(lun, 0, sizeof(struct usbmsc_lun_s *)); + memset(lun, 0, sizeof(struct usbmsc_lun_s)); } /**************************************************************************** @@ -1492,7 +1492,7 @@ int usbmsc_bindlun(FAR void *handle, FAR const char *drvrpath, /* Initialize the LUN structure */ - memset(lun, 0, sizeof(struct usbmsc_lun_s *)); + memset(lun, 0, sizeof(struct usbmsc_lun_s)); /* Allocate an I/O buffer big enough to hold one hardware sector. SCSI commands * are processed one at a time so all LUNs may share a single I/O buffer. The From 2eb782961f354b029aff045a62462118d7fd78c4 Mon Sep 17 00:00:00 2001 From: Pekka Ervasti Date: Tue, 20 Jun 2017 07:59:27 -0600 Subject: [PATCH 2/8] STM32 L4: Set I2C SDA and SCL pins to open drain mode. --- .../arm/src/stm32l4/chip/stm32l4x3xx_pinmap.h | 40 +++++++------- .../arm/src/stm32l4/chip/stm32l4x5xx_pinmap.h | 32 ++++++------ .../arm/src/stm32l4/chip/stm32l4x6xx_pinmap.h | 52 +++++++++---------- 3 files changed, 62 insertions(+), 62 deletions(-) diff --git a/arch/arm/src/stm32l4/chip/stm32l4x3xx_pinmap.h b/arch/arm/src/stm32l4/chip/stm32l4x3xx_pinmap.h index bf92bcf54b..40f4076cd8 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4x3xx_pinmap.h +++ b/arch/arm/src/stm32l4/chip/stm32l4x3xx_pinmap.h @@ -160,34 +160,34 @@ /* I2C */ -#define GPIO_I2C1_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN7) -#define GPIO_I2C1_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN9) -#define GPIO_I2C1_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN6) -#define GPIO_I2C1_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN8) +#define GPIO_I2C1_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN7) +#define GPIO_I2C1_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN9) +#define GPIO_I2C1_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN6) +#define GPIO_I2C1_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN8) #define GPIO_I2C1_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTA|GPIO_PIN1) #define GPIO_I2C1_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTA|GPIO_PIN14) #define GPIO_I2C1_SMBA_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN5) -#define GPIO_I2C2_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN11) -#define GPIO_I2C2_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN14) -#define GPIO_I2C2_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN10) -#define GPIO_I2C2_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN13) +#define GPIO_I2C2_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN11) +#define GPIO_I2C2_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN14) +#define GPIO_I2C2_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN10) +#define GPIO_I2C2_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN13) #define GPIO_I2C2_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN12) -#define GPIO_I2C3_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN4) -#define GPIO_I2C3_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTC|GPIO_PIN1) -#define GPIO_I2C3_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTA|GPIO_PIN7) -#define GPIO_I2C3_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTC|GPIO_PIN0) +#define GPIO_I2C3_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN4) +#define GPIO_I2C3_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN1) +#define GPIO_I2C3_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTA|GPIO_PIN7) +#define GPIO_I2C3_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN0) #define GPIO_I2C3_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN2) -#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF5 |GPIO_PORTB|GPIO_PIN7) -#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF3 |GPIO_PORTB|GPIO_PIN11) -#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF2 |GPIO_PORTC|GPIO_PIN1) -#define GPIO_I2C4_SDA_4 (GPIO_ALT|GPIO_AF4 |GPIO_PORTD|GPIO_PIN13) -#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF5 |GPIO_PORTB|GPIO_PIN6) -#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF3 |GPIO_PORTB|GPIO_PIN10) -#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF2 |GPIO_PORTC|GPIO_PIN0) -#define GPIO_I2C4_SCL_4 (GPIO_ALT|GPIO_AF4 |GPIO_PORTD|GPIO_PIN12) +#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF5 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN7) +#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF3 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN11) +#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF2 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN1) +#define GPIO_I2C4_SDA_4 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN13) +#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF5 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN6) +#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF3 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN10) +#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF2 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN0) +#define GPIO_I2C4_SCL_4 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN12) #define GPIO_I2C4_SMBA_1 (GPIO_ALT|GPIO_AF5 |GPIO_PORTA|GPIO_PIN14) #define GPIO_I2C4_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTD|GPIO_PIN11) diff --git a/arch/arm/src/stm32l4/chip/stm32l4x5xx_pinmap.h b/arch/arm/src/stm32l4/chip/stm32l4x5xx_pinmap.h index d6f6d1cf50..0a20355ca9 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4x5xx_pinmap.h +++ b/arch/arm/src/stm32l4/chip/stm32l4x5xx_pinmap.h @@ -257,28 +257,28 @@ * I2C1-3 that are not defined here. */ -#define GPIO_I2C1_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN7) -#define GPIO_I2C1_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN9) -#define GPIO_I2C1_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN13) -#define GPIO_I2C1_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN6) -#define GPIO_I2C1_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN8) -#define GPIO_I2C1_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN14) +#define GPIO_I2C1_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN7) +#define GPIO_I2C1_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN9) +#define GPIO_I2C1_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN13) +#define GPIO_I2C1_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN6) +#define GPIO_I2C1_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN8) +#define GPIO_I2C1_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN14) #define GPIO_I2C1_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN5) #define GPIO_I2C1_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN15) -#define GPIO_I2C2_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN11) -#define GPIO_I2C2_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN14) -#define GPIO_I2C2_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN0) -#define GPIO_I2C2_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN10) -#define GPIO_I2C2_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN13) -#define GPIO_I2C2_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN1) +#define GPIO_I2C2_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN11) +#define GPIO_I2C2_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN14) +#define GPIO_I2C2_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN0) +#define GPIO_I2C2_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN10) +#define GPIO_I2C2_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN13) +#define GPIO_I2C2_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN1) #define GPIO_I2C2_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN12) #define GPIO_I2C2_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN2) -#define GPIO_I2C3_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTC|GPIO_PIN1) -#define GPIO_I2C3_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN8) -#define GPIO_I2C3_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTC|GPIO_PIN0) -#define GPIO_I2C3_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN7) +#define GPIO_I2C3_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN1) +#define GPIO_I2C3_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN8) +#define GPIO_I2C3_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN0) +#define GPIO_I2C3_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN7) #define GPIO_I2C3_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN2) #define GPIO_I2C3_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN6) diff --git a/arch/arm/src/stm32l4/chip/stm32l4x6xx_pinmap.h b/arch/arm/src/stm32l4/chip/stm32l4x6xx_pinmap.h index c149e1dd01..64ae763081 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4x6xx_pinmap.h +++ b/arch/arm/src/stm32l4/chip/stm32l4x6xx_pinmap.h @@ -299,41 +299,41 @@ * I2C1-3 that are not defined here. */ -#define GPIO_I2C1_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN7) -#define GPIO_I2C1_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN9) -#define GPIO_I2C1_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN13) -#define GPIO_I2C1_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN6) -#define GPIO_I2C1_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN8) -#define GPIO_I2C1_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN14) +#define GPIO_I2C1_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN7) +#define GPIO_I2C1_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN9) +#define GPIO_I2C1_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN13) +#define GPIO_I2C1_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN6) +#define GPIO_I2C1_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN8) +#define GPIO_I2C1_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN14) #define GPIO_I2C1_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN5) #define GPIO_I2C1_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN15) -#define GPIO_I2C2_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN11) -#define GPIO_I2C2_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN14) -#define GPIO_I2C2_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN0) -#define GPIO_I2C2_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN10) -#define GPIO_I2C2_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN13) -#define GPIO_I2C2_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN1) +#define GPIO_I2C2_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN11) +#define GPIO_I2C2_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN14) +#define GPIO_I2C2_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN0) +#define GPIO_I2C2_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN10) +#define GPIO_I2C2_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN13) +#define GPIO_I2C2_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN1) #define GPIO_I2C2_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN12) #define GPIO_I2C2_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN2) -#define GPIO_I2C3_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTC|GPIO_PIN1) -#define GPIO_I2C3_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN8) -#define GPIO_I2C3_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTC|GPIO_PIN0) -#define GPIO_I2C3_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN7) +#define GPIO_I2C3_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN1) +#define GPIO_I2C3_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN8) +#define GPIO_I2C3_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN0) +#define GPIO_I2C3_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTG|GPIO_PIN7) #define GPIO_I2C3_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_PORTB|GPIO_PIN2) #define GPIO_I2C3_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTG|GPIO_PIN6) -#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF5 |GPIO_PORTB|GPIO_PIN7) -#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF3 |GPIO_PORTB|GPIO_PIN11) -#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF2 |GPIO_PORTC|GPIO_PIN1) -#define GPIO_I2C4_SDA_4 (GPIO_ALT|GPIO_AF4 |GPIO_PORTD|GPIO_PIN13) -#define GPIO_I2C4_SDA_5 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN15) -#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF5 |GPIO_PORTB|GPIO_PIN6) -#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF3 |GPIO_PORTB|GPIO_PIN10) -#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF2 |GPIO_PORTC|GPIO_PIN0) -#define GPIO_I2C4_SCL_4 (GPIO_ALT|GPIO_AF4 |GPIO_PORTD|GPIO_PIN12) -#define GPIO_I2C4_SCL_5 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN14) +#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF5 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN7) +#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF3 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN11) +#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF2 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN1) +#define GPIO_I2C4_SDA_4 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN13) +#define GPIO_I2C4_SDA_5 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN15) +#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF5 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN6) +#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF3 |GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN10) +#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF2 |GPIO_OPENDRAIN|GPIO_PORTC|GPIO_PIN0) +#define GPIO_I2C4_SCL_4 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN12) +#define GPIO_I2C4_SCL_5 (GPIO_ALT|GPIO_AF4 |GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN14) #define GPIO_I2C4_SMBA_1 (GPIO_ALT|GPIO_AF5 |GPIO_PORTA|GPIO_PIN14) #define GPIO_I2C4_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_PORTD|GPIO_PIN11) #define GPIO_I2C4_SMBA_3 (GPIO_ALT|GPIO_AF4 |GPIO_PORTF|GPIO_PIN13) From 47ad81b3e54a5ebc08d56f5a449ef1110add1222 Mon Sep 17 00:00:00 2001 From: Gregory Nutt Date: Tue, 20 Jun 2017 08:02:42 -0600 Subject: [PATCH 3/8] Trivial spelling fix --- arch/arm/src/stm32/stm32_otgfsdev.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm/src/stm32/stm32_otgfsdev.c b/arch/arm/src/stm32/stm32_otgfsdev.c index 4d23392912..90b5b97ace 100644 --- a/arch/arm/src/stm32/stm32_otgfsdev.c +++ b/arch/arm/src/stm32/stm32_otgfsdev.c @@ -299,7 +299,7 @@ #define EP0 (0) -/* The set of all enpoints available to the class implementation (1-3) */ +/* The set of all endpoints available to the class implementation (1-3) */ #define STM32_EP_AVAILABLE (0x0e) /* All available endpoints */ From 2c548a4e58ac07579f309212b1315106bc708130 Mon Sep 17 00:00:00 2001 From: Juha Niskanen Date: Tue, 20 Jun 2017 08:04:09 -0600 Subject: [PATCH 4/8] STM32 L4: I2C4 was writing to wrong RCC registers --- arch/arm/src/stm32l4/chip/stm32l4_i2c.h | 2 +- arch/arm/src/stm32l4/chip/stm32l4x3xx_rcc.h | 2 +- arch/arm/src/stm32l4/chip/stm32l4x5xx_rcc.h | 2 +- arch/arm/src/stm32l4/chip/stm32l4x6xx_rcc.h | 2 +- arch/arm/src/stm32l4/stm32l4_i2c.c | 30 +++++++++++++++++---- 5 files changed, 29 insertions(+), 9 deletions(-) diff --git a/arch/arm/src/stm32l4/chip/stm32l4_i2c.h b/arch/arm/src/stm32l4/chip/stm32l4_i2c.h index a28dad8728..398073514a 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4_i2c.h +++ b/arch/arm/src/stm32l4/chip/stm32l4_i2c.h @@ -259,5 +259,5 @@ #define I2C_TXDR_MASK (0xff) -#endif /* __ARCH_ARM_SRC_STM32L4_CHIP_STM32F30XXX_I2C_H */ +#endif /* __ARCH_ARM_SRC_STM32L4_CHIP_STM32L4_I2C_H */ diff --git a/arch/arm/src/stm32l4/chip/stm32l4x3xx_rcc.h b/arch/arm/src/stm32l4/chip/stm32l4x3xx_rcc.h index f05fec85cc..4f6af7e206 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4x3xx_rcc.h +++ b/arch/arm/src/stm32l4/chip/stm32l4x3xx_rcc.h @@ -109,7 +109,7 @@ #define STM32L4_RCC_APB1ENR2 (STM32L4_RCC_BASE+STM32L4_RCC_APB1ENR2_OFFSET) #define STM32L4_RCC_APB2ENR (STM32L4_RCC_BASE+STM32L4_RCC_APB2ENR_OFFSET) #define STM32L4_RCC_AHB1SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB1SMENR_OFFSET) -#define STM32L4_RCC_AHB2SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB2SMENR) +#define STM32L4_RCC_AHB2SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB2SMENR_OFFSET) #define STM32L4_RCC_AHB3SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB3SMENR_OFFSET) #define STM32L4_RCC_APB1SMENR1 (STM32L4_RCC_BASE+STM32L4_RCC_APB1SMENR1_OFFSET) #define STM32L4_RCC_APB1SMENR2 (STM32L4_RCC_BASE+STM32L4_RCC_APB1SMENR2_OFFSET) diff --git a/arch/arm/src/stm32l4/chip/stm32l4x5xx_rcc.h b/arch/arm/src/stm32l4/chip/stm32l4x5xx_rcc.h index 8177609e26..ee49a2720b 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4x5xx_rcc.h +++ b/arch/arm/src/stm32l4/chip/stm32l4x5xx_rcc.h @@ -107,7 +107,7 @@ #define STM32L4_RCC_APB1ENR2 (STM32L4_RCC_BASE+STM32L4_RCC_APB1ENR2_OFFSET) #define STM32L4_RCC_APB2ENR (STM32L4_RCC_BASE+STM32L4_RCC_APB2ENR_OFFSET) #define STM32L4_RCC_AHB1SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB1SMENR_OFFSET) -#define STM32L4_RCC_AHB2SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB2SMENR) +#define STM32L4_RCC_AHB2SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB2SMENR_OFFSET) #define STM32L4_RCC_AHB3SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB3SMENR_OFFSET) #define STM32L4_RCC_APB1SMENR1 (STM32L4_RCC_BASE+STM32L4_RCC_APB1SMENR1_OFFSET) #define STM32L4_RCC_APB1SMENR2 (STM32L4_RCC_BASE+STM32L4_RCC_APB1SMENR2_OFFSET) diff --git a/arch/arm/src/stm32l4/chip/stm32l4x6xx_rcc.h b/arch/arm/src/stm32l4/chip/stm32l4x6xx_rcc.h index 7a8f97a3b2..237c34a548 100644 --- a/arch/arm/src/stm32l4/chip/stm32l4x6xx_rcc.h +++ b/arch/arm/src/stm32l4/chip/stm32l4x6xx_rcc.h @@ -109,7 +109,7 @@ #define STM32L4_RCC_APB1ENR2 (STM32L4_RCC_BASE+STM32L4_RCC_APB1ENR2_OFFSET) #define STM32L4_RCC_APB2ENR (STM32L4_RCC_BASE+STM32L4_RCC_APB2ENR_OFFSET) #define STM32L4_RCC_AHB1SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB1SMENR_OFFSET) -#define STM32L4_RCC_AHB2SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB2SMENR) +#define STM32L4_RCC_AHB2SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB2SMENR_OFFSET) #define STM32L4_RCC_AHB3SMENR (STM32L4_RCC_BASE+STM32L4_RCC_AHB3SMENR_OFFSET) #define STM32L4_RCC_APB1SMENR1 (STM32L4_RCC_BASE+STM32L4_RCC_APB1SMENR1_OFFSET) #define STM32L4_RCC_APB1SMENR2 (STM32L4_RCC_BASE+STM32L4_RCC_APB1SMENR2_OFFSET) diff --git a/arch/arm/src/stm32l4/stm32l4_i2c.c b/arch/arm/src/stm32l4/stm32l4_i2c.c index 892cde5f69..47597c875b 100644 --- a/arch/arm/src/stm32l4/stm32l4_i2c.c +++ b/arch/arm/src/stm32l4/stm32l4_i2c.c @@ -1273,7 +1273,7 @@ static inline void stm32l4_i2c_sendstop(FAR struct stm32l4_i2c_priv_s *priv) * Name: stm32l4_i2c_getstatus * * Description: - * Get 32-bit status (SR1 and SR2 combined) + * Get 32-bit status (ISR register) * ************************************************************************************/ @@ -1556,9 +1556,20 @@ static int stm32l4_i2c_init(FAR struct stm32l4_i2c_priv_s *priv) /* Enable power and reset the peripheral */ - modifyreg32(STM32L4_RCC_APB1ENR1, 0, priv->config->clk_bit); - modifyreg32(STM32L4_RCC_APB1RSTR1, 0, priv->config->reset_bit); - modifyreg32(STM32L4_RCC_APB1RSTR1, priv->config->reset_bit, 0); +#ifdef CONFIG_STM32L4_I2C4 + if (priv->config->base == STM32L4_I2C4_BASE) + { + modifyreg32(STM32L4_RCC_APB1ENR2, 0, priv->config->clk_bit); + modifyreg32(STM32L4_RCC_APB1RSTR2, 0, priv->config->reset_bit); + modifyreg32(STM32L4_RCC_APB1RSTR2, priv->config->reset_bit, 0); + } + else +#endif + { + modifyreg32(STM32L4_RCC_APB1ENR1, 0, priv->config->clk_bit); + modifyreg32(STM32L4_RCC_APB1RSTR1, 0, priv->config->reset_bit); + modifyreg32(STM32L4_RCC_APB1RSTR1, priv->config->reset_bit, 0); + } /* Configure pins */ @@ -1631,7 +1642,16 @@ static int stm32l4_i2c_deinit(FAR struct stm32l4_i2c_priv_s *priv) /* Disable clocking */ - modifyreg32(STM32L4_RCC_APB1ENR1, priv->config->clk_bit, 0); +#ifdef CONFIG_STM32L4_I2C4 + if (priv->config->base == STM32L4_I2C4_BASE) + { + modifyreg32(STM32L4_RCC_APB1ENR2, priv->config->clk_bit, 0); + } + else +#endif + { + modifyreg32(STM32L4_RCC_APB1ENR1, priv->config->clk_bit, 0); + } return OK; } From 326ab01a91e46d661045484769bf64f8b55cb33c Mon Sep 17 00:00:00 2001 From: Juha Niskanen Date: Tue, 20 Jun 2017 08:06:30 -0600 Subject: [PATCH 5/8] STM32 F7: Set I2C4 SDA and SCL pins to open drain mode --- .../src/stm32f7/chip/stm32f74xx75xx_pinmap.h | 12 ++++++------ .../src/stm32f7/chip/stm32f76xx77xx_pinmap.h | 18 +++++++++--------- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/arch/arm/src/stm32f7/chip/stm32f74xx75xx_pinmap.h b/arch/arm/src/stm32f7/chip/stm32f74xx75xx_pinmap.h index efc3b1c3d5..aaa3875ff2 100644 --- a/arch/arm/src/stm32f7/chip/stm32f74xx75xx_pinmap.h +++ b/arch/arm/src/stm32f7/chip/stm32f74xx75xx_pinmap.h @@ -552,12 +552,12 @@ #define GPIO_I2C3_SMBA_1 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN9) #define GPIO_I2C3_SMBA_2 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN9) -#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN12) -#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN14) -#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN11) -#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN13) -#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN15) -#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN12) +#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN12) +#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN14) +#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTH|GPIO_PIN11) +#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN13) +#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN15) +#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTH|GPIO_PIN12) #define GPIO_I2C4_SMBA_1 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN11) #define GPIO_I2C4_SMBA_2 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN13) #define GPIO_I2C4_SMBA_3 (GPIO_ALT|GPIO_AF4|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN10) diff --git a/arch/arm/src/stm32f7/chip/stm32f76xx77xx_pinmap.h b/arch/arm/src/stm32f7/chip/stm32f76xx77xx_pinmap.h index c5d1b50a16..e951a8f904 100644 --- a/arch/arm/src/stm32f7/chip/stm32f76xx77xx_pinmap.h +++ b/arch/arm/src/stm32f7/chip/stm32f76xx77xx_pinmap.h @@ -622,15 +622,15 @@ #define GPIO_I2C3_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN9) #define GPIO_I2C3_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN9) -#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN12) -#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN14) -#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN11) -#define GPIO_I2C4_SCL_4 (GPIO_ALT|GPIO_AF11|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN6) -#define GPIO_I2C4_SCL_5 (GPIO_ALT|GPIO_AF1 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN8) -#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN13) -#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN15) -#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN12) -#define GPIO_I2C4_SDA_4 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN9) +#define GPIO_I2C4_SCL_1 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN12) +#define GPIO_I2C4_SCL_2 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN14) +#define GPIO_I2C4_SCL_3 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTH|GPIO_PIN11) +#define GPIO_I2C4_SCL_4 (GPIO_ALT|GPIO_AF11|GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN6) +#define GPIO_I2C4_SCL_5 (GPIO_ALT|GPIO_AF1 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN8) +#define GPIO_I2C4_SDA_1 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTD|GPIO_PIN13) +#define GPIO_I2C4_SDA_2 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTF|GPIO_PIN15) +#define GPIO_I2C4_SDA_3 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTH|GPIO_PIN12) +#define GPIO_I2C4_SDA_4 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_OPENDRAIN|GPIO_PORTB|GPIO_PIN9) #define GPIO_I2C4_SMBA_1 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN11) #define GPIO_I2C4_SMBA_2 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN13) #define GPIO_I2C4_SMBA_3 (GPIO_ALT|GPIO_AF4 |GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN10) From 0bf4893b2cfda701bc221ef0efcb4f399ba65206 Mon Sep 17 00:00:00 2001 From: Sebastien Lorquet Date: Tue, 20 Jun 2017 11:56:54 -0600 Subject: [PATCH 6/8] STM32: Allow clock frequencies > 168 Mhz on stm32f427/429. We need to enable the power overdrive for this case. This patch allows the required bits to be set in proper sequence. It also modifies the local register access operations to allow more than 16-bit registers. --- arch/arm/src/stm32/stm32_pwr.c | 52 ++++++++++++++++++++++++++++++---- arch/arm/src/stm32/stm32_pwr.h | 14 +++++++++ 2 files changed, 60 insertions(+), 6 deletions(-) diff --git a/arch/arm/src/stm32/stm32_pwr.c b/arch/arm/src/stm32/stm32_pwr.c index b2aee60177..2b0ed2a14c 100644 --- a/arch/arm/src/stm32/stm32_pwr.c +++ b/arch/arm/src/stm32/stm32_pwr.c @@ -64,19 +64,20 @@ static uint16_t g_bkp_writable_counter = 0; * Private Functions ************************************************************************************/ -static inline uint16_t stm32_pwr_getreg(uint8_t offset) +static inline uint32_t stm32_pwr_getreg(uint8_t offset) { - return (uint16_t)getreg32(STM32_PWR_BASE + (uint32_t)offset); + return getreg32(STM32_PWR_BASE + (uint32_t)offset); } -static inline void stm32_pwr_putreg(uint8_t offset, uint16_t value) +static inline void stm32_pwr_putreg(uint8_t offset, uint32_t value) { - putreg32((uint32_t)value, STM32_PWR_BASE + (uint32_t)offset); + putreg32(value, STM32_PWR_BASE + (uint32_t)offset); } -static inline void stm32_pwr_modifyreg(uint8_t offset, uint16_t clearbits, uint16_t setbits) +static inline void stm32_pwr_modifyreg(uint8_t offset, uint32_t clearbits, + uint32_t setbits) { - modifyreg32(STM32_PWR_BASE + (uint32_t)offset, (uint32_t)clearbits, (uint32_t)setbits); + modifyreg32(STM32_PWR_BASE + (uint32_t)offset, clearbits, setbits); } /************************************************************************************ @@ -372,4 +373,43 @@ void stm32_pwr_disablepvd(void) #endif /* CONFIG_STM32_ENERGYLITE */ +/************************************************************************************ + * Name: stm32_pwr_enableoverdrive + * + * Description: + * Enable or disable the overdrive mode, allowing clock rates up to 180 MHz. + * If not enabled, the max allowed frequency is 168 MHz. + * + ************************************************************************************/ + +#if defined(CONFIG_STM32_STM32F427) || defined(CONFIG_STM32_STM32F429) || \ + defined(CONFIG_STM32_STM32F446) || defined(CONFIG_STM32_STM32F469) +void stm32_pwr_enableoverdrive(bool state) +{ + + /* Switch overdrive state */ + + if (state) + { + stm32_pwr_modifyreg(STM32_PWR_CR_OFFSET, 0, PWR_CR_ODEN); + } + else + { + stm32_pwr_modifyreg(STM32_PWR_CR_OFFSET, PWR_CR_ODEN, 0); + } + + /* Wait for overdrive ready */ + + while ((stm32_pwr_getreg(STM32_PWR_CSR_OFFSET) & PWR_CSR_ODRDY) == 0); + + /* Set ODSWEN to switch to this new state*/ + + stm32_pwr_modifyreg(STM32_PWR_CR_OFFSET, 0, PWR_CR_ODSWEN); + + /* Wait for completion */ + + while ((stm32_pwr_getreg(STM32_PWR_CSR_OFFSET) & PWR_CSR_ODSWRDY) == 0); +} +#endif + #endif /* CONFIG_STM32_PWR */ diff --git a/arch/arm/src/stm32/stm32_pwr.h b/arch/arm/src/stm32/stm32_pwr.h index ab33eb9b2c..19af928f14 100644 --- a/arch/arm/src/stm32/stm32_pwr.h +++ b/arch/arm/src/stm32/stm32_pwr.h @@ -215,6 +215,20 @@ void stm32_pwr_disablepvd(void); #endif /* CONFIG_STM32_ENERGYLITE */ +/************************************************************************************ + * Name: stm32_pwr_enableoverdrive + * + * Description: + * Enable or disable the overdrive mode, allowing clock rates up to 180 MHz. + * If not enabled, the max allowed frequency is 168 MHz. + * + ************************************************************************************/ + +#if defined(CONFIG_STM32_STM32F427) || defined(CONFIG_STM32_STM32F429) || \ + defined(CONFIG_STM32_STM32F446) || defined(CONFIG_STM32_STM32F469) +void stm32_pwr_enableoverdrive(bool state); +#endif + #undef EXTERN #if defined(__cplusplus) } From 9e0f583774d4df2a46f2b132bbd535090a8b5d80 Mon Sep 17 00:00:00 2001 From: David Sidrane Date: Tue, 20 Jun 2017 08:34:12 -1000 Subject: [PATCH 7/8] Kinetis:I2C driver added I2C3, reference counting and reset Refactored the driver to support reference counting and reset added I2C3 --- arch/arm/src/kinetis/kinetis_i2c.c | 612 ++++++++++++++++++++++------- 1 file changed, 463 insertions(+), 149 deletions(-) diff --git a/arch/arm/src/kinetis/kinetis_i2c.c b/arch/arm/src/kinetis/kinetis_i2c.c index 6350b18f34..50ebd69597 100644 --- a/arch/arm/src/kinetis/kinetis_i2c.c +++ b/arch/arm/src/kinetis/kinetis_i2c.c @@ -1,8 +1,8 @@ /**************************************************************************** - * arch/arm/src/kinetis/kinetis_i2c.c * * Copyright (C) 2016-2017 Gregory Nutt. All rights reserved. - * Author: Matias v01d + * Authors: Matias v01d + * David Sidrane * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -68,7 +68,7 @@ #include "kinetis_i2c.h" #if defined(CONFIG_KINETIS_I2C0) || defined(CONFIG_KINETIS_I2C1) || \ - defined(CONFIG_KINETIS_I2C2) + defined(CONFIG_KINETIS_I2C2) || defined(CONFIG_KINETIS_I2C3) /**************************************************************************** * Pre-processor Definitions @@ -83,6 +83,12 @@ #define STATE_TIMEOUT 2 #define STATE_NAK 3 +#define MKI2C_OUTPUT(p) (((p) & (_PIN_PORT_MASK | _PIN_MASK)) | \ + GPIO_OPENDRAIN | GPIO_OUTPUT_ONE) + +#define MKI2C_INPUT(p) (((p) & (_PIN_PORT_MASK | _PIN_MASK)) | \ + PIN_ANALOG) + /* TODO: * - revisar tamanio de todos los registros (getreg/putreg) */ @@ -91,18 +97,29 @@ * Private Types ****************************************************************************/ +/* I2C Device hardware configuration */ + +struct kinetis_i2c_config_s +{ + uint32_t base; /* I2C base address */ + uint32_t clk_reg; /* Clock Register */ + uint32_t clk_bit; /* Clock enable bit */ + uint32_t scl_pin; /* GPIO configuration for SCL as SCL */ + uint32_t sda_pin; /* GPIO configuration for SDA as SDA */ + uint16_t irqid; /* IRQ for this device */ +}; + /* I2C device state structure */ struct kinetis_i2cdev_s { struct i2c_master_s dev; /* Generic I2C device */ - uintptr_t base; /* Base address of registers */ - uint32_t basefreq; /* Branch frequency */ + const struct kinetis_i2c_config_s *config; /* Port configuration */ uint32_t frequency; /* Current I2C frequency */ - uint16_t irqid; /* IRQ for this device */ uint16_t nmsg; /* Number of transfer remaining */ uint16_t wrcnt; /* number of bytes sent to tx fifo */ uint16_t rdcnt; /* number of bytes read from rx fifo */ + int refs; /* Reference count */ volatile uint8_t state; /* State of state machine */ bool restart; /* Should next transfer restart or not */ sem_t mutex; /* Only one thread can access at a time */ @@ -123,8 +140,22 @@ static uint8_t kinetis_i2c_getreg(struct kinetis_i2cdev_s *priv, static void kinetis_i2c_putreg(struct kinetis_i2cdev_s *priv, uint8_t value, uint8_t offset); +/* Exclusion Helpers */ + +static inline void kinetis_i2c_sem_init(FAR struct kinetis_i2cdev_s *priv); +static inline void kinetis_i2c_sem_destroy(FAR struct kinetis_i2cdev_s *priv); +static inline void kinetis_i2c_sem_wait(FAR struct kinetis_i2cdev_s *priv); +static inline void kinetis_i2c_sem_post(struct kinetis_i2cdev_s *priv); + +/* Signal Helper */ + +static inline void kinetis_i2c_endwait(struct kinetis_i2cdev_s *priv); + /* I2C helpers */ +static int kinetis_i2c_init(FAR struct kinetis_i2cdev_s *priv); +static int kinetis_i2c_deinit(FAR struct kinetis_i2cdev_s *priv); + static void kinetis_i2c_setfrequency(struct kinetis_i2cdev_s *priv, uint32_t frequency); static int kinetis_i2c_start(struct kinetis_i2cdev_s *priv); @@ -148,7 +179,7 @@ static int kinetis_i2c_reset(struct i2c_master_s *dev); /* I2C lower half driver operations */ -static const struct i2c_ops_s g_i2c_ops = +static const struct i2c_ops_s kinetis_i2c_ops = { .transfer = kinetis_i2c_transfer #ifdef CONFIG_I2C_RESET @@ -156,16 +187,90 @@ static const struct i2c_ops_s g_i2c_ops = #endif }; -/* I2C device state instances */ +/* I2C device structures */ #ifdef CONFIG_KINETIS_I2C0 -static struct kinetis_i2cdev_s g_i2c0_dev; +static const struct kinetis_i2c_config_s kinetis_i2c0_config = +{ + .base = KINETIS_I2C0_BASE, + .clk_reg = KINETIS_SIM_SCGC4, + .clk_bit = SIM_SCGC4_I2C0, + .scl_pin = PIN_I2C0_SCL, + .sda_pin = PIN_I2C0_SDA, + .irqid = KINETIS_IRQ_I2C0, +}; + +static struct kinetis_i2cdev_s g_i2c0_dev = +{ + .dev.ops = &kinetis_i2c_ops, + .config = &kinetis_i2c0_config, + .refs = 0, + .state = STATE_OK, + .msgs = NULL, +}; #endif + #ifdef CONFIG_KINETIS_I2C1 -static struct kinetis_i2cdev_s g_i2c1_dev; +static const struct kinetis_i2c_config_s kinetis_i2c1_config = +{ + .base = KINETIS_I2C1_BASE, + .clk_reg = KINETIS_SIM_SCGC4, + .clk_bit = SIM_SCGC4_I2C1, + .scl_pin = PIN_I2C1_SCL, + .sda_pin = PIN_I2C1_SDA, + .irqid = KINETIS_IRQ_I2C1, +}; + +static struct kinetis_i2cdev_s g_i2c1_dev = +{ + .dev.ops = &kinetis_i2c_ops, + .config = &kinetis_i2c1_config, + .refs = 0, + .state = STATE_OK, + .msgs = NULL, +}; #endif + #ifdef CONFIG_KINETIS_I2C2 -static struct kinetis_i2cdev_s g_i2c2_dev; +static const struct kinetis_i2c_config_s kinetis_i2c2_config = +{ + .base = KINETIS_I2C2_BASE, + .clk_reg = KINETIS_SIM_SCGC1, + .clk_bit = SIM_SCGC1_I2C2, + .scl_pin = PIN_I2C2_SCL, + .sda_pin = PIN_I2C2_SDA, + .irqid = KINETIS_IRQ_I2C2, +}; + +static struct kinetis_i2cdev_s g_i2c2_dev = +{ + .dev.ops = &kinetis_i2c_ops, + .config = &kinetis_i2c2_config, + .refs = 0, + .state = STATE_OK, + .msgs = NULL, +}; +#endif + +#ifdef CONFIG_KINETIS_I2C3 +static const struct kinetis_i2c_config_s kinetis_i2c3_config = +{ + .base = KINETIS_I2C3_BASE, + .clk_reg = KINETIS_SIM_SCGC1, + .clk_bit = SIM_SCGC1_I2C3, + .scl_pin = PIN_I2C3_SCL, + .sda_pin = PIN_I2C3_SDA, + .irqid = KINETIS_IRQ_I2C3, +}; + +static struct kinetis_i2cdev_s g_i2c3_dev = +{ + .dev.ops = &kinetis_i2c_ops, + .config = &kinetis_i2c3_config, + .refs = 0, + .state = STATE_OK, + .msgs = NULL, +}; #endif /**************************************************************************** @@ -183,7 +288,7 @@ static struct kinetis_i2cdev_s g_i2c2_dev; static uint8_t kinetis_i2c_getreg(struct kinetis_i2cdev_s *priv, uint8_t offset) { - return getreg8(priv->base + offset); + return getreg8(priv->config->base + offset); } /**************************************************************************** @@ -197,7 +302,174 @@ static uint8_t kinetis_i2c_getreg(struct kinetis_i2cdev_s *priv, static void kinetis_i2c_putreg(struct kinetis_i2cdev_s *priv, uint8_t value, uint8_t offset) { - putreg8(value, priv->base + offset); + putreg8(value, priv->config->base + offset); +} + +/************************************************************************************ + * Name: kinetis_i2c_sem_init + * + * Description: + * Initialize semaphores + * + ************************************************************************************/ + +static inline void kinetis_i2c_sem_init(FAR struct kinetis_i2cdev_s *priv) +{ + sem_init(&priv->mutex, 0, 1); + + /* This semaphore is used for signaling and, hence, should not have + * priority inheritance enabled. + */ + + sem_init(&priv->wait, 0, 0); + sem_setprotocol(&priv->wait, SEM_PRIO_NONE); +} + +/************************************************************************************ + * Name: kinetis_i2c_sem_destroy + * + * Description: + * Destroy semaphores. + * + ************************************************************************************/ + +static inline void kinetis_i2c_sem_destroy(FAR struct kinetis_i2cdev_s *priv) +{ + sem_destroy(&priv->mutex); + sem_destroy(&priv->wait); +} + +/************************************************************************************ + * Name: kinetis_i2c_sem_wait + * + * Description: + * Take the exclusive access, waiting as necessary + * + ************************************************************************************/ + +static inline void kinetis_i2c_sem_wait(FAR struct kinetis_i2cdev_s *priv) +{ + while (sem_wait(&priv->mutex) != 0) + { + DEBUGASSERT(errno == EINTR); + } +} + +/************************************************************************************ + * Name: kinetis_i2c_sem_post + * + * Description: + * Release the mutual exclusion semaphore + * + ************************************************************************************/ + +static inline void kinetis_i2c_sem_post(struct kinetis_i2cdev_s *priv) +{ + sem_post(&priv->mutex); +} + +/************************************************************************************ + * Name: kinetis_i2c_endwait + * + * Description: + * Release the signaling semaphore + * + ************************************************************************************/ + +static inline void kinetis_i2c_endwait(struct kinetis_i2cdev_s *priv) +{ + sem_post(&priv->wait); +} + +/************************************************************************************ + * Name: kinetis_i2c_init + * + * Description: + * Setup the I2C hardware, ready for operation with defaults + * + ************************************************************************************/ + +static int kinetis_i2c_init(FAR struct kinetis_i2cdev_s *priv) +{ + uint32_t regval; + + /* Enable the clock to peripheral */ + + modifyreg32(priv->config->clk_reg, 0, priv->config->clk_bit); + + /* Disable while configuring */ + + kinetis_i2c_putreg(priv, 0, KINETIS_I2C_C1_OFFSET); + + /* Configure pins */ + + if (kinetis_pinconfig(priv->config->scl_pin) < 0) + { + return ERROR; + } + + if (kinetis_pinconfig(priv->config->sda_pin) < 0) + { + kinetis_pinconfig(MKI2C_INPUT(priv->config->scl_pin)); + return ERROR; + } + + /* High-drive select */ + + regval = kinetis_i2c_getreg(priv, KINETIS_I2C_C2_OFFSET); + regval |= I2C_C2_HDRS; + kinetis_i2c_putreg(priv, regval, KINETIS_I2C_C2_OFFSET); + + /* Attach Interrupt Handler */ + + irq_attach(priv->config->irqid, kinetis_i2c_interrupt, priv); + + /* Enable Interrupt Handler */ + + up_enable_irq(priv->config->irqid); + + /* Force a frequency update */ + + priv->frequency = 0; + + /* Set the default I2C frequency */ + + kinetis_i2c_setfrequency(priv, I2C_DEFAULT_FREQUENCY); + + /* Enable I2C */ + + kinetis_i2c_putreg(priv, I2C_C1_IICEN, KINETIS_I2C_C1_OFFSET); + return OK; +} + +/************************************************************************************ + * Name: kinetis_i2c_deinit + * + * Description: + * Shutdown the I2C hardware + * + ************************************************************************************/ + +static int kinetis_i2c_deinit(FAR struct kinetis_i2cdev_s *priv) +{ + /* Disable I2C */ + + kinetis_i2c_putreg(priv, 0, KINETIS_I2C_C1_OFFSET); + + /* Unconfigure GPIO pins */ + + kinetis_pinconfig(MKI2C_INPUT(priv->config->scl_pin)); + kinetis_pinconfig(MKI2C_INPUT(priv->config->sda_pin)); + + /* Disable and detach interrupts */ + + up_disable_irq(priv->config->irqid); + irq_detach(priv->config->irqid); + + /* Disable clocking */ + + modifyreg32(priv->config->clk_reg, priv->config->clk_bit, 0); + return OK; } /**************************************************************************** @@ -565,7 +837,7 @@ static void kinetis_i2c_stop(struct kinetis_i2cdev_s *priv) kinetis_i2c_putreg(priv, I2C_C1_IICEN | I2C_C1_IICIE, KINETIS_I2C_C1_OFFSET); - sem_post(&priv->wait); + kinetis_i2c_endwait(priv); } /**************************************************************************** @@ -585,7 +857,7 @@ static void kinetis_i2c_timeout(int argc, uint32_t arg, ...) irqstate_t flags = enter_critical_section(); priv->state = STATE_TIMEOUT; - sem_post(&priv->wait); + kinetis_i2c_endwait(priv); leave_critical_section(flags); } @@ -612,7 +884,7 @@ void kinetis_i2c_nextmsg(struct kinetis_i2cdev_s *priv) if (priv->restart) { - sem_post(&priv->wait); + kinetis_i2c_endwait(priv); } } else @@ -695,7 +967,7 @@ static int kinetis_i2c_interrupt(int irq, void *context, void *arg) KINETIS_I2C_D_OFFSET); priv->wrcnt++; - sem_post(&priv->wait); + kinetis_i2c_endwait(priv); } } else @@ -824,7 +1096,7 @@ static int kinetis_i2c_transfer(struct i2c_master_s *dev, /* Get exclusive access to the I2C bus */ - sem_wait(&priv->mutex); + kinetis_i2c_sem_wait(priv); /* Set up for the transfer */ @@ -888,7 +1160,7 @@ static int kinetis_i2c_transfer(struct i2c_master_s *dev, wd_start(priv->timeout, I2C_TIMEOUT, kinetis_i2c_timeout, 1, (uint32_t) priv); - sem_wait(&priv->wait); + kinetis_i2c_endwait(priv); wd_cancel(priv->timeout); @@ -901,7 +1173,7 @@ static int kinetis_i2c_transfer(struct i2c_master_s *dev, /* Release access to I2C bus */ - sem_post(&priv->mutex); + kinetis_i2c_sem_post(priv); if (priv->state != STATE_OK) { @@ -930,8 +1202,118 @@ static int kinetis_i2c_transfer(struct i2c_master_s *dev, #ifdef CONFIG_I2C_RESET static int kinetis_i2c_reset(struct i2c_master_s *dev) { - i2cinfo("No reset...\n"); - return OK; + struct kinetis_i2cdev_s *priv = (struct kinetis_i2cdev_s *)dev; + unsigned int clock_count; + unsigned int stretch_count; + uint32_t scl_gpio; + uint32_t sda_gpio; + uint32_t frequency; + int ret = ERROR; + + DEBUGASSERT(dev); + + /* Our caller must own a ref */ + + DEBUGASSERT(priv->refs > 0); + + /* Lock out other clients */ + + kinetis_i2c_sem_wait(priv); + + /* Save the current frequency */ + + frequency = priv->frequency; + + /* De-init the port */ + + kinetis_i2c_deinit(priv); + + /* Use GPIO configuration to un-wedge the bus */ + + scl_gpio = MKI2C_OUTPUT(priv->config->scl_pin); + sda_gpio = MKI2C_OUTPUT(priv->config->sda_pin); + + kinetis_pinconfig(scl_gpio); + kinetis_pinconfig(sda_gpio); + + /* Let SDA go high */ + + kinetis_gpiowrite(sda_gpio, 1); + + /* Clock the bus until any slaves currently driving it let it go. */ + + clock_count = 0; + while (!kinetis_gpioread(sda_gpio)) + { + /* Give up if we have tried too hard */ + + if (clock_count++ > 10) + { + goto out; + } + + /* Sniff to make sure that clock stretching has finished. + * + * If the bus never relaxes, the reset has failed. + */ + + stretch_count = 0; + while (!kinetis_gpioread(scl_gpio)) + { + /* Give up if we have tried too hard */ + + if (stretch_count++ > 10) + { + goto out; + } + + up_udelay(10); + } + + /* Drive SCL low */ + + kinetis_gpiowrite(scl_gpio, 0); + up_udelay(10); + + /* Drive SCL high again */ + + kinetis_gpiowrite(scl_gpio, 1); + up_udelay(10); + } + + /* Generate a start followed by a stop to reset slave + * state machines. + */ + + kinetis_gpiowrite(sda_gpio, 0); + up_udelay(10); + kinetis_gpiowrite(scl_gpio, 0); + up_udelay(10); + kinetis_gpiowrite(scl_gpio, 1); + up_udelay(10); + kinetis_gpiowrite(sda_gpio, 1); + up_udelay(10); + + /* Revert the GPIO configuration. */ + + kinetis_pinconfig(MKI2C_INPUT(sda_gpio)); + kinetis_pinconfig(MKI2C_INPUT(scl_gpio)); + + /* Re-init the port */ + + kinetis_i2c_init(priv); + + /* Restore the frequency */ + + kinetis_i2c_setfrequency(priv, frequency); + ret = OK; + +out: + + /* Release the port for re-use by other clients */ + + kinetis_i2c_sem_post(priv); + return ret; } #endif /* CONFIG_I2C_RESET */ @@ -950,145 +1332,58 @@ static int kinetis_i2c_reset(struct i2c_master_s *dev) struct i2c_master_s *kinetis_i2cbus_initialize(int port) { struct kinetis_i2cdev_s *priv; + irqstate_t flags; i2cinfo("port=%d\n", port); - if (port > 1) + switch(port) { - i2cerr("ERROR: Kinetis I2C Only suppors ports 0 and 1\n"); - return NULL; - } - - irqstate_t flags; - uint32_t regval; - - flags = enter_critical_section(); - #ifdef CONFIG_KINETIS_I2C0 - if (port == 0) - { - priv = &g_i2c0_dev; - priv->base = KINETIS_I2C0_BASE; - priv->irqid = KINETIS_IRQ_I2C0; - priv->basefreq = BOARD_BUS_FREQ; - - /* Enable clock */ - - regval = getreg32(KINETIS_SIM_SCGC4); - regval |= SIM_SCGC4_I2C0; - putreg32(regval, KINETIS_SIM_SCGC4); - - /* Disable while configuring */ - - kinetis_i2c_putreg(priv, 0, KINETIS_I2C_C1_OFFSET); - - /* Configure pins */ - - kinetis_pinconfig(PIN_I2C0_SCL); - kinetis_pinconfig(PIN_I2C0_SDA); - } - else + case 0: + priv = &g_i2c0_dev; + break; #endif #ifdef CONFIG_KINETIS_I2C1 - if (port == 1) - { - priv = &g_i2c1_dev; - priv->base = KINETIS_I2C1_BASE; - priv->irqid = KINETIS_IRQ_I2C1; - priv->basefreq = BOARD_BUS_FREQ; - - /* Enable clock */ - - regval = getreg32(KINETIS_SIM_SCGC4); - regval |= SIM_SCGC4_I2C1; - putreg32(regval, KINETIS_SIM_SCGC4); - - /* Disable while configuring */ - - kinetis_i2c_putreg(priv, 0, KINETIS_I2C_C1_OFFSET); - - /* Configure pins */ - - kinetis_pinconfig(PIN_I2C1_SCL); - kinetis_pinconfig(PIN_I2C1_SDA); - } - else + case 1: + priv = &g_i2c1_dev; + break; #endif #ifdef CONFIG_KINETIS_I2C2 - if (port == 2) - { - priv = &g_i2c2_dev; - priv->base = KINETIS_I2C2_BASE; - priv->irqid = KINETIS_IRQ_I2C2; - priv->basefreq = BOARD_BUS_FREQ; - - /* Enable clock */ - - regval = getreg32(KINETIS_SIM_SCGC4); - regval |= SIM_SCGC4_I2C2; - putreg32(regval, KINETIS_SIM_SCGC4); - - /* Disable while configuring */ - - kinetis_i2c_putreg(priv, 0, KINETIS_I2C_C1_OFFSET); - - /* Configure pins */ - - kinetis_pinconfig(PIN_I2C2_SCL); - kinetis_pinconfig(PIN_I2C2_SDA); - } - else + case 2: + priv = &g_i2c2_dev; + break; #endif - { - leave_critical_section(flags); - i2cerr("ERROR: Unsupport I2C bus: %d\n", port); - return NULL; +#ifdef CONFIG_KINETIS_I2C3 + case 3: + priv = &g_i2c3_dev; + break; +#endif + default: + i2cerr("ERROR: Kinetis I2C Only suppors ports 0 and %d\n", KINETIS_NI2C-1); + return NULL; } - /* Set the default I2C frequency */ - - kinetis_i2c_setfrequency(priv, I2C_DEFAULT_FREQUENCY); - - /* Enable */ - - kinetis_i2c_putreg(priv, I2C_C1_IICEN, KINETIS_I2C_C1_OFFSET); - - /* High-drive select (TODO: why)? */ - - regval = kinetis_i2c_getreg(priv, KINETIS_I2C_C2_OFFSET); - regval |= I2C_C2_HDRS; - kinetis_i2c_putreg(priv, regval, KINETIS_I2C_C2_OFFSET); - + flags = enter_critical_section(); + if ((volatile int)priv->refs++ == 0) + { + priv->timeout = wd_create(); + DEBUGASSERT(priv->timeout != 0); + if (priv->timeout == NULL) + { + priv->refs--; + goto errout; + } + kinetis_i2c_sem_init(priv); + kinetis_i2c_init(priv); + } leave_critical_section(flags); - /* Initialize semaphores */ - - sem_init(&priv->mutex, 0, 1); - sem_init(&priv->wait, 0, 0); - - /* The wait semaphore is used for signaling and, hence, should not have - * priority inheritance enabled. - */ - - sem_setprotocol(&priv->wait, SEM_PRIO_NONE); - - /* Allocate a watchdog timer */ - - priv->timeout = wd_create(); - DEBUGASSERT(priv->timeout != 0); - - /* Attach Interrupt Handler */ - - irq_attach(priv->irqid, kinetis_i2c_interrupt, priv); - - /* Enable Interrupt Handler */ - - up_enable_irq(priv->irqid); - - /* Install our operations */ - - priv->dev.ops = &g_i2c_ops; return &priv->dev; + +errout: + leave_critical_section(flags); + return NULL; + } /**************************************************************************** @@ -1102,13 +1397,32 @@ struct i2c_master_s *kinetis_i2cbus_initialize(int port) int kinetis_i2cbus_uninitialize(struct i2c_master_s *dev) { struct kinetis_i2cdev_s *priv = (struct kinetis_i2cdev_s *)dev; + irqstate_t flags; DEBUGASSERT(priv != NULL); - kinetis_i2c_putreg(priv, 0, KINETIS_I2C_C1_OFFSET); + /* Decrement reference count and check for underflow */ - up_disable_irq(priv->irqid); - irq_detach(priv->irqid); + if (priv->refs == 0) + { + return ERROR; + } + + flags = enter_critical_section(); + + if (--priv->refs) + { + leave_critical_section(flags); + return OK; + } + + leave_critical_section(flags); + + /* Disable power and other HW resource (GPIO's) */ + + kinetis_i2c_deinit(priv); + kinetis_i2c_sem_destroy(priv); + wd_delete(priv->timeout); return OK; } From 5de74441a6b7d2861f02b071815ebba2c47a6dc2 Mon Sep 17 00:00:00 2001 From: Gregory Nutt Date: Tue, 20 Jun 2017 13:33:14 -0600 Subject: [PATCH 8/8] Costmetic change from review of last PR --- arch/arm/src/kinetis/kinetis_i2c.c | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/arch/arm/src/kinetis/kinetis_i2c.c b/arch/arm/src/kinetis/kinetis_i2c.c index 50ebd69597..88fef0f2fa 100644 --- a/arch/arm/src/kinetis/kinetis_i2c.c +++ b/arch/arm/src/kinetis/kinetis_i2c.c @@ -1403,26 +1403,26 @@ int kinetis_i2cbus_uninitialize(struct i2c_master_s *dev) /* Decrement reference count and check for underflow */ - if (priv->refs == 0) - { - return ERROR; - } + if (priv->refs == 0) + { + return ERROR; + } - flags = enter_critical_section(); + flags = enter_critical_section(); - if (--priv->refs) - { - leave_critical_section(flags); - return OK; - } + if (--priv->refs) + { + leave_critical_section(flags); + return OK; + } - leave_critical_section(flags); + leave_critical_section(flags); - /* Disable power and other HW resource (GPIO's) */ + /* Disable power and other HW resource (GPIO's) */ - kinetis_i2c_deinit(priv); - kinetis_i2c_sem_destroy(priv); - wd_delete(priv->timeout); + kinetis_i2c_deinit(priv); + kinetis_i2c_sem_destroy(priv); + wd_delete(priv->timeout); return OK; }