Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4e9f9fd5 authored by Herbert Valerio Riedel's avatar Herbert Valerio Riedel Committed by Russell King
Browse files

[ARM] 4668/1: ep93xx: implement new GPIO API



Implement new GPIO API for ep93xx platform as defined in Documentation/gpio.txt
and provide transitional __deprecated wrappers for the previous gpio_line_*
functions.

Signed-off-by: default avatarHerbert Valerio Riedel <hvr@gnu.org>
Acked-by: default avatarLennert Buytenhek <buytenh@wantstofly.org>
Signed-off-by: default avatarRussell King <rmk+kernel@arm.linux.org.uk>
parent 9b73e76f
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -217,6 +217,7 @@ config ARCH_EP93XX
	bool "EP93xx-based"
	select ARM_AMBA
	select ARM_VIC
	select GENERIC_GPIO
	help
	  This enables support for the Cirrus EP93xx series of CPUs.

+44 −19
Original line number Diff line number Diff line
@@ -188,7 +188,7 @@ static unsigned char data_direction_register_offset[8] = {
	0x10, 0x14, 0x18, 0x1c, 0x24, 0x34, 0x3c, 0x44,
};

void gpio_line_config(int line, int direction)
static void ep93xx_gpio_set_direction(unsigned line, int direction)
{
	unsigned int data_direction_register;
	unsigned long flags;
@@ -219,39 +219,64 @@ void gpio_line_config(int line, int direction)
	}
	local_irq_restore(flags);
}

void __deprecated gpio_line_config(int line, int direction)
{
	ep93xx_gpio_set_direction(line, direction);
}
EXPORT_SYMBOL(gpio_line_config);

int gpio_line_get(int line)
int gpio_direction_input(unsigned gpio)
{
	if (gpio > EP93XX_GPIO_LINE_H(7))
		return -EINVAL;

	ep93xx_gpio_set_direction(gpio, GPIO_IN);

	return 0;
}
EXPORT_SYMBOL(gpio_direction_input);

int gpio_direction_output(unsigned gpio, int value)
{
	if (gpio > EP93XX_GPIO_LINE_H(7))
		return -EINVAL;

	gpio_set_value(gpio, value);
	ep93xx_gpio_set_direction(gpio, GPIO_OUT);

	return 0;
}
EXPORT_SYMBOL(gpio_direction_output);

int gpio_get_value(unsigned gpio)
{
	unsigned int data_register;

	data_register = EP93XX_GPIO_REG(data_register_offset[line >> 3]);
	data_register = EP93XX_GPIO_REG(data_register_offset[gpio >> 3]);

	return !!(__raw_readb(data_register) & (1 << (line & 7)));
	return !!(__raw_readb(data_register) & (1 << (gpio & 7)));
}
EXPORT_SYMBOL(gpio_line_get);
EXPORT_SYMBOL(gpio_get_value);

void gpio_line_set(int line, int value)
void gpio_set_value(unsigned gpio, int value)
{
	unsigned int data_register;
	unsigned long flags;
	unsigned char v;

	data_register = EP93XX_GPIO_REG(data_register_offset[line >> 3]);
	data_register = EP93XX_GPIO_REG(data_register_offset[gpio >> 3]);

	local_irq_save(flags);
	if (value == EP93XX_GPIO_HIGH) {
	v = __raw_readb(data_register);
		v |= 1 << (line & 7);
	if (value)
		v |= 1 << (gpio & 7);
	else
		v &= ~(1 << (gpio & 7));
	__raw_writeb(v, data_register);
	} else if (value == EP93XX_GPIO_LOW) {
		v = __raw_readb(data_register);
		v &= ~(1 << (line & 7));
		__raw_writeb(v, data_register);
	}
	local_irq_restore(flags);
}
EXPORT_SYMBOL(gpio_line_set);
EXPORT_SYMBOL(gpio_set_value);


/*************************************************************************
@@ -334,9 +359,9 @@ static int ep93xx_gpio_irq_type(unsigned int irq, unsigned int type)

	line = irq - IRQ_EP93XX_GPIO(0);
	if (line >= 0 && line < 16) {
		gpio_line_config(line, GPIO_IN);
		ep93xx_gpio_set_direction(line, GPIO_IN);
	} else {
		gpio_line_config(EP93XX_GPIO_LINE_F(line-16), GPIO_IN);
		ep93xx_gpio_set_direction(EP93XX_GPIO_LINE_F(line-16), GPIO_IN);
	}

	port = line >> 3;
+66 −10
Original line number Diff line number Diff line
@@ -5,16 +5,6 @@
#ifndef __ASM_ARCH_GPIO_H
#define __ASM_ARCH_GPIO_H

#define GPIO_IN				0
#define GPIO_OUT			1

#define EP93XX_GPIO_LOW			0
#define EP93XX_GPIO_HIGH		1

extern void gpio_line_config(int line, int direction);
extern int  gpio_line_get(int line);
extern void gpio_line_set(int line, int value);

/* GPIO port A.  */
#define EP93XX_GPIO_LINE_A(x)		((x) + 0)
#define EP93XX_GPIO_LINE_EGPIO0		EP93XX_GPIO_LINE_A(0)
@@ -103,5 +93,71 @@ extern void gpio_line_set(int line, int value);
#define EP93XX_GPIO_LINE_DD6		EP93XX_GPIO_LINE_H(6)
#define EP93XX_GPIO_LINE_DD7		EP93XX_GPIO_LINE_H(7)

/* new generic GPIO API - see Documentation/gpio.txt */

static inline int gpio_request(unsigned gpio, const char *label)
{
	if (gpio > EP93XX_GPIO_LINE_H(7))
		return -EINVAL;
	return 0;
}

static inline void gpio_free(unsigned gpio)
{
}

int gpio_direction_input(unsigned gpio);
int gpio_direction_output(unsigned gpio, int value);
int gpio_get_value(unsigned gpio);
void gpio_set_value(unsigned gpio, int value);

#include <asm-generic/gpio.h> /* cansleep wrappers */

/*
 * Map GPIO A0..A7  (0..7)  to irq 64..71,
 *          B0..B7  (7..15) to irq 72..79, and
 *          F0..F7 (40..47) to irq 80..87.
 */

static inline int gpio_to_irq(unsigned gpio)
{
	if (gpio <= EP93XX_GPIO_LINE_EGPIO15)
		return 64 + gpio;

	if (gpio >= EP93XX_GPIO_LINE_F(0) && gpio <= EP93XX_GPIO_LINE_F(7))
		return 80 + (gpio - EP93XX_GPIO_LINE_F(0));

	return -EINVAL;
}

static inline int irq_to_gpio(unsigned irq)
{
	if (irq >= 64 && irq <= 79)
		return irq - 64;

	if (irq >= 80 && irq <= 87)
		return (irq - 80) + EP93XX_GPIO_LINE_F(0);

	return -EINVAL;
}

/* obsolete specific GPIO API */
#define GPIO_IN				0
#define GPIO_OUT			1

#define EP93XX_GPIO_LOW			0
#define EP93XX_GPIO_HIGH		1

void __deprecated gpio_line_config(int line, int direction);

static inline int  __deprecated gpio_line_get(int line)
{
	return gpio_get_value(line);
}

static inline void __deprecated gpio_line_set(int line, int value)
{
	gpio_set_value(line, value);
}

#endif