/*
 * Copyright 2010-2011 Calxeda, Inc.
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms and conditions of the GNU General Public License,
 * version 2, as published by the Free Software Foundation.
 *
 * This program is distributed in the hope it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
 * more details.
 *
 * You should have received a copy of the GNU General Public License along with
 * this program.  If not, see <http://www.gnu.org/licenses/>.
 */
#include <linux/clk.h>
#include <linux/clkdev.h>
#include <linux/io.h>
#include <linux/irq.h>
#include <linux/irqdomain.h>
#include <linux/of.h>
#include <linux/of_irq.h>
#include <linux/of_platform.h>
#include <linux/of_address.h>

#include <asm/cacheflush.h>
#include <asm/unified.h>
#include <asm/smp_scu.h>
#include <asm/hardware/arm_timer.h>
#include <asm/hardware/timer-sp.h>
#include <asm/hardware/gic.h>
#include <asm/hardware/cache-l2x0.h>
#include <asm/mach/arch.h>
#include <asm/mach/map.h>
#include <asm/mach/time.h>
#include <mach/irqs.h>

#include "core.h"
#include "sysregs.h"

void __iomem *sregs_base;

#define HB_SCU_VIRT_BASE	0xfee00000
void __iomem *scu_base_addr = ((void __iomem *)(HB_SCU_VIRT_BASE));

static struct map_desc scu_io_desc __initdata = {
	.virtual	= HB_SCU_VIRT_BASE,
	.pfn		= 0, /* run-time */
	.length		= SZ_4K,
	.type		= MT_DEVICE,
};

static void __init highbank_scu_map_io(void)
{
	unsigned long base;

	/* Get SCU base */
	asm("mrc p15, 4, %0, c15, c0, 0" : "=r" (base));

	scu_io_desc.pfn = __phys_to_pfn(base);
	iotable_init(&scu_io_desc, 1);
}

static void __init highbank_map_io(void)
{
	highbank_scu_map_io();
	highbank_lluart_map_io();
}

#define HB_JUMP_TABLE_PHYS(cpu)		(0x40 + (0x10 * (cpu)))
#define HB_JUMP_TABLE_VIRT(cpu)		phys_to_virt(HB_JUMP_TABLE_PHYS(cpu))

void highbank_set_cpu_jump(int cpu, void *jump_addr)
{
	writel(BSYM(virt_to_phys(jump_addr)), HB_JUMP_TABLE_VIRT(cpu));
	__cpuc_flush_dcache_area(HB_JUMP_TABLE_VIRT(cpu), 16);
	outer_clean_range(HB_JUMP_TABLE_PHYS(cpu),
			  HB_JUMP_TABLE_PHYS(cpu) + 15);
}

const static struct of_device_id irq_match[] = {
	{ .compatible = "arm,cortex-a9-gic", .data = gic_of_init, },
	{}
};

static void __init highbank_init_irq(void)
{
	of_irq_init(irq_match);
	l2x0_of_init(0, ~0UL);
}

static void __init highbank_timer_init(void)
{
	int irq;
	struct device_node *np;
	void __iomem *timer_base;

	/* Map system registers */
	np = of_find_compatible_node(NULL, NULL, "calxeda,hb-sregs");
	sregs_base = of_iomap(np, 0);
	WARN_ON(!sregs_base);

	np = of_find_compatible_node(NULL, NULL, "arm,sp804");
	timer_base = of_iomap(np, 0);
	WARN_ON(!timer_base);
	irq = irq_of_parse_and_map(np, 0);

	highbank_clocks_init();

	sp804_clocksource_init(timer_base + 0x20, "timer1");
	sp804_clockevents_init(timer_base, irq, "timer0");
}

static struct sys_timer highbank_timer = {
	.init = highbank_timer_init,
};

static void highbank_power_off(void)
{
	hignbank_set_pwr_shutdown();
	scu_power_mode(scu_base_addr, SCU_PM_POWEROFF);

	while (1)
		cpu_do_idle();
}

static void __init highbank_init(void)
{
	pm_power_off = highbank_power_off;

	of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
}

static const char *highbank_match[] __initconst = {
	"calxeda,highbank",
	NULL,
};

DT_MACHINE_START(HIGHBANK, "Highbank")
	.map_io		= highbank_map_io,
	.init_irq	= highbank_init_irq,
	.timer		= &highbank_timer,
	.init_machine	= highbank_init,
	.dt_compat	= highbank_match,
MACHINE_END
