--- a/arch/arm/mach-ixp4xx/common.c +++ b/arch/arm/mach-ixp4xx/common.c @@ -36,6 +36,7 @@ #include #include #include +#include #include #include @@ -375,12 +376,50 @@ static struct platform_device *ixp46x_de unsigned long ixp4xx_exp_bus_size; EXPORT_SYMBOL(ixp4xx_exp_bus_size); +static int ixp4xx_gpio_direction_input(struct gpio_chip *chip, unsigned gpio) +{ + gpio_line_config(gpio, IXP4XX_GPIO_IN); + return 0; +} + +static int ixp4xx_gpio_direction_output(struct gpio_chip *chip, unsigned gpio, int level) +{ + gpio_line_set(gpio, level); + gpio_line_config(gpio, IXP4XX_GPIO_OUT); + return 0; +} + +static int ixp4xx_gpio_get_value(struct gpio_chip *chip, unsigned gpio) +{ + int value; + + gpio_line_get(gpio, &value); + return value; +} + +static void ixp4xx_gpio_set_value(struct gpio_chip *chip, unsigned gpio, int value) +{ + gpio_line_set(gpio, value); +} + +static struct gpio_chip ixp4xx_gpio_chip = { + .label = "IXP4XX_GPIO_CHIP", + .direction_input = ixp4xx_gpio_direction_input, + .direction_output = ixp4xx_gpio_direction_output, + .get = ixp4xx_gpio_get_value, + .set = ixp4xx_gpio_set_value, + .base = 0, + .ngpio = 16, +}; + void __init ixp4xx_sys_init(void) { ixp4xx_exp_bus_size = SZ_16M; platform_add_devices(ixp4xx_devices, ARRAY_SIZE(ixp4xx_devices)); + gpiochip_add(&ixp4xx_gpio_chip); + if (cpu_is_ixp46x()) { int region; --- a/arch/arm/Kconfig +++ b/arch/arm/Kconfig @@ -529,7 +529,7 @@ config ARCH_IXP4XX depends on MMU select CLKSRC_MMIO select CPU_XSCALE - select GENERIC_GPIO + select ARCH_REQUIRE_GPIOLIB select GENERIC_CLOCKEVENTS select HAVE_SCHED_CLOCK select MIGHT_HAVE_PCI --- a/arch/arm/mach-ixp4xx/include/mach/gpio.h +++ b/arch/arm/mach-ixp4xx/include/mach/gpio.h @@ -27,38 +27,19 @@ #include #include +#include /* cansleep wrappers */ #define __ARM_GPIOLIB_COMPLEX -static inline int gpio_request(unsigned gpio, const char *label) -{ - return 0; -} - -static inline void gpio_free(unsigned gpio) -{ - might_sleep(); - - return; -} - -static inline int gpio_direction_input(unsigned gpio) -{ - gpio_line_config(gpio, IXP4XX_GPIO_IN); - return 0; -} - -static inline int gpio_direction_output(unsigned gpio, int level) -{ - gpio_line_set(gpio, level); - gpio_line_config(gpio, IXP4XX_GPIO_OUT); - return 0; -} +#define NR_BUILTIN_GPIO 16 static inline int gpio_get_value(unsigned gpio) { int value; + if (gpio >= NR_BUILTIN_GPIO) + return __gpio_get_value(gpio); + gpio_line_get(gpio, &value); return value; @@ -66,10 +47,13 @@ static inline int gpio_get_value(unsigne static inline void gpio_set_value(unsigned gpio, int value) { - gpio_line_set(gpio, value); + if (gpio >= NR_BUILTIN_GPIO) + __gpio_set_value(gpio, value); + else + gpio_line_set(gpio, value); } -#include /* cansleep wrappers */ +#define gpio_cansleep __gpio_cansleep extern int gpio_to_irq(int gpio); #define gpio_to_irq gpio_to_irq