diff --git a/arch/arm/src/lm3s/chip.h b/arch/arm/src/lm3s/chip.h index 071d35ca76..511b2e3780 100644 --- a/arch/arm/src/lm3s/chip.h +++ b/arch/arm/src/lm3s/chip.h @@ -58,7 +58,7 @@ # define LM3S_NADC 1 /* One ADC module */ # define LM2S_NPWM 0 /* No PWM generator modules */ # define LM3S_NQEI 0 /* No quadrature encoders */ -# define LC3S_NGPIOS 38 /* 5-38 GPIOs, depending on configuration */ +# define LM3S_NPORTS 8 /* 8 Ports (GPIOA-H) 5-38 GPIOs */ #elif defined(CONFIG_ARCH_CHIP_LM3S6965) # define LM3S_NTIMERS 4 /* Four general purpose timers */ # define LM3S_NETHCONTROLLERS 1 /* One Ethernet controller */ @@ -69,7 +69,7 @@ # define LM3S_NADC 1 /* One ADC module */ # define LM2S_NPWM 3 /* Three PWM generator modules */ # define LM3S_NQEI 2 /* Two quadrature encoders */ -# define LC3S_NGPIOS 42 /* 0-42 GPIOs */ +# define LM3S_NPORTS 7 /* 7 Ports (GPIOA-G), 0-42 GPIOs */ #elif defined(CONFIG_ARCH_CHIP_LM3S9B96) # define LM3S_NTIMERS 4 /* Four general purpose timers */ # define LM3S_NETHCONTROLLERS 1 /* One Ethernet controller */ @@ -81,7 +81,7 @@ # define LM3S_CAN 2 /* Two CAN module */ # define LM3S_NPWM 4 /* Four PWM generator modules */ # define LM3S_NQEI 2 /* Two quadrature encoders */ -# define LC3S_NGPIOS 65 /* 0-65 GPIOs */ +# define LM3S_NPORTS 9 /* 9 Ports (GPIOA-H,J) 0-65 GPIOs */ #else # error "Capabilities not specified for this LM3S chip" #endif diff --git a/arch/arm/src/lm3s/lm3s_gpio.c b/arch/arm/src/lm3s/lm3s_gpio.c index 5614b54f9c..db88343ee6 100644 --- a/arch/arm/src/lm3s/lm3s_gpio.c +++ b/arch/arm/src/lm3s/lm3s_gpio.c @@ -56,17 +56,6 @@ * Pre-processor Definitions ****************************************************************************/ -/* This current implementation can only support, at most, 8 GPIO ports. Some - * newer chips (such as the LM3S9B96) have 9 GPIO ports. It will require - * some restructuring of the definitions in lm3s_internal.h and to the size - * of the g_gpiobase[] table and the lm3s_gpiobaseaddress() function in this - * file to access GPIOs in ports above GPIOH. - */ - -#if LC3S_NGPIOS > 64 -# warning "This design must be extended to access ports above GPIOH" -#endif - /* These definitions are part of the implementation of the GPIO pad * configuration of Table 9-1 in the LM3S6918 data sheet. */ @@ -151,17 +140,23 @@ static const struct gpio_func_s g_funcbits[] = {GPIO_INTERRUPT_SETBITS, GPIO_INTERRUPT_CLRBITS}, /* GPIO_FUNC_INTERRUPT */ }; -static const uint32_t g_gpiobase[] = +static const uint32_t g_gpiobase[LM3S_NPORTS] = { + /* All support LM3S parts have at least 7 ports, GPIOA-G */ + LM3S_GPIOA_BASE, LM3S_GPIOB_BASE, LM3S_GPIOC_BASE, LM3S_GPIOD_BASE, LM3S_GPIOE_BASE, LM3S_GPIOF_BASE, LM3S_GPIOG_BASE, - /* GPIOH exists on the LM3S6918, but not on the LM3S6965 */ + /* GPIOH exists on the LM3S6918 and th LM3S6B96, but not on the LM3S6965 */ -#ifdef LM3S_GPIOH_BASE +#if LM3S_NPORTS > 7 LM3S_GPIOH_BASE, -#else - 0, +#endif + + /* GPIOJ exists on the LM3S6B96, but not on the LM3S6918 or LM3S6965 */ + +#if LM3S_NPORTS > 8 + LM3S_GPIOJ_BASE, #endif }; @@ -182,9 +177,14 @@ static const uint32_t g_gpiobase[] = * ****************************************************************************/ -static inline uint32_t lm3s_gpiobaseaddress(unsigned int port) +static uint32_t lm3s_gpiobaseaddress(unsigned int port) { - return g_gpiobase[port & 7]; + uint32_t gpiobase = 0; + if (port < LM3S_NPORTS) + { + gpiobase = g_gpiobase[port]; + } + return gpiobase; } /**************************************************************************** diff --git a/arch/arm/src/lm3s/lm3s_gpioirq.c b/arch/arm/src/lm3s/lm3s_gpioirq.c index 4165a41273..1165f6decb 100644 --- a/arch/arm/src/lm3s/lm3s_gpioirq.c +++ b/arch/arm/src/lm3s/lm3s_gpioirq.c @@ -92,6 +92,13 @@ static const uint32_t g_gpiobase[] = #ifndef CONFIG_LM3S_DISABLE_GPIOG_IRQS LM3S_GPIOG_BASE, #endif + + /* NOTE: Not all LM3S architectures support GPIOs above GPIOG. If the chip + * does not support these higher ports, then they must be disabled in the + * configuration. Otherwise, the following will likely cause compilation + * errors! + */ + #ifndef CONFIG_LM3S_DISABLE_GPIOH_IRQS LM3S_GPIOH_BASE, #endif @@ -399,6 +406,7 @@ void gpio_irqdisable(int irq) /* Get the base address of the GPIO module associated with this IRQ */ base = lm3s_gpiobaseaddress(gpioirq); + DEBUGASSERT(base != 0); pin = (1 << (gpioirq & 7)); /* Disable the GPIO interrupt. "The GPIO IM register is the interrupt diff --git a/arch/arm/src/lm3s/lm3s_internal.h b/arch/arm/src/lm3s/lm3s_internal.h index 32671c586a..759a667fd7 100644 --- a/arch/arm/src/lm3s/lm3s_internal.h +++ b/arch/arm/src/lm3s/lm3s_internal.h @@ -64,7 +64,7 @@ /* Bit-encoded input to lm3s_configgpio() *******************************************/ /* Encoding: - * FFFS SPPP IIIn nnnn nnnn nnnn nVPP PBBB + * FFFS SPPP IIIn nnnn nnnn nnnn VPPP PBBB * * These bits set the primary function of the pin: * FFFn nnnn nnnn nnnn nnnn nnnn nnnn nnnn @@ -119,25 +119,20 @@ #define GPIO_INT_HIGHLEVEL (4 << GPIO_INT_SHIFT) /* Interrupt on high level */ /* If the pin is an GPIO digital output, then this identifies the initial output value: - * nnnn nnnn nnnn nnnn nnnn nnnn nVnn nnnn + * nnnn nnnn nnnn nnnn nnnn nnnn Vnnn nnnn */ -#define GPIO_VALUE_SHIFT 6 /* Bit 6: If output, inital value of output */ +#define GPIO_VALUE_SHIFT 7 /* Bit 7: If output, inital value of output */ #define GPIO_VALUE_MASK (1 << GPIO_VALUE_SHIFT) #define GPIO_VALUE_ZERO (0 << GPIO_VALUE_SHIFT) /* Initial value is zero */ #define GPIO_VALUE_ONE (1 << GPIO_VALUE_SHIFT) /* Initial value is one */ /* This identifies the GPIO port - * nnnn nnnn nnnn nnnn nnnn nnnn nnPP Pnnn - * - * NOTE: Because this field is limited to 3 bits, it can only support 8 ports. - * Newer chips (such as the LM3S9B96) have 9 GPIO ports. It will require - * some restructuring of these definitions (and the logic in lm3s_gpio.c) - * to access GPIOs in ports above GPIOH. + * nnnn nnnn nnnn nnnn nnnn nnnn nPPP Pnnn */ -#define GPIO_PORT_SHIFT 3 /* Bit 3-5: Port number */ -#define GPIO_PORT_MASK (7 << GPIO_PORT_SHIFT) +#define GPIO_PORT_SHIFT 3 /* Bit 3-6: Port number */ +#define GPIO_PORT_MASK (15 << GPIO_PORT_SHIFT) #define GPIO_PORTA (0 << GPIO_PORT_SHIFT) /* GPIOA */ #define GPIO_PORTB (1 << GPIO_PORT_SHIFT) /* GPIOB */ #define GPIO_PORTC (2 << GPIO_PORT_SHIFT) /* GPIOC */ @@ -146,6 +141,7 @@ #define GPIO_PORTF (5 << GPIO_PORT_SHIFT) /* GPIOF */ #define GPIO_PORTG (6 << GPIO_PORT_SHIFT) /* GPIOG */ #define GPIO_PORTH (7 << GPIO_PORT_SHIFT) /* GPIOH */ +#define GPIO_PORTJ (8 << GPIO_PORT_SHIFT) /* GPIOJ */ /* This identifies the bit in the port: * nnnn nnnn nnnn nnnn nnnn nnnn nnnn nBBB