// SPDX-License-Identifier: GPL-2.0
/*
 * Etrax general port I/O device
 *
 * Copyright (c) 1999-2007 Axis Communications AB
 *
 * Authors:    Bjorn Wesen      (initial version)
 *             Ola Knutsson     (LED handling)
 *             Johan Adolfsson  (read/set directions, write, port G)
 */


#include <linux/module.h>
#include <linux/sched.h>
#include <linux/slab.h>
#include <linux/ioport.h>
#include <linux/errno.h>
#include <linux/kernel.h>
#include <linux/fs.h>
#include <linux/string.h>
#include <linux/poll.h>
#include <linux/init.h>
#include <linux/interrupt.h>

#include <asm/etraxgpio.h>
#include <arch/svinto.h>
#include <asm/io.h>
#include <asm/irq.h>
#include <arch/io_interface_mux.h>

#define GPIO_MAJOR 120  /* experimental MAJOR number */

#define D(x)

#if 0
static int dp_cnt;
#define DP(x) do { dp_cnt++; if (dp_cnt % 1000 == 0) x; }while(0)
#else
#define DP(x)
#endif

static char gpio_name[] = "etrax gpio";

#if 0
static wait_queue_head_t *gpio_wq;
#endif

static long gpio_ioctl(struct file *file, unsigned int cmd, unsigned long arg);
static ssize_t gpio_write(struct file *file, const char __user *buf,
	size_t count, loff_t *off);
static int gpio_open(struct inode *inode, struct file *filp);
static int gpio_release(struct inode *inode, struct file *filp);
static __poll_t gpio_poll(struct file *filp, struct poll_table_struct *wait);

/* private data per open() of this driver */

struct gpio_private {
	struct gpio_private *next;
	/* These fields are for PA and PB only */
	volatile unsigned char *port, *shadow;
	volatile unsigned char *dir, *dir_shadow;
	unsigned char changeable_dir;
	unsigned char changeable_bits;
	unsigned char clk_mask;
	unsigned char data_mask;
	unsigned char write_msb;
	unsigned char pad1, pad2, pad3;
	/* These fields are generic */
	unsigned long highalarm, lowalarm;
	wait_queue_head_t alarm_wq;
	int minor;
};

/* linked list of alarms to check for */

static struct gpio_private *alarmlist;

static int gpio_some_alarms; /* Set if someone uses alarm */
static unsigned long gpio_pa_irq_enabled_mask;

static DEFINE_SPINLOCK(gpio_lock); /* Protect directions etc */

/* Port A and B use 8 bit access, but Port G is 32 bit */
#define NUM_PORTS (GPIO_MINOR_B+1)

static volatile unsigned char *ports[NUM_PORTS] = {
	R_PORT_PA_DATA,
	R_PORT_PB_DATA,
};
static volatile unsigned char *shads[NUM_PORTS] = {
	&port_pa_data_shadow,
	&port_pb_data_shadow
};

/* What direction bits that are user changeable 1=changeable*/
#ifndef CONFIG_ETRAX_PA_CHANGEABLE_DIR
#define CONFIG_ETRAX_PA_CHANGEABLE_DIR 0x00
#endif
#ifndef CONFIG_ETRAX_PB_CHANGEABLE_DIR
#define CONFIG_ETRAX_PB_CHANGEABLE_DIR 0x00
#endif

#ifndef CONFIG_ETRAX_PA_CHANGEABLE_BITS
#define CONFIG_ETRAX_PA_CHANGEABLE_BITS 0xFF
#endif
#ifndef CONFIG_ETRAX_PB_CHANGEABLE_BITS
#define CONFIG_ETRAX_PB_CHANGEABLE_BITS 0xFF
#endif


static unsigned char changeable_dir[NUM_PORTS] = {
	CONFIG_ETRAX_PA_CHANGEABLE_DIR,
	CONFIG_ETRAX_PB_CHANGEABLE_DIR
};
static unsigned char changeable_bits[NUM_PORTS] = {
	CONFIG_ETRAX_PA_CHANGEABLE_BITS,
	CONFIG_ETRAX_PB_CHANGEABLE_BITS
};

static volatile unsigned char *dir[NUM_PORTS] = {
	R_PORT_PA_DIR,
	R_PORT_PB_DIR
};

static volatile unsigned char *dir_shadow[NUM_PORTS] = {
	&port_pa_dir_shadow,
	&port_pb_dir_shadow
};

/* All bits in port g that can change dir. */
static const unsigned long int changeable_dir_g_mask = 0x01FFFF01;

/* Port G is 32 bit, handle it special, some bits are both inputs
   and outputs at the same time, only some of the bits can change direction
   and some of them in groups of 8 bit. */
static unsigned long changeable_dir_g;
static unsigned long dir_g_in_bits;
static unsigned long dir_g_out_bits;
static unsigned long dir_g_shadow; /* 1=output */

#define USE_PORTS(priv) ((priv)->minor <= GPIO_MINOR_B)


static __poll_t gpio_poll(struct file *file, poll_table *wait)
{
	__poll_t mask = 0;
	struct gpio_private *priv = file->private_data;
	unsigned long data;
	unsigned long flags;

	spin_lock_irqsave(&gpio_lock, flags);

	poll_wait(file, &priv->alarm_wq, wait);
	if (priv->minor == GPIO_MINOR_A) {
		unsigned long tmp;
		data = *R_PORT_PA_DATA;
		/* PA has support for high level interrupt -
		 * lets activate for those low and with highalarm set
		 */
		tmp = ~data & priv->highalarm & 0xFF;
		tmp = (tmp << R_IRQ_MASK1_SET__pa0__BITNR);

		gpio_pa_irq_enabled_mask |= tmp;
		*R_IRQ_MASK1_SET = tmp;
	} else if (priv->minor == GPIO_MINOR_B)
		data = *R_PORT_PB_DATA;
	else if (priv->minor == GPIO_MINOR_G)
		data = *R_PORT_G_DATA;
	else {
		mask = 0;
		goto out;
	}

	if ((data & priv->highalarm) ||
	    (~data & priv->lowalarm)) {
		mask = EPOLLIN|EPOLLRDNORM;
	}

out:
	spin_unlock_irqrestore(&gpio_lock, flags);
	DP(printk("gpio_poll ready: mask 0x%08X\n", mask));

	return mask;
}

int etrax_gpio_wake_up_check(void)
{
	struct gpio_private *priv;
	unsigned long data = 0;
        int ret = 0;
	unsigned long flags;

	spin_lock_irqsave(&gpio_lock, flags);
	priv = alarmlist;
	while (priv) {
		if (USE_PORTS(priv))
			data = *priv->port;
		else if (priv->minor == GPIO_MINOR_G)
			data = *R_PORT_G_DATA;

		if ((data & priv->highalarm) ||
		    (~data & priv->lowalarm)) {
			DP(printk("etrax_gpio_wake_up_check %i\n",priv->minor));
			wake_up_interruptible(&priv->alarm_wq);
                        ret = 1;
		}
		priv = priv->next;
	}
	spin_unlock_irqrestore(&gpio_lock, flags);
        return ret;
}

static irqreturn_t
gpio_poll_timer_interrupt(int irq, void *dev_id)
{
	if (gpio_some_alarms) {
		etrax_gpio_wake_up_check();
                return IRQ_HANDLED;
	}
        return IRQ_NONE;
}

static irqreturn_t
gpio_interrupt(int irq, void *dev_id)
{
	unsigned long tmp;
	unsigned long flags;

	spin_lock_irqsave(&gpio_lock, flags);

	/* Find what PA interrupts are active */
	tmp = (*R_IRQ_READ1);

	/* Find those that we have enabled */
	tmp &= gpio_pa_irq_enabled_mask;

	/* Clear them.. */
	*R_IRQ_MASK1_CLR = tmp;
	gpio_pa_irq_enabled_mask &= ~tmp;

	spin_unlock_irqrestore(&gpio_lock, flags);

	if (gpio_some_alarms)
		return IRQ_RETVAL(etrax_gpio_wake_up_check());

        return IRQ_NONE;
}

static void gpio_write_bit(struct gpio_private *priv,
	unsigned char data, int bit)
{
	*priv->port = *priv->shadow &= ~(priv->clk_mask);
	if (data & 1 << bit)
		*priv->port = *priv->shadow |= priv->data_mask;
	else
		*priv->port = *priv->shadow &= ~(priv->data_mask);

	/* For FPGA: min 5.0ns (DCC) before CCLK high */
	*priv->port = *priv->shadow |= priv->clk_mask;
}

static void gpio_write_byte(struct gpio_private *priv, unsigned char data)
{
	int i;

	if (priv->write_msb)
		for (i = 7; i >= 0; i--)
			gpio_write_bit(priv, data, i);
	else
		for (i = 0; i <= 7; i++)
			gpio_write_bit(priv, data, i);
}

static ssize_t gpio_write(struct file *file, const char __user *buf,
	size_t count, loff_t *off)
{
	struct gpio_private *priv = file->private_data;
	unsigned long flags;
	ssize_t retval = count;

	if (priv->minor != GPIO_MINOR_A && priv->minor != GPIO_MINOR_B)
		return -EFAULT;

	if (!access_ok(VERIFY_READ, buf, count))
		return -EFAULT;

	spin_lock_irqsave(&gpio_lock, flags);

	/* It must have been configured using the IO_CFG_WRITE_MODE */
	/* Perhaps a better error code? */
	if (priv->clk_mask == 0 || priv->data_mask == 0) {
		retval = -EPERM;
		goto out;
	}

	D(printk(KERN_DEBUG "gpio_write: %02X to data 0x%02X "
		"clk 0x%02X msb: %i\n",
		count, priv->data_mask, priv->clk_mask, priv->write_msb));

	while (count--)
		gpio_write_byte(priv, *buf++);

out:
	spin_unlock_irqrestore(&gpio_lock, flags);
	return retval;
}



static int
gpio_open(struct inode *inode, struct file *filp)
{
	struct gpio_private *priv;
	int p = iminor(inode);
	unsigned long flags;

	if (p > GPIO_MINOR_LAST)
		return -EINVAL;

	priv = kzalloc(sizeof(struct gpio_private), GFP_KERNEL);

	if (!priv)
		return -ENOMEM;

	priv->minor = p;

	/* initialize the io/alarm struct */

	if (USE_PORTS(priv)) { /* A and B */
		priv->port = ports[p];
		priv->shadow = shads[p];
		priv->dir = dir[p];
		priv->dir_shadow = dir_shadow[p];
		priv->changeable_dir = changeable_dir[p];
		priv->changeable_bits = changeable_bits[p];
	} else {
		priv->port = NULL;
		priv->shadow = NULL;
		priv->dir = NULL;
		priv->dir_shadow = NULL;
		priv->changeable_dir = 0;
		priv->changeable_bits = 0;
	}

	priv->highalarm = 0;
	priv->lowalarm = 0;
	priv->clk_mask = 0;
	priv->data_mask = 0;
	init_waitqueue_head(&priv->alarm_wq);

	filp->private_data = priv;

	/* link it into our alarmlist */
	spin_lock_irqsave(&gpio_lock, flags);
	priv->next = alarmlist;
	alarmlist = priv;
	spin_unlock_irqrestore(&gpio_lock, flags);

	return 0;
}

static int
gpio_release(struct inode *inode, struct file *filp)
{
	struct gpio_private *p;
	struct gpio_private *todel;
	unsigned long flags;

	spin_lock_irqsave(&gpio_lock, flags);

	p = alarmlist;
	todel = filp->private_data;

	/* unlink from alarmlist and free the private structure */

	if (p == todel) {
		alarmlist = todel->next;
	} else {
		while (p->next != todel)
			p = p->next;
		p->next = todel->next;
	}

	kfree(todel);
	/* Check if there are still any alarms set */
	p = alarmlist;
	while (p) {
		if (p->highalarm | p->lowalarm) {
			gpio_some_alarms = 1;
			goto out;
		}
		p = p->next;
	}
	gpio_some_alarms = 0;
out:
	spin_unlock_irqrestore(&gpio_lock, flags);
	return 0;
}

/* Main device API. ioctl's to read/set/clear bits, as well as to
 * set alarms to wait for using a subsequent select().
 */
inline unsigned long setget_input(struct gpio_private *priv, unsigned long arg)
{
	/* Set direction 0=unchanged 1=input,
	 * return mask with 1=input */
	if (USE_PORTS(priv)) {
		*priv->dir = *priv->dir_shadow &=
		~((unsigned char)arg & priv->changeable_dir);
		return ~(*priv->dir_shadow) & 0xFF; /* Only 8 bits */
	}

	if (priv->minor != GPIO_MINOR_G)
		return 0;

	/* We must fiddle with R_GEN_CONFIG to change dir */
	if (((arg & dir_g_in_bits) != arg) &&
	    (arg & changeable_dir_g)) {
		arg &= changeable_dir_g;
		/* Clear bits in genconfig to set to input */
		if (arg & (1<<0)) {
			genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, g0dir);
			dir_g_in_bits |= (1<<0);
			dir_g_out_bits &= ~(1<<0);
		}
		if ((arg & 0x0000FF00) == 0x0000FF00) {
			genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, g8_15dir);
			dir_g_in_bits |= 0x0000FF00;
			dir_g_out_bits &= ~0x0000FF00;
		}
		if ((arg & 0x00FF0000) == 0x00FF0000) {
			genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, g16_23dir);
			dir_g_in_bits |= 0x00FF0000;
			dir_g_out_bits &= ~0x00FF0000;
		}
		if (arg & (1<<24)) {
			genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, g24dir);
			dir_g_in_bits |= (1<<24);
			dir_g_out_bits &= ~(1<<24);
		}
		D(printk(KERN_DEBUG "gpio: SETINPUT on port G set "
			 "genconfig to 0x%08lX "
			 "in_bits: 0x%08lX "
			 "out_bits: 0x%08lX\n",
			 (unsigned long)genconfig_shadow,
			 dir_g_in_bits, dir_g_out_bits));
		*R_GEN_CONFIG = genconfig_shadow;
		/* Must be a >120 ns delay before writing this again */

	}
	return dir_g_in_bits;
} /* setget_input */

inline unsigned long setget_output(struct gpio_private *priv, unsigned long arg)
{
	if (USE_PORTS(priv)) {
		*priv->dir = *priv->dir_shadow |=
			((unsigned char)arg & priv->changeable_dir);
		return *priv->dir_shadow;
	}
	if (priv->minor != GPIO_MINOR_G)
		return 0;

	/* We must fiddle with R_GEN_CONFIG to change dir */
	if (((arg & dir_g_out_bits) != arg) &&
	    (arg & changeable_dir_g)) {
		/* Set bits in genconfig to set to output */
		if (arg & (1<<0)) {
			genconfig_shadow |= IO_MASK(R_GEN_CONFIG, g0dir);
			dir_g_out_bits |= (1<<0);
			dir_g_in_bits &= ~(1<<0);
		}
		if ((arg & 0x0000FF00) == 0x0000FF00) {
			genconfig_shadow |= IO_MASK(R_GEN_CONFIG, g8_15dir);
			dir_g_out_bits |= 0x0000FF00;
			dir_g_in_bits &= ~0x0000FF00;
		}
		if ((arg & 0x00FF0000) == 0x00FF0000) {
			genconfig_shadow |= IO_MASK(R_GEN_CONFIG, g16_23dir);
			dir_g_out_bits |= 0x00FF0000;
			dir_g_in_bits &= ~0x00FF0000;
		}
		if (arg & (1<<24)) {
			genconfig_shadow |= IO_MASK(R_GEN_CONFIG, g24dir);
			dir_g_out_bits |= (1<<24);
			dir_g_in_bits &= ~(1<<24);
		}
		D(printk(KERN_INFO "gpio: SETOUTPUT on port G set "
			 "genconfig to 0x%08lX "
			 "in_bits: 0x%08lX "
			 "out_bits: 0x%08lX\n",
			 (unsigned long)genconfig_shadow,
			 dir_g_in_bits, dir_g_out_bits));
		*R_GEN_CONFIG = genconfig_shadow;
		/* Must be a >120 ns delay before writing this again */
	}
	return dir_g_out_bits & 0x7FFFFFFF;
} /* setget_output */

static int
gpio_leds_ioctl(unsigned int cmd, unsigned long arg);

static long gpio_ioctl(struct file *file, unsigned int cmd, unsigned long arg)
{
	unsigned long flags;
	unsigned long val;
        int ret = 0;

	struct gpio_private *priv = file->private_data;
	if (_IOC_TYPE(cmd) != ETRAXGPIO_IOCTYPE)
		return -EINVAL;

	switch (_IOC_NR(cmd)) {
	case IO_READBITS: /* Use IO_READ_INBITS and IO_READ_OUTBITS instead */
		// read the port
		spin_lock_irqsave(&gpio_lock, flags);
		if (USE_PORTS(priv)) {
			ret =  *priv->port;
		} else if (priv->minor == GPIO_MINOR_G) {
			ret =  (*R_PORT_G_DATA) & 0x7FFFFFFF;
		}
		spin_unlock_irqrestore(&gpio_lock, flags);

		break;
	case IO_SETBITS:
		// set changeable bits with a 1 in arg
		spin_lock_irqsave(&gpio_lock, flags);

		if (USE_PORTS(priv)) {
			*priv->port = *priv->shadow |=
			  ((unsigned char)arg & priv->changeable_bits);
		} else if (priv->minor == GPIO_MINOR_G) {
			*R_PORT_G_DATA = port_g_data_shadow |= (arg & dir_g_out_bits);
		}
		spin_unlock_irqrestore(&gpio_lock, flags);

		break;
	case IO_CLRBITS:
		// clear changeable bits with a 1 in arg
		spin_lock_irqsave(&gpio_lock, flags);
		if (USE_PORTS(priv)) {
			*priv->port = *priv->shadow &=
			 ~((unsigned char)arg & priv->changeable_bits);
		} else if (priv->minor == GPIO_MINOR_G) {
			*R_PORT_G_DATA = port_g_data_shadow &= ~((unsigned long)arg & dir_g_out_bits);
		}
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_HIGHALARM:
		// set alarm when bits with 1 in arg go high
		spin_lock_irqsave(&gpio_lock, flags);
		priv->highalarm |= arg;
		gpio_some_alarms = 1;
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_LOWALARM:
		// set alarm when bits with 1 in arg go low
		spin_lock_irqsave(&gpio_lock, flags);
		priv->lowalarm |= arg;
		gpio_some_alarms = 1;
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_CLRALARM:
		/* clear alarm for bits with 1 in arg */
		spin_lock_irqsave(&gpio_lock, flags);
		priv->highalarm &= ~arg;
		priv->lowalarm  &= ~arg;
		{
			/* Must update gpio_some_alarms */
			struct gpio_private *p = alarmlist;
			int some_alarms;
			p = alarmlist;
			some_alarms = 0;
			while (p) {
				if (p->highalarm | p->lowalarm) {
					some_alarms = 1;
					break;
				}
				p = p->next;
			}
			gpio_some_alarms = some_alarms;
		}
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_READDIR: /* Use IO_SETGET_INPUT/OUTPUT instead! */
		/* Read direction 0=input 1=output */
		spin_lock_irqsave(&gpio_lock, flags);
		if (USE_PORTS(priv)) {
			ret = *priv->dir_shadow;
		} else if (priv->minor == GPIO_MINOR_G) {
			/* Note: Some bits are both in and out,
			 * Those that are dual is set here as well.
			 */
			ret = (dir_g_shadow | dir_g_out_bits) & 0x7FFFFFFF;
		}
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_SETINPUT: /* Use IO_SETGET_INPUT instead! */
		/* Set direction 0=unchanged 1=input,
		 * return mask with 1=input
		 */
		spin_lock_irqsave(&gpio_lock, flags);
		ret = setget_input(priv, arg) & 0x7FFFFFFF;
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_SETOUTPUT: /* Use IO_SETGET_OUTPUT instead! */
		/* Set direction 0=unchanged 1=output,
		 * return mask with 1=output
		 */
		spin_lock_irqsave(&gpio_lock, flags);
		ret =  setget_output(priv, arg) & 0x7FFFFFFF;
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_SHUTDOWN:
		spin_lock_irqsave(&gpio_lock, flags);
		SOFT_SHUTDOWN();
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_GET_PWR_BT:
		spin_lock_irqsave(&gpio_lock, flags);
#if defined (CONFIG_ETRAX_SOFT_SHUTDOWN)
		ret = (*R_PORT_G_DATA & ( 1 << CONFIG_ETRAX_POWERBUTTON_BIT));
#else
		ret = 0;
#endif
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_CFG_WRITE_MODE:
		spin_lock_irqsave(&gpio_lock, flags);
		priv->clk_mask = arg & 0xFF;
		priv->data_mask = (arg >> 8) & 0xFF;
		priv->write_msb = (arg >> 16) & 0x01;
		/* Check if we're allowed to change the bits and
		 * the direction is correct
		 */
		if (!((priv->clk_mask & priv->changeable_bits) &&
		      (priv->data_mask & priv->changeable_bits) &&
		      (priv->clk_mask & *priv->dir_shadow) &&
		      (priv->data_mask & *priv->dir_shadow)))
		{
			priv->clk_mask = 0;
			priv->data_mask = 0;
			ret = -EPERM;
		}
		spin_unlock_irqrestore(&gpio_lock, flags);
		break;
	case IO_READ_INBITS:
		/* *arg is result of reading the input pins */
		spin_lock_irqsave(&gpio_lock, flags);
		if (USE_PORTS(priv)) {
			val = *priv->port;
		} else if (priv->minor == GPIO_MINOR_G) {
			val = *R_PORT_G_DATA;
		}
		spin_unlock_irqrestore(&gpio_lock, flags);
		if (copy_to_user((void __user *)arg, &val, sizeof(val)))
			ret = -EFAULT;
		break;
	case IO_READ_OUTBITS:
		 /* *arg is result of reading the output shadow */
		spin_lock_irqsave(&gpio_lock, flags);
		if (USE_PORTS(priv)) {
			val = *priv->shadow;
		} else if (priv->minor == GPIO_MINOR_G) {
			val = port_g_data_shadow;
		}
		spin_unlock_irqrestore(&gpio_lock, flags);
		if (copy_to_user((void __user *)arg, &val, sizeof(val)))
			ret = -EFAULT;
		break;
	case IO_SETGET_INPUT:
		/* bits set in *arg is set to input,
		 * *arg updated with current input pins.
		 */
		if (copy_from_user(&val, (void __user *)arg, sizeof(val)))
		{
			ret = -EFAULT;
			break;
		}
		spin_lock_irqsave(&gpio_lock, flags);
		val = setget_input(priv, val);
		spin_unlock_irqrestore(&gpio_lock, flags);
		if (copy_to_user((void __user *)arg, &val, sizeof(val)))
			ret = -EFAULT;
		break;
	case IO_SETGET_OUTPUT:
		/* bits set in *arg is set to output,
		 * *arg updated with current output pins.
		 */
		if (copy_from_user(&val, (void __user *)arg, sizeof(val))) {
			ret = -EFAULT;
			break;
		}
		spin_lock_irqsave(&gpio_lock, flags);
		val = setget_output(priv, val);
		spin_unlock_irqrestore(&gpio_lock, flags);
		if (copy_to_user((void __user *)arg, &val, sizeof(val)))
			ret = -EFAULT;
		break;
	default:
		spin_lock_irqsave(&gpio_lock, flags);
		if (priv->minor == GPIO_MINOR_LEDS)
			ret = gpio_leds_ioctl(cmd, arg);
		else
			ret = -EINVAL;
		spin_unlock_irqrestore(&gpio_lock, flags);
	} /* switch */

	return ret;
}

static int
gpio_leds_ioctl(unsigned int cmd, unsigned long arg)
{
	unsigned char green;
	unsigned char red;

	switch (_IOC_NR(cmd)) {
	case IO_LEDACTIVE_SET:
		green = ((unsigned char)arg) & 1;
		red   = (((unsigned char)arg) >> 1) & 1;
		CRIS_LED_ACTIVE_SET_G(green);
		CRIS_LED_ACTIVE_SET_R(red);
		break;

	case IO_LED_SETBIT:
		CRIS_LED_BIT_SET(arg);
		break;

	case IO_LED_CLRBIT:
		CRIS_LED_BIT_CLR(arg);
		break;

	default:
		return -EINVAL;
	} /* switch */

	return 0;
}

static const struct file_operations gpio_fops = {
	.owner          = THIS_MODULE,
	.poll           = gpio_poll,
	.unlocked_ioctl = gpio_ioctl,
	.write          = gpio_write,
	.open           = gpio_open,
	.release        = gpio_release,
	.llseek		= noop_llseek,
};

static void ioif_watcher(const unsigned int gpio_in_available,
	const unsigned int gpio_out_available,
	const unsigned char pa_available,
	const unsigned char pb_available)
{
	unsigned long int flags;

	D(printk(KERN_DEBUG "gpio.c: ioif_watcher called\n"));
	D(printk(KERN_DEBUG "gpio.c: G in: 0x%08x G out: 0x%08x "
		"PA: 0x%02x PB: 0x%02x\n",
		gpio_in_available, gpio_out_available,
		pa_available, pb_available));

	spin_lock_irqsave(&gpio_lock, flags);

	dir_g_in_bits = gpio_in_available;
	dir_g_out_bits = gpio_out_available;

	/* Initialise the dir_g_shadow etc. depending on genconfig */
	/* 0=input 1=output */
	if (genconfig_shadow & IO_STATE(R_GEN_CONFIG, g0dir, out))
		dir_g_shadow |= (1 << 0);
	if (genconfig_shadow & IO_STATE(R_GEN_CONFIG, g8_15dir, out))
		dir_g_shadow |= 0x0000FF00;
	if (genconfig_shadow & IO_STATE(R_GEN_CONFIG, g16_23dir, out))
		dir_g_shadow |= 0x00FF0000;
	if (genconfig_shadow & IO_STATE(R_GEN_CONFIG, g24dir, out))
		dir_g_shadow |= (1 << 24);

	changeable_dir_g = changeable_dir_g_mask;
	changeable_dir_g &= dir_g_out_bits;
	changeable_dir_g &= dir_g_in_bits;

	/* Correct the bits that can change direction */
	dir_g_out_bits &= ~changeable_dir_g;
	dir_g_out_bits |= dir_g_shadow;
	dir_g_in_bits &= ~changeable_dir_g;
	dir_g_in_bits |= (~dir_g_shadow & changeable_dir_g);

	spin_unlock_irqrestore(&gpio_lock, flags);

	printk(KERN_INFO "GPIO port G: in_bits: 0x%08lX out_bits: 0x%08lX "
		"val: %08lX\n",
	       dir_g_in_bits, dir_g_out_bits, (unsigned long)*R_PORT_G_DATA);
	printk(KERN_INFO "GPIO port G: dir: %08lX changeable: %08lX\n",
	       dir_g_shadow, changeable_dir_g);
}

/* main driver initialization routine, called from mem.c */

static int __init gpio_init(void)
{
	int res;
#if defined (CONFIG_ETRAX_CSP0_LEDS)
	int i;
#endif

	res = register_chrdev(GPIO_MAJOR, gpio_name, &gpio_fops);
	if (res < 0) {
		printk(KERN_ERR "gpio: couldn't get a major number.\n");
		return res;
	}

	/* Clear all leds */
#if defined (CONFIG_ETRAX_CSP0_LEDS) ||  defined (CONFIG_ETRAX_PA_LEDS) || defined (CONFIG_ETRAX_PB_LEDS)
	CRIS_LED_NETWORK_SET(0);
	CRIS_LED_ACTIVE_SET(0);
	CRIS_LED_DISK_READ(0);
	CRIS_LED_DISK_WRITE(0);

#if defined (CONFIG_ETRAX_CSP0_LEDS)
	for (i = 0; i < 32; i++)
		CRIS_LED_BIT_SET(i);
#endif

#endif
	/* The I/O interface allocation watcher will be called when
	 * registering it. */
	if (cris_io_interface_register_watcher(ioif_watcher)){
		printk(KERN_WARNING "gpio_init: Failed to install IO "
			"if allocator watcher\n");
	}

	printk(KERN_INFO "ETRAX 100LX GPIO driver v2.5, (c) 2001-2008 "
		"Axis Communications AB\n");
	/* We call etrax_gpio_wake_up_check() from timer interrupt and
	 * from default_idle() in kernel/process.c
	 * The check in default_idle() reduces latency from ~15 ms to ~6 ms
	 * in some tests.
	 */
	res = request_irq(TIMER0_IRQ_NBR, gpio_poll_timer_interrupt,
		IRQF_SHARED, "gpio poll", gpio_name);
	if (res) {
		printk(KERN_CRIT "err: timer0 irq for gpio\n");
		return res;
	}
	res = request_irq(PA_IRQ_NBR, gpio_interrupt,
		IRQF_SHARED, "gpio PA", gpio_name);
	if (res)
		printk(KERN_CRIT "err: PA irq for gpio\n");

	return res;
}

/* this makes sure that gpio_init is called during kernel boot */
module_init(gpio_init);

