/*
 * arch/arm/mach-ixp2000/core.c
 *
 * Common routines used by all IXP2400/2800 based platforms.
 *
 * Author: Deepak Saxena <dsaxena@plexity.net>
 *
 * Copyright 2004 (C) MontaVista Software, Inc. 
 *
 * Based on work Copyright (C) 2002-2003 Intel Corporation
 * 
 * This file is licensed under the terms of the GNU General Public
 * License version 2. This program is licensed "as is" without any 
 * warranty of any kind, whether express or implied.
 */

#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/spinlock.h>
#include <linux/sched.h>
#include <linux/interrupt.h>
#include <linux/irq.h>
#include <linux/serial.h>
#include <linux/tty.h>
#include <linux/bitops.h>
#include <linux/serial_8250.h>
#include <linux/mm.h>

#include <asm/types.h>
#include <asm/setup.h>
#include <asm/memory.h>
#include <mach/hardware.h>
#include <asm/irq.h>
#include <asm/system.h>
#include <asm/tlbflush.h>
#include <asm/pgtable.h>

#include <asm/mach/map.h>
#include <asm/mach/time.h>
#include <asm/mach/irq.h>

#include <mach/gpio.h>

static DEFINE_SPINLOCK(ixp2000_slowport_lock);
static unsigned long ixp2000_slowport_irq_flags;

/*************************************************************************
 * Slowport access routines
 *************************************************************************/
void ixp2000_acquire_slowport(struct slowport_cfg *new_cfg, struct slowport_cfg *old_cfg)
{
	spin_lock_irqsave(&ixp2000_slowport_lock, ixp2000_slowport_irq_flags);

	old_cfg->CCR = *IXP2000_SLOWPORT_CCR;
	old_cfg->WTC = *IXP2000_SLOWPORT_WTC2;
	old_cfg->RTC = *IXP2000_SLOWPORT_RTC2;
	old_cfg->PCR = *IXP2000_SLOWPORT_PCR;
	old_cfg->ADC = *IXP2000_SLOWPORT_ADC;

	ixp2000_reg_write(IXP2000_SLOWPORT_CCR, new_cfg->CCR);
	ixp2000_reg_write(IXP2000_SLOWPORT_WTC2, new_cfg->WTC);
	ixp2000_reg_write(IXP2000_SLOWPORT_RTC2, new_cfg->RTC);
	ixp2000_reg_write(IXP2000_SLOWPORT_PCR, new_cfg->PCR);
	ixp2000_reg_wrb(IXP2000_SLOWPORT_ADC, new_cfg->ADC);
}

void ixp2000_release_slowport(struct slowport_cfg *old_cfg)
{
	ixp2000_reg_write(IXP2000_SLOWPORT_CCR, old_cfg->CCR);
	ixp2000_reg_write(IXP2000_SLOWPORT_WTC2, old_cfg->WTC);
	ixp2000_reg_write(IXP2000_SLOWPORT_RTC2, old_cfg->RTC);
	ixp2000_reg_write(IXP2000_SLOWPORT_PCR, old_cfg->PCR);
	ixp2000_reg_wrb(IXP2000_SLOWPORT_ADC, old_cfg->ADC);

	spin_unlock_irqrestore(&ixp2000_slowport_lock, 
					ixp2000_slowport_irq_flags);
}

/*************************************************************************
 * Chip specific mappings shared by all IXP2000 systems
 *************************************************************************/
static struct map_desc ixp2000_io_desc[] __initdata = {
	{
		.virtual	= IXP2000_CAP_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_CAP_PHYS_BASE),
		.length		= IXP2000_CAP_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_INTCTL_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_INTCTL_PHYS_BASE),
		.length		= IXP2000_INTCTL_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_PCI_CREG_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_PCI_CREG_PHYS_BASE),
		.length		= IXP2000_PCI_CREG_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_PCI_CSR_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_PCI_CSR_PHYS_BASE),
		.length		= IXP2000_PCI_CSR_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_MSF_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_MSF_PHYS_BASE),
		.length		= IXP2000_MSF_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_SCRATCH_RING_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_SCRATCH_RING_PHYS_BASE),
		.length		= IXP2000_SCRATCH_RING_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_SRAM0_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_SRAM0_PHYS_BASE),
		.length		= IXP2000_SRAM0_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_PCI_IO_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_PCI_IO_PHYS_BASE),
		.length		= IXP2000_PCI_IO_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_PCI_CFG0_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_PCI_CFG0_PHYS_BASE),
		.length		= IXP2000_PCI_CFG0_SIZE,
		.type		= MT_DEVICE,
	}, {
		.virtual	= IXP2000_PCI_CFG1_VIRT_BASE,
		.pfn		= __phys_to_pfn(IXP2000_PCI_CFG1_PHYS_BASE),
		.length		= IXP2000_PCI_CFG1_SIZE,
		.type		= MT_DEVICE,
	}
};

void __init ixp2000_map_io(void)
{
	iotable_init(ixp2000_io_desc, ARRAY_SIZE(ixp2000_io_desc));

	/* Set slowport to 8-bit mode.  */
	ixp2000_reg_wrb(IXP2000_SLOWPORT_FRM, 1);
}


/*************************************************************************
 * Serial port support for IXP2000
 *************************************************************************/
static struct plat_serial8250_port ixp2000_serial_port[] = {
	{
		.mapbase	= IXP2000_UART_PHYS_BASE,
		.membase	= (char *)(IXP2000_UART_VIRT_BASE + 3),
		.irq		= IRQ_IXP2000_UART,
		.flags		= UPF_BOOT_AUTOCONF | UPF_SKIP_TEST,
		.iotype		= UPIO_MEM,
		.regshift	= 2,
		.uartclk	= 50000000,
	},
	{ },
};

static struct resource ixp2000_uart_resource = {
	.start		= IXP2000_UART_PHYS_BASE,
	.end		= IXP2000_UART_PHYS_BASE + 0x1f,
	.flags		= IORESOURCE_MEM,
};

static struct platform_device ixp2000_serial_device = {
	.name		= "serial8250",
	.id		= PLAT8250_DEV_PLATFORM,
	.dev		= {
		.platform_data		= ixp2000_serial_port,
	},
	.num_resources	= 1,
	.resource	= &ixp2000_uart_resource,
};

void __init ixp2000_uart_init(void)
{
	platform_device_register(&ixp2000_serial_device);
}


/*************************************************************************
 * Timer-tick functions for IXP2000
 *************************************************************************/
static unsigned ticks_per_jiffy;
static unsigned ticks_per_usec;
static unsigned next_jiffy_time;
static volatile unsigned long *missing_jiffy_timer_csr;

unsigned long ixp2000_gettimeoffset (void)
{
 	unsigned long offset;

	offset = next_jiffy_time - *missing_jiffy_timer_csr;

	return offset / ticks_per_usec;
}

static int ixp2000_timer_interrupt(int irq, void *dev_id)
{
	/* clear timer 1 */
	ixp2000_reg_wrb(IXP2000_T1_CLR, 1);

	while ((signed long)(next_jiffy_time - *missing_jiffy_timer_csr)
							>= ticks_per_jiffy) {
		timer_tick();
		next_jiffy_time -= ticks_per_jiffy;
	}

	return IRQ_HANDLED;
}

static struct irqaction ixp2000_timer_irq = {
	.name		= "IXP2000 Timer Tick",
	.flags		= IRQF_DISABLED | IRQF_TIMER | IRQF_IRQPOLL,
	.handler	= ixp2000_timer_interrupt,
};

void __init ixp2000_init_time(unsigned long tick_rate)
{
	ticks_per_jiffy = (tick_rate + HZ/2) / HZ;
	ticks_per_usec = tick_rate / 1000000;

	/*
	 * We use timer 1 as our timer interrupt.
	 */
	ixp2000_reg_write(IXP2000_T1_CLR, 0);
	ixp2000_reg_write(IXP2000_T1_CLD, ticks_per_jiffy - 1);
	ixp2000_reg_write(IXP2000_T1_CTL, (1 << 7));

	/*
	 * We use a second timer as a monotonic counter for tracking
	 * missed jiffies.  The IXP2000 has four timers, but if we're
	 * on an A-step IXP2800, timer 2 and 3 don't work, so on those
	 * chips we use timer 4.  Timer 4 is the only timer that can
	 * be used for the watchdog, so we use timer 2 if we're on a
	 * non-buggy chip.
	 */
	if ((*IXP2000_PRODUCT_ID & 0x001ffef0) == 0x00000000) {
		printk(KERN_INFO "Enabling IXP2800 erratum #25 workaround\n");

		ixp2000_reg_write(IXP2000_T4_CLR, 0);
		ixp2000_reg_write(IXP2000_T4_CLD, -1);
		ixp2000_reg_wrb(IXP2000_T4_CTL, (1 << 7));
		missing_jiffy_timer_csr = IXP2000_T4_CSR;
	} else {
		ixp2000_reg_write(IXP2000_T2_CLR, 0);
		ixp2000_reg_write(IXP2000_T2_CLD, -1);
		ixp2000_reg_wrb(IXP2000_T2_CTL, (1 << 7));
		missing_jiffy_timer_csr = IXP2000_T2_CSR;
	}
 	next_jiffy_time = 0xffffffff;

	/* register for interrupt */
	setup_irq(IRQ_IXP2000_TIMER1, &ixp2000_timer_irq);
}

/*************************************************************************
 * GPIO helpers
 *************************************************************************/
static unsigned long GPIO_IRQ_falling_edge;
static unsigned long GPIO_IRQ_rising_edge;
static unsigned long GPIO_IRQ_level_low;
static unsigned long GPIO_IRQ_level_high;

static void update_gpio_int_csrs(void)
{
	ixp2000_reg_write(IXP2000_GPIO_FEDR, GPIO_IRQ_falling_edge);
	ixp2000_reg_write(IXP2000_GPIO_REDR, GPIO_IRQ_rising_edge);
	ixp2000_reg_write(IXP2000_GPIO_LSLR, GPIO_IRQ_level_low);
	ixp2000_reg_wrb(IXP2000_GPIO_LSHR, GPIO_IRQ_level_high);
}

void gpio_line_config(int line, int direction)
{
	unsigned long flags;

	local_irq_save(flags);
	if (direction == GPIO_OUT) {
		/* if it's an output, it ain't an interrupt anymore */
		GPIO_IRQ_falling_edge &= ~(1 << line);
		GPIO_IRQ_rising_edge &= ~(1 << line);
		GPIO_IRQ_level_low &= ~(1 << line);
		GPIO_IRQ_level_high &= ~(1 << line);
		update_gpio_int_csrs();

		ixp2000_reg_wrb(IXP2000_GPIO_PDSR, 1 << line);
	} else if (direction == GPIO_IN) {
		ixp2000_reg_wrb(IXP2000_GPIO_PDCR, 1 << line);
	}
	local_irq_restore(flags);
}
EXPORT_SYMBOL(gpio_line_config);


/*************************************************************************
 * IRQ handling IXP2000
 *************************************************************************/
static void ixp2000_GPIO_irq_handler(unsigned int irq, struct irq_desc *desc)
{                               
	int i;
	unsigned long status = *IXP2000_GPIO_INST;
		   
	for (i = 0; i <= 7; i++) {
		if (status & (1<<i)) {
			generic_handle_irq(i + IRQ_IXP2000_GPIO0);
		}
	}
}

static int ixp2000_GPIO_irq_type(unsigned int irq, unsigned int type)
{
	int line = irq - IRQ_IXP2000_GPIO0;

	/*
	 * First, configure this GPIO line as an input.
	 */
	ixp2000_reg_write(IXP2000_GPIO_PDCR, 1 << line);

	/*
	 * Then, set the proper trigger type.
	 */
	if (type & IRQ_TYPE_EDGE_FALLING)
		GPIO_IRQ_falling_edge |= 1 << line;
	else
		GPIO_IRQ_falling_edge &= ~(1 << line);
	if (type & IRQ_TYPE_EDGE_RISING)
		GPIO_IRQ_rising_edge |= 1 << line;
	else
		GPIO_IRQ_rising_edge &= ~(1 << line);
	if (type & IRQ_TYPE_LEVEL_LOW)
		GPIO_IRQ_level_low |= 1 << line;
	else
		GPIO_IRQ_level_low &= ~(1 << line);
	if (type & IRQ_TYPE_LEVEL_HIGH)
		GPIO_IRQ_level_high |= 1 << line;
	else
		GPIO_IRQ_level_high &= ~(1 << line);
	update_gpio_int_csrs();

	return 0;
}

static void ixp2000_GPIO_irq_mask_ack(unsigned int irq)
{
	ixp2000_reg_write(IXP2000_GPIO_INCR, (1 << (irq - IRQ_IXP2000_GPIO0)));

	ixp2000_reg_write(IXP2000_GPIO_EDSR, (1 << (irq - IRQ_IXP2000_GPIO0)));
	ixp2000_reg_write(IXP2000_GPIO_LDSR, (1 << (irq - IRQ_IXP2000_GPIO0)));
	ixp2000_reg_wrb(IXP2000_GPIO_INST, (1 << (irq - IRQ_IXP2000_GPIO0)));
}

static void ixp2000_GPIO_irq_mask(unsigned int irq)
{
	ixp2000_reg_wrb(IXP2000_GPIO_INCR, (1 << (irq - IRQ_IXP2000_GPIO0)));
}

static void ixp2000_GPIO_irq_unmask(unsigned int irq)
{
	ixp2000_reg_write(IXP2000_GPIO_INSR, (1 << (irq - IRQ_IXP2000_GPIO0)));
}

static struct irq_chip ixp2000_GPIO_irq_chip = {
	.ack		= ixp2000_GPIO_irq_mask_ack,
	.mask		= ixp2000_GPIO_irq_mask,
	.unmask		= ixp2000_GPIO_irq_unmask,
	.set_type	= ixp2000_GPIO_irq_type,
};

static void ixp2000_pci_irq_mask(unsigned int irq)
{
	unsigned long temp = *IXP2000_PCI_XSCALE_INT_ENABLE;
	if (irq == IRQ_IXP2000_PCIA)
		ixp2000_reg_wrb(IXP2000_PCI_XSCALE_INT_ENABLE, (temp & ~(1 << 26)));
	else if (irq == IRQ_IXP2000_PCIB)
		ixp2000_reg_wrb(IXP2000_PCI_XSCALE_INT_ENABLE, (temp & ~(1 << 27)));
}

static void ixp2000_pci_irq_unmask(unsigned int irq)
{
	unsigned long temp = *IXP2000_PCI_XSCALE_INT_ENABLE;
	if (irq == IRQ_IXP2000_PCIA)
		ixp2000_reg_write(IXP2000_PCI_XSCALE_INT_ENABLE, (temp | (1 << 26)));
	else if (irq == IRQ_IXP2000_PCIB)
		ixp2000_reg_write(IXP2000_PCI_XSCALE_INT_ENABLE, (temp | (1 << 27)));
}

/*
 * Error interrupts. These are used extensively by the microengine drivers
 */
static void ixp2000_err_irq_handler(unsigned int irq, struct irq_desc *desc)
{
	int i;
	unsigned long status = *IXP2000_IRQ_ERR_STATUS;

	for(i = 31; i >= 0; i--) {
		if(status & (1 << i)) {
			generic_handle_irq(IRQ_IXP2000_DRAM0_MIN_ERR + i);
		}
	}
}

static void ixp2000_err_irq_mask(unsigned int irq)
{
	ixp2000_reg_write(IXP2000_IRQ_ERR_ENABLE_CLR,
			(1 << (irq - IRQ_IXP2000_DRAM0_MIN_ERR)));
}

static void ixp2000_err_irq_unmask(unsigned int irq)
{
	ixp2000_reg_write(IXP2000_IRQ_ERR_ENABLE_SET,
			(1 << (irq - IRQ_IXP2000_DRAM0_MIN_ERR)));
}

static struct irq_chip ixp2000_err_irq_chip = {
	.ack	= ixp2000_err_irq_mask,
	.mask	= ixp2000_err_irq_mask,
	.unmask	= ixp2000_err_irq_unmask
};

static struct irq_chip ixp2000_pci_irq_chip = {
	.ack	= ixp2000_pci_irq_mask,
	.mask	= ixp2000_pci_irq_mask,
	.unmask	= ixp2000_pci_irq_unmask
};

static void ixp2000_irq_mask(unsigned int irq)
{
	ixp2000_reg_wrb(IXP2000_IRQ_ENABLE_CLR, (1 << irq));
}

static void ixp2000_irq_unmask(unsigned int irq)
{
	ixp2000_reg_write(IXP2000_IRQ_ENABLE_SET, (1 << irq));
}

static struct irq_chip ixp2000_irq_chip = {
	.ack	= ixp2000_irq_mask,
	.mask	= ixp2000_irq_mask,
	.unmask	= ixp2000_irq_unmask
};

void __init ixp2000_init_irq(void)
{
	int irq;

	/*
	 * Mask all sources
	 */
	ixp2000_reg_write(IXP2000_IRQ_ENABLE_CLR, 0xffffffff);
	ixp2000_reg_write(IXP2000_FIQ_ENABLE_CLR, 0xffffffff);

	/* clear all GPIO edge/level detects */
	ixp2000_reg_write(IXP2000_GPIO_REDR, 0);
	ixp2000_reg_write(IXP2000_GPIO_FEDR, 0);
	ixp2000_reg_write(IXP2000_GPIO_LSHR, 0);
	ixp2000_reg_write(IXP2000_GPIO_LSLR, 0);
	ixp2000_reg_write(IXP2000_GPIO_INCR, -1);

	/* clear PCI interrupt sources */
	ixp2000_reg_wrb(IXP2000_PCI_XSCALE_INT_ENABLE, 0);

	/*
	 * Certain bits in the IRQ status register of the 
	 * IXP2000 are reserved. Instead of trying to map
	 * things non 1:1 from bit position to IRQ number,
	 * we mark the reserved IRQs as invalid. This makes
	 * our mask/unmask code much simpler.
	 */
	for (irq = IRQ_IXP2000_SOFT_INT; irq <= IRQ_IXP2000_THDB3; irq++) {
		if ((1 << irq) & IXP2000_VALID_IRQ_MASK) {
			set_irq_chip(irq, &ixp2000_irq_chip);
			set_irq_handler(irq, handle_level_irq);
			set_irq_flags(irq, IRQF_VALID);
		} else set_irq_flags(irq, 0);
	}

	for (irq = IRQ_IXP2000_DRAM0_MIN_ERR; irq <= IRQ_IXP2000_SP_INT; irq++) {
		if((1 << (irq - IRQ_IXP2000_DRAM0_MIN_ERR)) &
				IXP2000_VALID_ERR_IRQ_MASK) {
			set_irq_chip(irq, &ixp2000_err_irq_chip);
			set_irq_handler(irq, handle_level_irq);
			set_irq_flags(irq, IRQF_VALID);
		}
		else
			set_irq_flags(irq, 0);
	}
	set_irq_chained_handler(IRQ_IXP2000_ERRSUM, ixp2000_err_irq_handler);

	for (irq = IRQ_IXP2000_GPIO0; irq <= IRQ_IXP2000_GPIO7; irq++) {
		set_irq_chip(irq, &ixp2000_GPIO_irq_chip);
		set_irq_handler(irq, handle_level_irq);
		set_irq_flags(irq, IRQF_VALID);
	}
	set_irq_chained_handler(IRQ_IXP2000_GPIO, ixp2000_GPIO_irq_handler);

	/*
	 * Enable PCI irqs.  The actual PCI[AB] decoding is done in
	 * entry-macro.S, so we don't need a chained handler for the
	 * PCI interrupt source.
	 */
	ixp2000_reg_write(IXP2000_IRQ_ENABLE_SET, (1 << IRQ_IXP2000_PCI));
	for (irq = IRQ_IXP2000_PCIA; irq <= IRQ_IXP2000_PCIB; irq++) {
		set_irq_chip(irq, &ixp2000_pci_irq_chip);
		set_irq_handler(irq, handle_level_irq);
		set_irq_flags(irq, IRQF_VALID);
	}
}

