From 774e7f9865397633f0f80c2936cdde52fadac32b Mon Sep 17 00:00:00 2001 From: v01d Date: Sat, 4 Jun 2016 00:28:53 -0300 Subject: [PATCH] lpc43 GPIO Interrupts enabled and fixed (not all cases tested) --- arch/arm/src/lpc43xx/Kconfig | 7 +++++++ arch/arm/src/lpc43xx/lpc43_gpio.c | 4 ++++ arch/arm/src/lpc43xx/lpc43_gpio.h | 12 ++++++------ arch/arm/src/lpc43xx/lpc43_gpioint.c | 29 +++++++++++++++++++++++++++- arch/arm/src/lpc43xx/lpc43_gpioint.h | 16 +++++++++++++++ 5 files changed, 61 insertions(+), 7 deletions(-) diff --git a/arch/arm/src/lpc43xx/Kconfig b/arch/arm/src/lpc43xx/Kconfig index 5b7d730151e..c6df85ae351 100644 --- a/arch/arm/src/lpc43xx/Kconfig +++ b/arch/arm/src/lpc43xx/Kconfig @@ -150,6 +150,13 @@ endchoice # LPC43XX Boot Configuration menu "LPC43xx Peripheral Support" + +config GPIO_IRQ + bool "GPIO interrupt support" + default n + ---help--- + Enable support for GPIO interrupts + config LPC43_ADC0 bool "ADC0" default n diff --git a/arch/arm/src/lpc43xx/lpc43_gpio.c b/arch/arm/src/lpc43xx/lpc43_gpio.c index 3d5db11b7e4..49b7f9b27f2 100644 --- a/arch/arm/src/lpc43xx/lpc43_gpio.c +++ b/arch/arm/src/lpc43xx/lpc43_gpio.c @@ -49,6 +49,10 @@ #include "up_arch.h" #include "lpc43_gpio.h" +#ifdef CONFIG_GPIO_IRQ +#include "lpc43_gpioint.h" +#endif + /**************************************************************************** * Pre-processor Definitions ****************************************************************************/ diff --git a/arch/arm/src/lpc43xx/lpc43_gpio.h b/arch/arm/src/lpc43xx/lpc43_gpio.h index 1ee14fac639..4f16c841de4 100644 --- a/arch/arm/src/lpc43xx/lpc43_gpio.h +++ b/arch/arm/src/lpc43xx/lpc43_gpio.h @@ -143,7 +143,7 @@ * ..CC C... .... .... */ -#define GPIO_PININT_SHIFT (10) /* Bits 11-13: Pin interrupt number */ +#define GPIO_PININT_SHIFT (11) /* Bits 11-13: Pin interrupt number */ #define GPIO_PININT_MASK (7 << GPIO_PININT_SHIFT) # define GPIO_PININT0 (0 << GPIO_PININT_SHIFT) # define GPIO_PININT1 (1 << GPIO_PININT_SHIFT) @@ -162,9 +162,9 @@ * .... .III .... .... */ -#define _GPIO_INT_LEVEL (1 << 10) /* Bit 10: 1=Level (vs edge) */ -#define _GPIO_INT_HIGH (1 << 9) /* Bit 9: 1=High level or rising edge */ -#define _GPIO_INT_LOW (1 << 8) /* Bit 8: 1=Low level or falling edge */ +#define _GPIO_INT_EDGE (1 << 10) /* Bit 10: 1=Edge (vs level) */ +#define _GPIO_INT_LOW (1 << 9) /* Bit 9: 1=Low level or falling edge */ +#define _GPIO_INT_HIGH (1 << 8) /* Bit 8: 1=High level or rising edge */ #define GPIO_INT_SHIFT (8) /* Bits 8-10: Interrupt mode */ #define GPIO_INT_MASK (7 << GPIO_INT_SHIFT) @@ -176,8 +176,8 @@ #define GPIO_IS_ACTIVE_HI(p) (((p) & _GPIO_INT_HIGH) != 0) #define GPIO_IS_ACTIVE_LOW(p) (((p) & _GPIO_INT_LOW) != 0) -#define GPIO_IS_EDGE(p) (((p) & _GPIO_INT_LEVEL) == 0) -#define GPIO_IS_LEVEL(p) (((p) & _GPIO_INT_LEVEL) != 0) +#define GPIO_IS_LEVEL(p) (((p) & _GPIO_INT_EDGE) == 0) +#define GPIO_IS_EDGE(p) (((p) & _GPIO_INT_EDGE) != 0) /* GPIO Port Number: * diff --git a/arch/arm/src/lpc43xx/lpc43_gpioint.c b/arch/arm/src/lpc43xx/lpc43_gpioint.c index 51e010ba330..029e2aec20a 100644 --- a/arch/arm/src/lpc43xx/lpc43_gpioint.c +++ b/arch/arm/src/lpc43xx/lpc43_gpioint.c @@ -57,6 +57,7 @@ #include #include +#include #include @@ -176,7 +177,7 @@ int lpc43_gpioint_grpinitialize(int group, bool anded, bool level) int lpc43_gpioint_pinconfig(uint16_t gpiocfg) { unsigned int port = ((gpiocfg & GPIO_PORT_MASK) >> GPIO_PORT_SHIFT); - unsigned int pin = ((gpiocfg & GPIO_PORT_MASK) >> GPIO_PORT_SHIFT); + unsigned int pin = ((gpiocfg & GPIO_PIN_MASK) >> GPIO_PIN_SHIFT); unsigned int pinint = ((gpiocfg & GPIO_PININT_MASK) >> GPIO_PININT_SHIFT); uint32_t bitmask = (1 << pinint); uint32_t regval; @@ -227,6 +228,8 @@ int lpc43_gpioint_pinconfig(uint16_t gpiocfg) /* Configure the active high level or rising edge */ + /* TODO: this works for edge sensitive, but not level sensitive, active level is only controlled in IENF */ + regval = getreg32(LPC43_GPIOINT_IENR); if (GPIO_IS_ACTIVE_HI(gpiocfg)) { @@ -321,4 +324,28 @@ int lpc43_gpioint_grpconfig(uint16_t gpiocfg) return OK; } +/**************************************************************************** + * Name: lpc43_gpioint_ack + * + * Description: + * Acknowledge the interrupt for a given pint interrupt number. Call this + * inside the interrupt handler. For edge sensitive interrupts, the interrupt + * status is cleared. For level sensitive interrupts, the active-high/-low + * sensitivity is inverted. + * + * Returned Value: + * Zero on success; a negated errno value on failure. + * + ****************************************************************************/ + +int lpc43_gpioint_ack(uint8_t intnumber) +{ + uint32_t regval; + + regval = getreg32(LPC43_GPIOINT_IST); + regval |= (1 << intnumber); + putreg32(regval, LPC43_GPIOINT_IST); + return OK; +} + #endif /* CONFIG_GPIO_IRQ */ diff --git a/arch/arm/src/lpc43xx/lpc43_gpioint.h b/arch/arm/src/lpc43xx/lpc43_gpioint.h index 35b22f7c7f2..ec34649455b 100644 --- a/arch/arm/src/lpc43xx/lpc43_gpioint.h +++ b/arch/arm/src/lpc43xx/lpc43_gpioint.h @@ -136,5 +136,21 @@ int lpc43_gpioint_pinconfig(uint16_t gpiocfg); int lpc43_gpioint_grpconfig(uint16_t gpiocfg); +/**************************************************************************** + * Name: lpc43_gpioint_ack + * + * Description: + * Acknowledge the interrupt for a given pint interrupt number. Call this + * inside the interrupt handler. For edge sensitive interrupts, the interrupt + * status is cleared. For level sensitive interrupts, the active-high/-low + * sensitivity is inverted. + * + * Returned Value: + * Zero on success; a negated errno value on failure. + * + ****************************************************************************/ + +int lpc43_gpioint_ack(uint8_t intnumber); + #endif /* CONFIG_GPIO_IRQ */ #endif /* __ARCH_ARM_SRC_LPC43XX_LPC43_GPIOINT_H */